aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm')
-rw-r--r--arch/arm/Kconfig20
-rw-r--r--arch/arm/boot/dts/Makefile2
-rw-r--r--arch/arm/boot/dts/exynos4210.dtsi22
-rw-r--r--arch/arm/boot/dts/exynos4212.dtsi22
-rw-r--r--arch/arm/boot/dts/exynos4412.dtsi24
-rw-r--r--arch/arm/boot/dts/exynos5250.dtsi22
-rw-r--r--arch/arm/boot/dts/integratorcp.dts6
-rw-r--r--arch/arm/boot/dts/omap3-beagle.dts71
-rw-r--r--arch/arm/boot/dts/omap3.dtsi31
-rw-r--r--arch/arm/boot/dts/omap4.dtsi30
-rw-r--r--arch/arm/boot/dts/r8a7779.dtsi98
-rw-r--r--arch/arm/boot/dts/tegra114-dalmore.dts14
-rw-r--r--arch/arm/boot/dts/tegra114-pluto.dts14
-rw-r--r--arch/arm/boot/dts/tegra114.dtsi12
-rw-r--r--arch/arm/boot/dts/tegra20-colibri-512.dtsi15
-rw-r--r--arch/arm/boot/dts/tegra20-harmony.dts17
-rw-r--r--arch/arm/boot/dts/tegra20-paz00.dts15
-rw-r--r--arch/arm/boot/dts/tegra20-seaboard.dts15
-rw-r--r--arch/arm/boot/dts/tegra20-tamonten.dtsi15
-rw-r--r--arch/arm/boot/dts/tegra20-trimslice.dts15
-rw-r--r--arch/arm/boot/dts/tegra20-ventana.dts15
-rw-r--r--arch/arm/boot/dts/tegra20-whistler.dts14
-rw-r--r--arch/arm/boot/dts/tegra20.dtsi4
-rw-r--r--arch/arm/boot/dts/tegra30-beaver.dts15
-rw-r--r--arch/arm/boot/dts/tegra30-cardhu.dtsi15
-rw-r--r--arch/arm/boot/dts/tegra30.dtsi6
-rw-r--r--arch/arm/boot/dts/versatile-ab.dts12
-rw-r--r--arch/arm/boot/dts/vexpress-v2p-ca9.dts1
-rw-r--r--arch/arm/boot/dts/vt8500.dtsi10
-rw-r--r--arch/arm/boot/dts/wm8505.dtsi10
-rw-r--r--arch/arm/boot/dts/wm8650.dtsi10
-rw-r--r--arch/arm/boot/dts/wm8850.dtsi10
-rw-r--r--arch/arm/boot/dts/zynq-7000.dtsi45
-rw-r--r--arch/arm/boot/dts/zynq-zc702.dts10
-rw-r--r--arch/arm/common/timer-sp.c140
-rw-r--r--arch/arm/include/asm/arch_timer.h13
-rw-r--r--arch/arm/include/asm/hardware/timer-sp.h16
-rw-r--r--arch/arm/include/asm/sched_clock.h2
-rw-r--r--arch/arm/include/asm/smp_twd.h8
-rw-r--r--arch/arm/kernel/arch_timer.c29
-rw-r--r--arch/arm/kernel/entry-armv.S13
-rw-r--r--arch/arm/kernel/process.c13
-rw-r--r--arch/arm/kernel/sched_clock.c15
-rw-r--r--arch/arm/kernel/smp_twd.c17
-rw-r--r--arch/arm/kernel/time.c7
-rw-r--r--arch/arm/mach-at91/at91sam9261.c2
-rw-r--r--arch/arm/mach-at91/at91sam9261_devices.c6
-rw-r--r--arch/arm/mach-at91/at91sam9263.c1
-rw-r--r--arch/arm/mach-at91/at91sam9263_devices.c2
-rw-r--r--arch/arm/mach-at91/at91sam9g45.c2
-rw-r--r--arch/arm/mach-at91/at91sam9g45_devices.c6
-rw-r--r--arch/arm/mach-at91/at91sam9rl.c1
-rw-r--r--arch/arm/mach-at91/at91sam9rl_devices.c2
-rw-r--r--arch/arm/mach-exynos/Kconfig10
-rw-r--r--arch/arm/mach-exynos/Makefile2
-rw-r--r--arch/arm/mach-exynos/common.c6
-rw-r--r--arch/arm/mach-exynos/common.h2
-rw-r--r--arch/arm/mach-exynos/include/mach/irqs.h6
-rw-r--r--arch/arm/mach-exynos/include/mach/map.h1
-rw-r--r--arch/arm/mach-exynos/include/mach/regs-mct.h53
-rw-r--r--arch/arm/mach-exynos/mach-armlex4210.c2
-rw-r--r--arch/arm/mach-exynos/mach-exynos4-dt.c3
-rw-r--r--arch/arm/mach-exynos/mach-exynos5-dt.c2
-rw-r--r--arch/arm/mach-exynos/mach-nuri.c2
-rw-r--r--arch/arm/mach-exynos/mach-origen.c2
-rw-r--r--arch/arm/mach-exynos/mach-smdk4x12.c4
-rw-r--r--arch/arm/mach-exynos/mach-smdkv310.c4
-rw-r--r--arch/arm/mach-exynos/mach-universal_c210.c6
-rw-r--r--arch/arm/mach-exynos/mct.c485
-rw-r--r--arch/arm/mach-highbank/highbank.c27
-rw-r--r--arch/arm/mach-imx/clk-busy.c2
-rw-r--r--arch/arm/mach-imx/mach-imx6q.c5
-rw-r--r--arch/arm/mach-integrator/integrator_ap.c6
-rw-r--r--arch/arm/mach-integrator/integrator_cp.c41
-rw-r--r--arch/arm/mach-omap2/board-3430sdp.c21
-rw-r--r--arch/arm/mach-omap2/board-3630sdp.c21
-rw-r--r--arch/arm/mach-omap2/board-am3517crane.c24
-rw-r--r--arch/arm/mach-omap2/board-am3517evm.c17
-rw-r--r--arch/arm/mach-omap2/board-cm-t35.c20
-rw-r--r--arch/arm/mach-omap2/board-cm-t3517.c22
-rw-r--r--arch/arm/mach-omap2/board-devkit8000.c8
-rw-r--r--arch/arm/mach-omap2/board-generic.c2
-rw-r--r--arch/arm/mach-omap2/board-igep0020.c32
-rw-r--r--arch/arm/mach-omap2/board-omap3beagle.c34
-rw-r--r--arch/arm/mach-omap2/board-omap3evm.c25
-rw-r--r--arch/arm/mach-omap2/board-omap3pandora.c21
-rw-r--r--arch/arm/mach-omap2/board-omap3stalker.c17
-rw-r--r--arch/arm/mach-omap2/board-omap3touchbook.c17
-rw-r--r--arch/arm/mach-omap2/board-omap4panda.c55
-rw-r--r--arch/arm/mach-omap2/board-overo.c16
-rw-r--r--arch/arm/mach-omap2/board-zoom.c16
-rw-r--r--arch/arm/mach-omap2/clock.c2
-rw-r--r--arch/arm/mach-omap2/common.h3
-rw-r--r--arch/arm/mach-omap2/gpmc-nand.c42
-rw-r--r--arch/arm/mach-omap2/gpmc-onenand.c122
-rw-r--r--arch/arm/mach-omap2/gpmc-smc91x.c30
-rw-r--r--arch/arm/mach-omap2/gpmc.c548
-rw-r--r--arch/arm/mach-omap2/gpmc.h43
-rw-r--r--arch/arm/mach-omap2/omap_device.c13
-rw-r--r--arch/arm/mach-omap2/omap_hwmod.c4
-rw-r--r--arch/arm/mach-omap2/pm-debug.c6
-rw-r--r--arch/arm/mach-omap2/powerdomain.c2
-rw-r--r--arch/arm/mach-omap2/timer.c133
-rw-r--r--arch/arm/mach-omap2/usb-host.c160
-rw-r--r--arch/arm/mach-omap2/usb-tusb6010.c62
-rw-r--r--arch/arm/mach-omap2/usb.h9
-rw-r--r--arch/arm/mach-s3c24xx/Kconfig7
-rw-r--r--arch/arm/mach-s3c24xx/Makefile8
-rw-r--r--arch/arm/mach-s3c24xx/bast-irq.c2
-rw-r--r--arch/arm/mach-s3c24xx/clock-s3c2410.c1
-rw-r--r--arch/arm/mach-s3c24xx/clock-s3c2412.c1
-rw-r--r--arch/arm/mach-s3c24xx/clock-s3c2416.c1
-rw-r--r--arch/arm/mach-s3c24xx/clock-s3c2443.c1
-rw-r--r--arch/arm/mach-s3c24xx/common-smdk.c3
-rw-r--r--arch/arm/mach-s3c24xx/common-smdk.h (renamed from arch/arm/plat-samsung/include/plat/common-smdk.h)3
-rw-r--r--arch/arm/mach-s3c24xx/common.c7
-rw-r--r--arch/arm/mach-s3c24xx/common.h94
-rw-r--r--arch/arm/mach-s3c24xx/dma-s3c2410.c1
-rw-r--r--arch/arm/mach-s3c24xx/dma-s3c2412.c1
-rw-r--r--arch/arm/mach-s3c24xx/dma-s3c2440.c1
-rw-r--r--arch/arm/mach-s3c24xx/dma-s3c2443.c1
-rw-r--r--arch/arm/mach-s3c24xx/include/mach/entry-macro.S70
-rw-r--r--arch/arm/mach-s3c24xx/include/mach/irqs.h58
-rw-r--r--arch/arm/mach-s3c24xx/include/mach/regs-sdi.h127
-rw-r--r--arch/arm/mach-s3c24xx/irq-pm.c7
-rw-r--r--arch/arm/mach-s3c24xx/irq-s3c2412.c215
-rw-r--r--arch/arm/mach-s3c24xx/irq-s3c2440.c128
-rw-r--r--arch/arm/mach-s3c24xx/irq-s3c244x.c142
-rw-r--r--arch/arm/mach-s3c24xx/irq.c822
-rw-r--r--arch/arm/mach-s3c24xx/mach-amlm5900.c7
-rw-r--r--arch/arm/mach-s3c24xx/mach-anubis.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-at2440evb.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-bast.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-gta02.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-h1940.c12
-rw-r--r--arch/arm/mach-s3c24xx/mach-jive.c8
-rw-r--r--arch/arm/mach-s3c24xx/mach-mini2440.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-n30.c11
-rw-r--r--arch/arm/mach-s3c24xx/mach-nexcoder.c8
-rw-r--r--arch/arm/mach-s3c24xx/mach-osiris.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-otom.c7
-rw-r--r--arch/arm/mach-s3c24xx/mach-qt2410.c8
-rw-r--r--arch/arm/mach-s3c24xx/mach-rx1950.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-rx3715.c11
-rw-r--r--arch/arm/mach-s3c24xx/mach-smdk2410.c9
-rw-r--r--arch/arm/mach-s3c24xx/mach-smdk2413.c19
-rw-r--r--arch/arm/mach-s3c24xx/mach-smdk2416.c8
-rw-r--r--arch/arm/mach-s3c24xx/mach-smdk2440.c11
-rw-r--r--arch/arm/mach-s3c24xx/mach-smdk2443.c9
-rw-r--r--arch/arm/mach-s3c24xx/mach-tct_hammer.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-vr1000.c6
-rw-r--r--arch/arm/mach-s3c24xx/mach-vstms.c9
-rw-r--r--arch/arm/mach-s3c24xx/pm-s3c2412.c9
-rw-r--r--arch/arm/mach-s3c24xx/s3c2410.c1
-rw-r--r--arch/arm/mach-s3c24xx/s3c2412.c1
-rw-r--r--arch/arm/mach-s3c24xx/s3c2416.c1
-rw-r--r--arch/arm/mach-s3c24xx/s3c2440.c1
-rw-r--r--arch/arm/mach-s3c24xx/s3c2442.c1
-rw-r--r--arch/arm/mach-s3c24xx/s3c2443.c1
-rw-r--r--arch/arm/mach-s3c24xx/s3c244x.c2
-rw-r--r--arch/arm/mach-s3c64xx/Kconfig2
-rw-r--r--arch/arm/mach-s3c64xx/mach-anw6410.c4
-rw-r--r--arch/arm/mach-s3c64xx/mach-crag6410.c4
-rw-r--r--arch/arm/mach-s3c64xx/mach-hmt.c4
-rw-r--r--arch/arm/mach-s3c64xx/mach-mini6410.c4
-rw-r--r--arch/arm/mach-s3c64xx/mach-ncp.c4
-rw-r--r--arch/arm/mach-s3c64xx/mach-real6410.c4
-rw-r--r--arch/arm/mach-s3c64xx/mach-smartq.c2
-rw-r--r--arch/arm/mach-s3c64xx/mach-smartq5.c3
-rw-r--r--arch/arm/mach-s3c64xx/mach-smartq7.c3
-rw-r--r--arch/arm/mach-s3c64xx/mach-smdk6400.c4
-rw-r--r--arch/arm/mach-s3c64xx/mach-smdk6410.c4
-rw-r--r--arch/arm/mach-s5p64x0/Kconfig4
-rw-r--r--arch/arm/mach-s5p64x0/mach-smdk6440.c6
-rw-r--r--arch/arm/mach-s5p64x0/mach-smdk6450.c6
-rw-r--r--arch/arm/mach-s5pc100/Kconfig1
-rw-r--r--arch/arm/mach-s5pc100/mach-smdkc100.c4
-rw-r--r--arch/arm/mach-s5pv210/Kconfig2
-rw-r--r--arch/arm/mach-s5pv210/mach-aquila.c6
-rw-r--r--arch/arm/mach-s5pv210/mach-goni.c6
-rw-r--r--arch/arm/mach-s5pv210/mach-smdkc110.c6
-rw-r--r--arch/arm/mach-s5pv210/mach-smdkv210.c6
-rw-r--r--arch/arm/mach-s5pv210/mach-torbreck.c6
-rw-r--r--arch/arm/mach-shmobile/Kconfig2
-rw-r--r--arch/arm/mach-shmobile/Makefile7
-rw-r--r--arch/arm/mach-shmobile/board-kzm9d.c1
-rw-r--r--arch/arm/mach-shmobile/board-kzm9g.c14
-rw-r--r--arch/arm/mach-shmobile/clock-r8a7740.c13
-rw-r--r--arch/arm/mach-shmobile/clock-r8a7779.c8
-rw-r--r--arch/arm/mach-shmobile/clock-sh73a0.c7
-rw-r--r--arch/arm/mach-shmobile/headsmp-scu.S (renamed from arch/arm/mach-shmobile/headsmp-sh73a0.S)15
-rw-r--r--arch/arm/mach-shmobile/hotplug.c68
-rw-r--r--arch/arm/mach-shmobile/include/mach/common.h22
-rw-r--r--arch/arm/mach-shmobile/include/mach/irqs.h5
-rw-r--r--arch/arm/mach-shmobile/intc-r8a7779.c78
-rw-r--r--arch/arm/mach-shmobile/intc-sh73a0.c125
-rw-r--r--arch/arm/mach-shmobile/setup-emev2.c5
-rw-r--r--arch/arm/mach-shmobile/setup-r8a7740.c1
-rw-r--r--arch/arm/mach-shmobile/setup-r8a7779.c104
-rw-r--r--arch/arm/mach-shmobile/setup-sh7372.c1
-rw-r--r--arch/arm/mach-shmobile/setup-sh73a0.c163
-rw-r--r--arch/arm/mach-shmobile/smp-emev2.c86
-rw-r--r--arch/arm/mach-shmobile/smp-r8a7779.c129
-rw-r--r--arch/arm/mach-shmobile/smp-sh73a0.c36
-rw-r--r--arch/arm/mach-shmobile/timer.c7
-rw-r--r--arch/arm/mach-spear/spear13xx.c6
-rw-r--r--arch/arm/mach-tegra/Makefile5
-rw-r--r--arch/arm/mach-tegra/board-dt-tegra114.c46
-rw-r--r--arch/arm/mach-tegra/board-dt-tegra30.c60
-rw-r--r--arch/arm/mach-tegra/board-harmony-pcie.c13
-rw-r--r--arch/arm/mach-tegra/board.h4
-rw-r--r--arch/arm/mach-tegra/common.c31
-rw-r--r--arch/arm/mach-tegra/cpuidle-tegra20.c6
-rw-r--r--arch/arm/mach-tegra/cpuidle-tegra30.c10
-rw-r--r--arch/arm/mach-tegra/fuse.c4
-rw-r--r--arch/arm/mach-tegra/fuse.h7
-rw-r--r--arch/arm/mach-tegra/headsmp.S3
-rw-r--r--arch/arm/mach-tegra/hotplug.c23
-rw-r--r--arch/arm/mach-tegra/irq.c96
-rw-r--r--arch/arm/mach-tegra/irq.h6
-rw-r--r--arch/arm/mach-tegra/platsmp.c119
-rw-r--r--arch/arm/mach-tegra/pm.c150
-rw-r--r--arch/arm/mach-tegra/pm.h17
-rw-r--r--arch/arm/mach-tegra/pmc.c310
-rw-r--r--arch/arm/mach-tegra/pmc.h18
-rw-r--r--arch/arm/mach-tegra/reset-handler.S48
-rw-r--r--arch/arm/mach-tegra/sleep.h10
-rw-r--r--arch/arm/mach-tegra/tegra.c (renamed from arch/arm/mach-tegra/board-dt-tegra20.c)48
-rw-r--r--arch/arm/mach-tegra/tegra114_speedo.c104
-rw-r--r--arch/arm/mach-tegra/tegra2_emc.c2
-rw-r--r--arch/arm/mach-ux500/board-mop500-pins.c34
-rw-r--r--arch/arm/mach-ux500/cpu.c5
-rw-r--r--arch/arm/mach-ux500/timer.c3
-rw-r--r--arch/arm/mach-versatile/core.c26
-rw-r--r--arch/arm/mach-versatile/versatile_dt.c1
-rw-r--r--arch/arm/mach-vexpress/v2m.c25
-rw-r--r--arch/arm/mach-virt/virt.c9
-rw-r--r--arch/arm/mach-vt8500/Kconfig1
-rw-r--r--arch/arm/mach-zynq/Kconfig1
-rw-r--r--arch/arm/mach-zynq/Makefile2
-rw-r--r--arch/arm/mach-zynq/common.c3
-rw-r--r--arch/arm/mach-zynq/common.h2
-rw-r--r--arch/arm/mach-zynq/timer.c324
-rw-r--r--arch/arm/plat-omap/dmtimer.c12
-rw-r--r--arch/arm/plat-samsung/Kconfig2
-rw-r--r--arch/arm/plat-samsung/Makefile3
-rw-r--r--arch/arm/plat-samsung/include/plat/cpu.h15
-rw-r--r--arch/arm/plat-samsung/include/plat/irq.h116
-rw-r--r--arch/arm/plat-samsung/include/plat/s3c2410.h31
-rw-r--r--arch/arm/plat-samsung/include/plat/s3c2412.h32
-rw-r--r--arch/arm/plat-samsung/include/plat/s3c2416.h37
-rw-r--r--arch/arm/plat-samsung/include/plat/s3c2443.h36
-rw-r--r--arch/arm/plat-samsung/include/plat/s3c244x.h42
-rw-r--r--arch/arm/plat-samsung/include/plat/s5p-time.h40
-rw-r--r--arch/arm/plat-samsung/include/plat/samsung-time.h53
-rw-r--r--arch/arm/plat-samsung/samsung-time.c (renamed from arch/arm/plat-samsung/s5p-time.c)138
-rw-r--r--arch/arm/plat-samsung/time.c287
257 files changed, 3564 insertions, 4933 deletions
diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig
index 5fa0cc590887..38b5d5dad8e4 100644
--- a/arch/arm/Kconfig
+++ b/arch/arm/Kconfig
@@ -673,6 +673,7 @@ config ARCH_TEGRA
673 select HAVE_CLK 673 select HAVE_CLK
674 select HAVE_SMP 674 select HAVE_SMP
675 select MIGHT_HAVE_CACHE_L2X0 675 select MIGHT_HAVE_CACHE_L2X0
676 select SOC_BUS
676 select SPARSE_IRQ 677 select SPARSE_IRQ
677 select USE_OF 678 select USE_OF
678 help 679 help
@@ -769,12 +770,15 @@ config ARCH_SA1100
769config ARCH_S3C24XX 770config ARCH_S3C24XX
770 bool "Samsung S3C24XX SoCs" 771 bool "Samsung S3C24XX SoCs"
771 select ARCH_HAS_CPUFREQ 772 select ARCH_HAS_CPUFREQ
772 select ARCH_USES_GETTIMEOFFSET
773 select CLKDEV_LOOKUP 773 select CLKDEV_LOOKUP
774 select CLKSRC_MMIO
775 select GENERIC_CLOCKEVENTS
776 select GENERIC_GPIO
774 select HAVE_CLK 777 select HAVE_CLK
775 select HAVE_S3C2410_I2C if I2C 778 select HAVE_S3C2410_I2C if I2C
776 select HAVE_S3C2410_WATCHDOG if WATCHDOG 779 select HAVE_S3C2410_WATCHDOG if WATCHDOG
777 select HAVE_S3C_RTC if RTC_CLASS 780 select HAVE_S3C_RTC if RTC_CLASS
781 select MULTI_IRQ_HANDLER
778 select NEED_MACH_GPIO_H 782 select NEED_MACH_GPIO_H
779 select NEED_MACH_IO_H 783 select NEED_MACH_IO_H
780 help 784 help
@@ -787,10 +791,11 @@ config ARCH_S3C64XX
787 bool "Samsung S3C64XX" 791 bool "Samsung S3C64XX"
788 select ARCH_HAS_CPUFREQ 792 select ARCH_HAS_CPUFREQ
789 select ARCH_REQUIRE_GPIOLIB 793 select ARCH_REQUIRE_GPIOLIB
790 select ARCH_USES_GETTIMEOFFSET
791 select ARM_VIC 794 select ARM_VIC
792 select CLKDEV_LOOKUP 795 select CLKDEV_LOOKUP
796 select CLKSRC_MMIO
793 select CPU_V6 797 select CPU_V6
798 select GENERIC_CLOCKEVENTS
794 select HAVE_CLK 799 select HAVE_CLK
795 select HAVE_S3C2410_I2C if I2C 800 select HAVE_S3C2410_I2C if I2C
796 select HAVE_S3C2410_WATCHDOG if WATCHDOG 801 select HAVE_S3C2410_WATCHDOG if WATCHDOG
@@ -824,9 +829,11 @@ config ARCH_S5P64X0
824 829
825config ARCH_S5PC100 830config ARCH_S5PC100
826 bool "Samsung S5PC100" 831 bool "Samsung S5PC100"
827 select ARCH_USES_GETTIMEOFFSET
828 select CLKDEV_LOOKUP 832 select CLKDEV_LOOKUP
833 select CLKSRC_MMIO
829 select CPU_V7 834 select CPU_V7
835 select GENERIC_CLOCKEVENTS
836 select GENERIC_GPIO
830 select HAVE_CLK 837 select HAVE_CLK
831 select HAVE_S3C2410_I2C if I2C 838 select HAVE_S3C2410_I2C if I2C
832 select HAVE_S3C2410_WATCHDOG if WATCHDOG 839 select HAVE_S3C2410_WATCHDOG if WATCHDOG
@@ -1165,6 +1172,7 @@ config PLAT_VERSATILE
1165config ARM_TIMER_SP804 1172config ARM_TIMER_SP804
1166 bool 1173 bool
1167 select CLKSRC_MMIO 1174 select CLKSRC_MMIO
1175 select CLKSRC_OF if OF
1168 select HAVE_SCHED_CLOCK 1176 select HAVE_SCHED_CLOCK
1169 1177
1170source arch/arm/mm/Kconfig 1178source arch/arm/mm/Kconfig
@@ -1595,6 +1603,7 @@ config HAVE_ARM_ARCH_TIMER
1595config HAVE_ARM_TWD 1603config HAVE_ARM_TWD
1596 bool 1604 bool
1597 depends on SMP 1605 depends on SMP
1606 select CLKSRC_OF if OF
1598 help 1607 help
1599 This options enables support for the ARM timer and watchdog unit 1608 This options enables support for the ARM timer and watchdog unit
1600 1609
@@ -1648,7 +1657,7 @@ config LOCAL_TIMERS
1648 bool "Use local timer interrupts" 1657 bool "Use local timer interrupts"
1649 depends on SMP 1658 depends on SMP
1650 default y 1659 default y
1651 select HAVE_ARM_TWD if (!ARCH_MSM_SCORPIONMP && !EXYNOS4_MCT) 1660 select HAVE_ARM_TWD if (!ARCH_MSM_SCORPIONMP && !CLKSRC_EXYNOS_MCT)
1652 help 1661 help
1653 Enable support for local timers on SMP platforms, rather then the 1662 Enable support for local timers on SMP platforms, rather then the
1654 legacy IPI broadcast method. Local timers allows the system 1663 legacy IPI broadcast method. Local timers allows the system
@@ -1663,7 +1672,8 @@ config ARCH_NR_GPIO
1663 default 1024 if ARCH_SHMOBILE || ARCH_TEGRA 1672 default 1024 if ARCH_SHMOBILE || ARCH_TEGRA
1664 default 512 if SOC_OMAP5 1673 default 512 if SOC_OMAP5
1665 default 355 if ARCH_U8500 1674 default 355 if ARCH_U8500
1666 default 288 if ARCH_VT8500 || ARCH_SUNXI 1675 default 352 if ARCH_VT8500
1676 default 288 if ARCH_SUNXI
1667 default 264 if MACH_H4700 1677 default 264 if MACH_H4700
1668 default 0 1678 default 0
1669 help 1679 help
diff --git a/arch/arm/boot/dts/Makefile b/arch/arm/boot/dts/Makefile
index 234e78f7014e..e35b0a7ac77b 100644
--- a/arch/arm/boot/dts/Makefile
+++ b/arch/arm/boot/dts/Makefile
@@ -170,6 +170,8 @@ dtb-$(CONFIG_ARCH_TEGRA) += tegra20-harmony.dtb \
170 tegra30-cardhu-a04.dtb \ 170 tegra30-cardhu-a04.dtb \
171 tegra114-dalmore.dtb \ 171 tegra114-dalmore.dtb \
172 tegra114-pluto.dtb 172 tegra114-pluto.dtb
173dtb-$(CONFIG_ARCH_VERSATILE) += versatile-ab.dtb \
174 versatile-pb.dtb
173dtb-$(CONFIG_ARCH_VEXPRESS) += vexpress-v2p-ca5s.dtb \ 175dtb-$(CONFIG_ARCH_VEXPRESS) += vexpress-v2p-ca5s.dtb \
174 vexpress-v2p-ca9.dtb \ 176 vexpress-v2p-ca9.dtb \
175 vexpress-v2p-ca15-tc1.dtb \ 177 vexpress-v2p-ca15-tc1.dtb \
diff --git a/arch/arm/boot/dts/exynos4210.dtsi b/arch/arm/boot/dts/exynos4210.dtsi
index 2feffc70814c..49a2786e00b9 100644
--- a/arch/arm/boot/dts/exynos4210.dtsi
+++ b/arch/arm/boot/dts/exynos4210.dtsi
@@ -47,6 +47,28 @@
47 <0 12 0>, <0 13 0>, <0 14 0>, <0 15 0>; 47 <0 12 0>, <0 13 0>, <0 14 0>, <0 15 0>;
48 }; 48 };
49 49
50 mct@10050000 {
51 compatible = "samsung,exynos4210-mct";
52 reg = <0x10050000 0x800>;
53 interrupt-controller;
54 #interrups-cells = <2>;
55 interrupt-parent = <&mct_map>;
56 interrupts = <0 0>, <1 0>, <2 0>, <3 0>,
57 <4 0>, <5 0>;
58
59 mct_map: mct-map {
60 #interrupt-cells = <2>;
61 #address-cells = <0>;
62 #size-cells = <0>;
63 interrupt-map = <0x0 0 &gic 0 57 0>,
64 <0x1 0 &gic 0 69 0>,
65 <0x2 0 &combiner 12 6>,
66 <0x3 0 &combiner 12 7>,
67 <0x4 0 &gic 0 42 0>,
68 <0x5 0 &gic 0 48 0>;
69 };
70 };
71
50 pinctrl_0: pinctrl@11400000 { 72 pinctrl_0: pinctrl@11400000 {
51 compatible = "samsung,exynos4210-pinctrl"; 73 compatible = "samsung,exynos4210-pinctrl";
52 reg = <0x11400000 0x1000>; 74 reg = <0x11400000 0x1000>;
diff --git a/arch/arm/boot/dts/exynos4212.dtsi b/arch/arm/boot/dts/exynos4212.dtsi
index c6ae2005961f..36d4299789ef 100644
--- a/arch/arm/boot/dts/exynos4212.dtsi
+++ b/arch/arm/boot/dts/exynos4212.dtsi
@@ -25,4 +25,26 @@
25 gic:interrupt-controller@10490000 { 25 gic:interrupt-controller@10490000 {
26 cpu-offset = <0x8000>; 26 cpu-offset = <0x8000>;
27 }; 27 };
28
29 mct@10050000 {
30 compatible = "samsung,exynos4412-mct";
31 reg = <0x10050000 0x800>;
32 interrupt-controller;
33 #interrups-cells = <2>;
34 interrupt-parent = <&mct_map>;
35 interrupts = <0 0>, <1 0>, <2 0>, <3 0>,
36 <4 0>, <5 0>;
37
38 mct_map: mct-map {
39 #interrupt-cells = <2>;
40 #address-cells = <0>;
41 #size-cells = <0>;
42 interrupt-map = <0x0 0 &gic 0 57 0>,
43 <0x1 0 &combiner 12 5>,
44 <0x2 0 &combiner 12 6>,
45 <0x3 0 &combiner 12 7>,
46 <0x4 0 &gic 1 12 0>,
47 <0x5 0 &gic 1 12 0>;
48 };
49 };
28}; 50};
diff --git a/arch/arm/boot/dts/exynos4412.dtsi b/arch/arm/boot/dts/exynos4412.dtsi
index d7dfe312772a..821c9fdd1e3b 100644
--- a/arch/arm/boot/dts/exynos4412.dtsi
+++ b/arch/arm/boot/dts/exynos4412.dtsi
@@ -25,4 +25,28 @@
25 gic:interrupt-controller@10490000 { 25 gic:interrupt-controller@10490000 {
26 cpu-offset = <0x4000>; 26 cpu-offset = <0x4000>;
27 }; 27 };
28
29 mct@10050000 {
30 compatible = "samsung,exynos4412-mct";
31 reg = <0x10050000 0x800>;
32 interrupt-controller;
33 #interrups-cells = <2>;
34 interrupt-parent = <&mct_map>;
35 interrupts = <0 0>, <1 0>, <2 0>, <3 0>,
36 <4 0>, <5 0>, <6 0>, <7 0>;
37
38 mct_map: mct-map {
39 #interrupt-cells = <2>;
40 #address-cells = <0>;
41 #size-cells = <0>;
42 interrupt-map = <0x0 0 &gic 0 57 0>,
43 <0x1 0 &combiner 12 5>,
44 <0x2 0 &combiner 12 6>,
45 <0x3 0 &combiner 12 7>,
46 <0x4 0 &gic 1 12 0>,
47 <0x5 0 &gic 1 12 0>,
48 <0x6 0 &gic 1 12 0>,
49 <0x7 0 &gic 1 12 0>;
50 };
51 };
28}; 52};
diff --git a/arch/arm/boot/dts/exynos5250.dtsi b/arch/arm/boot/dts/exynos5250.dtsi
index b1ac73e21c80..c60108e0d27e 100644
--- a/arch/arm/boot/dts/exynos5250.dtsi
+++ b/arch/arm/boot/dts/exynos5250.dtsi
@@ -69,6 +69,28 @@
69 <0 28 0>, <0 29 0>, <0 30 0>, <0 31 0>; 69 <0 28 0>, <0 29 0>, <0 30 0>, <0 31 0>;
70 }; 70 };
71 71
72 mct@101C0000 {
73 compatible = "samsung,exynos4210-mct";
74 reg = <0x101C0000 0x800>;
75 interrupt-controller;
76 #interrups-cells = <2>;
77 interrupt-parent = <&mct_map>;
78 interrupts = <0 0>, <1 0>, <2 0>, <3 0>,
79 <4 0>, <5 0>;
80
81 mct_map: mct-map {
82 #interrupt-cells = <2>;
83 #address-cells = <0>;
84 #size-cells = <0>;
85 interrupt-map = <0x0 0 &combiner 23 3>,
86 <0x1 0 &combiner 23 4>,
87 <0x2 0 &combiner 25 2>,
88 <0x3 0 &combiner 25 3>,
89 <0x4 0 &gic 0 120 0>,
90 <0x5 0 &gic 0 121 0>;
91 };
92 };
93
72 watchdog { 94 watchdog {
73 compatible = "samsung,s3c2410-wdt"; 95 compatible = "samsung,s3c2410-wdt";
74 reg = <0x101D0000 0x100>; 96 reg = <0x101D0000 0x100>;
diff --git a/arch/arm/boot/dts/integratorcp.dts b/arch/arm/boot/dts/integratorcp.dts
index 8b119399025a..ff1aea0ee043 100644
--- a/arch/arm/boot/dts/integratorcp.dts
+++ b/arch/arm/boot/dts/integratorcp.dts
@@ -24,15 +24,15 @@
24 }; 24 };
25 25
26 timer0: timer@13000000 { 26 timer0: timer@13000000 {
27 compatible = "arm,sp804", "arm,primecell"; 27 compatible = "arm,integrator-cp-timer";
28 }; 28 };
29 29
30 timer1: timer@13000100 { 30 timer1: timer@13000100 {
31 compatible = "arm,sp804", "arm,primecell"; 31 compatible = "arm,integrator-cp-timer";
32 }; 32 };
33 33
34 timer2: timer@13000200 { 34 timer2: timer@13000200 {
35 compatible = "arm,sp804", "arm,primecell"; 35 compatible = "arm,integrator-cp-timer";
36 }; 36 };
37 37
38 pic: pic@14000000 { 38 pic: pic@14000000 {
diff --git a/arch/arm/boot/dts/omap3-beagle.dts b/arch/arm/boot/dts/omap3-beagle.dts
index f624dc85d441..02d23f15fd86 100644
--- a/arch/arm/boot/dts/omap3-beagle.dts
+++ b/arch/arm/boot/dts/omap3-beagle.dts
@@ -38,6 +38,57 @@
38 }; 38 };
39 }; 39 };
40 40
41 /* HS USB Port 2 RESET */
42 hsusb2_reset: hsusb2_reset_reg {
43 compatible = "regulator-fixed";
44 regulator-name = "hsusb2_reset";
45 regulator-min-microvolt = <3300000>;
46 regulator-max-microvolt = <3300000>;
47 gpio = <&gpio5 19 0>; /* gpio_147 */
48 startup-delay-us = <70000>;
49 enable-active-high;
50 };
51
52 /* HS USB Port 2 Power */
53 hsusb2_power: hsusb2_power_reg {
54 compatible = "regulator-fixed";
55 regulator-name = "hsusb2_vbus";
56 regulator-min-microvolt = <3300000>;
57 regulator-max-microvolt = <3300000>;
58 gpio = <&twl_gpio 18 0>; /* GPIO LEDA */
59 startup-delay-us = <70000>;
60 };
61
62 /* HS USB Host PHY on PORT 2 */
63 hsusb2_phy: hsusb2_phy {
64 compatible = "usb-nop-xceiv";
65 reset-supply = <&hsusb2_reset>;
66 vcc-supply = <&hsusb2_power>;
67 };
68};
69
70&omap3_pmx_core {
71 pinctrl-names = "default";
72 pinctrl-0 = <
73 &hsusbb2_pins
74 >;
75
76 hsusbb2_pins: pinmux_hsusbb2_pins {
77 pinctrl-single,pins = <
78 0x5c0 0x3 /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_clk OUTPUT */
79 0x5c2 0x3 /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_stp OUTPUT */
80 0x5c4 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dir INPUT | PULLDOWN */
81 0x5c6 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_nxt INPUT | PULLDOWN */
82 0x5c8 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat0 INPUT | PULLDOWN */
83 0x5cA 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat1 INPUT | PULLDOWN */
84 0x1a4 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat2 INPUT | PULLDOWN */
85 0x1a6 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat3 INPUT | PULLDOWN */
86 0x1a8 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat4 INPUT | PULLDOWN */
87 0x1aa 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat5 INPUT | PULLDOWN */
88 0x1ac 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat6 INPUT | PULLDOWN */
89 0x1ae 0x10b /* USBB2_ULPITLL_CLK_MUXMODE.usbb1_ulpiphy_dat7 INPUT | PULLDOWN */
90 >;
91 };
41}; 92};
42 93
43&i2c1 { 94&i2c1 {
@@ -65,3 +116,23 @@
65&mmc3 { 116&mmc3 {
66 status = "disabled"; 117 status = "disabled";
67}; 118};
119
120&usbhshost {
121 port2-mode = "ehci-phy";
122};
123
124&usbhsehci {
125 phys = <0 &hsusb2_phy>;
126};
127
128&twl_gpio {
129 ti,use-leds;
130 /* pullups: BIT(1) */
131 ti,pullups = <0x000002>;
132 /*
133 * pulldowns:
134 * BIT(2), BIT(6), BIT(7), BIT(8), BIT(13)
135 * BIT(15), BIT(16), BIT(17)
136 */
137 ti,pulldowns = <0x03a1c4>;
138};
diff --git a/arch/arm/boot/dts/omap3.dtsi b/arch/arm/boot/dts/omap3.dtsi
index 1acc26148ffc..a14f74bbce7c 100644
--- a/arch/arm/boot/dts/omap3.dtsi
+++ b/arch/arm/boot/dts/omap3.dtsi
@@ -397,5 +397,36 @@
397 ti,timer-alwon; 397 ti,timer-alwon;
398 ti,timer-secure; 398 ti,timer-secure;
399 }; 399 };
400
401 usbhstll: usbhstll@48062000 {
402 compatible = "ti,usbhs-tll";
403 reg = <0x48062000 0x1000>;
404 interrupts = <78>;
405 ti,hwmods = "usb_tll_hs";
406 };
407
408 usbhshost: usbhshost@48064000 {
409 compatible = "ti,usbhs-host";
410 reg = <0x48064000 0x400>;
411 ti,hwmods = "usb_host_hs";
412 #address-cells = <1>;
413 #size-cells = <1>;
414 ranges;
415
416 usbhsohci: ohci@48064400 {
417 compatible = "ti,ohci-omap3", "usb-ohci";
418 reg = <0x48064400 0x400>;
419 interrupt-parent = <&intc>;
420 interrupts = <76>;
421 };
422
423 usbhsehci: ehci@48064800 {
424 compatible = "ti,ehci-omap", "usb-ehci";
425 reg = <0x48064800 0x400>;
426 interrupt-parent = <&intc>;
427 interrupts = <77>;
428 };
429 };
430
400 }; 431 };
401}; 432};
diff --git a/arch/arm/boot/dts/omap4.dtsi b/arch/arm/boot/dts/omap4.dtsi
index 739bb79e410e..b7db1a2b6ca7 100644
--- a/arch/arm/boot/dts/omap4.dtsi
+++ b/arch/arm/boot/dts/omap4.dtsi
@@ -529,5 +529,35 @@
529 ti,hwmods = "timer11"; 529 ti,hwmods = "timer11";
530 ti,timer-pwm; 530 ti,timer-pwm;
531 }; 531 };
532
533 usbhstll: usbhstll@4a062000 {
534 compatible = "ti,usbhs-tll";
535 reg = <0x4a062000 0x1000>;
536 interrupts = <0 78 0x4>;
537 ti,hwmods = "usb_tll_hs";
538 };
539
540 usbhshost: usbhshost@4a064000 {
541 compatible = "ti,usbhs-host";
542 reg = <0x4a064000 0x800>;
543 ti,hwmods = "usb_host_hs";
544 #address-cells = <1>;
545 #size-cells = <1>;
546 ranges;
547
548 usbhsohci: ohci@4a064800 {
549 compatible = "ti,ohci-omap3", "usb-ohci";
550 reg = <0x4a064800 0x400>;
551 interrupt-parent = <&gic>;
552 interrupts = <0 76 0x4>;
553 };
554
555 usbhsehci: ehci@4a064c00 {
556 compatible = "ti,ehci-omap", "usb-ehci";
557 reg = <0x4a064c00 0x400>;
558 interrupt-parent = <&gic>;
559 interrupts = <0 77 0x4>;
560 };
561 };
532 }; 562 };
533}; 563};
diff --git a/arch/arm/boot/dts/r8a7779.dtsi b/arch/arm/boot/dts/r8a7779.dtsi
new file mode 100644
index 000000000000..fe5c6f213271
--- /dev/null
+++ b/arch/arm/boot/dts/r8a7779.dtsi
@@ -0,0 +1,98 @@
1/*
2 * Device Tree Source for Renesas r8a7779
3 *
4 * Copyright (C) 2013 Renesas Solutions Corp.
5 * Copyright (C) 2013 Simon Horman
6 *
7 * This file is licensed under the terms of the GNU General Public License
8 * version 2. This program is licensed "as is" without any warranty of any
9 * kind, whether express or implied.
10 */
11
12/include/ "skeleton.dtsi"
13
14/ {
15 compatible = "renesas,r8a7779";
16
17 cpus {
18 #address-cells = <1>;
19 #size-cells = <0>;
20
21 cpu@0 {
22 device_type = "cpu";
23 compatible = "arm,cortex-a9";
24 reg = <0>;
25 };
26 cpu@1 {
27 device_type = "cpu";
28 compatible = "arm,cortex-a9";
29 reg = <1>;
30 };
31 cpu@2 {
32 device_type = "cpu";
33 compatible = "arm,cortex-a9";
34 reg = <2>;
35 };
36 cpu@3 {
37 device_type = "cpu";
38 compatible = "arm,cortex-a9";
39 reg = <3>;
40 };
41 };
42
43 gic: interrupt-controller@f0001000 {
44 compatible = "arm,cortex-a9-gic";
45 #interrupt-cells = <3>;
46 interrupt-controller;
47 reg = <0xf0001000 0x1000>,
48 <0xf0000100 0x100>;
49 };
50
51 i2c0: i2c@0xffc70000 {
52 #address-cells = <1>;
53 #size-cells = <0>;
54 compatible = "renesas,rmobile-iic";
55 reg = <0xffc70000 0x1000>;
56 interrupt-parent = <&gic>;
57 interrupts = <0 79 0x4>;
58 };
59
60 i2c1: i2c@0xffc71000 {
61 #address-cells = <1>;
62 #size-cells = <0>;
63 compatible = "renesas,rmobile-iic";
64 reg = <0xffc71000 0x1000>;
65 interrupt-parent = <&gic>;
66 interrupts = <0 82 0x4>;
67 };
68
69 i2c2: i2c@0xffc72000 {
70 #address-cells = <1>;
71 #size-cells = <0>;
72 compatible = "renesas,rmobile-iic";
73 reg = <0xffc72000 0x1000>;
74 interrupt-parent = <&gic>;
75 interrupts = <0 80 0x4>;
76 };
77
78 i2c3: i2c@0xffc73000 {
79 #address-cells = <1>;
80 #size-cells = <0>;
81 compatible = "renesas,rmobile-iic";
82 reg = <0xffc73000 0x1000>;
83 interrupt-parent = <&gic>;
84 interrupts = <0 81 0x4>;
85 };
86
87 thermal@ffc48000 {
88 compatible = "renesas,rcar-thermal";
89 reg = <0xffc48000 0x38>;
90 };
91
92 sata: sata@fc600000 {
93 compatible = "renesas,rcar-sata";
94 reg = <0xfc600000 0x2000>;
95 interrupt-parent = <&gic>;
96 interrupts = <0 100 0x4>;
97 };
98};
diff --git a/arch/arm/boot/dts/tegra114-dalmore.dts b/arch/arm/boot/dts/tegra114-dalmore.dts
index a30aca62658a..616990dc92db 100644
--- a/arch/arm/boot/dts/tegra114-dalmore.dts
+++ b/arch/arm/boot/dts/tegra114-dalmore.dts
@@ -12,10 +12,22 @@
12 12
13 serial@70006300 { 13 serial@70006300 {
14 status = "okay"; 14 status = "okay";
15 clock-frequency = <408000000>;
16 }; 15 };
17 16
18 pmc { 17 pmc {
19 nvidia,invert-interrupt; 18 nvidia,invert-interrupt;
20 }; 19 };
20
21 clocks {
22 compatible = "simple-bus";
23 #address-cells = <1>;
24 #size-cells = <0>;
25
26 clk32k_in: clock {
27 compatible = "fixed-clock";
28 reg=<0>;
29 #clock-cells = <0>;
30 clock-frequency = <32768>;
31 };
32 };
21}; 33};
diff --git a/arch/arm/boot/dts/tegra114-pluto.dts b/arch/arm/boot/dts/tegra114-pluto.dts
index 9bea8f57aa47..6bbc8efae9c0 100644
--- a/arch/arm/boot/dts/tegra114-pluto.dts
+++ b/arch/arm/boot/dts/tegra114-pluto.dts
@@ -12,10 +12,22 @@
12 12
13 serial@70006300 { 13 serial@70006300 {
14 status = "okay"; 14 status = "okay";
15 clock-frequency = <408000000>;
16 }; 15 };
17 16
18 pmc { 17 pmc {
19 nvidia,invert-interrupt; 18 nvidia,invert-interrupt;
20 }; 19 };
20
21 clocks {
22 compatible = "simple-bus";
23 #address-cells = <1>;
24 #size-cells = <0>;
25
26 clk32k_in: clock {
27 compatible = "fixed-clock";
28 reg=<0>;
29 #clock-cells = <0>;
30 clock-frequency = <32768>;
31 };
32 };
21}; 33};
diff --git a/arch/arm/boot/dts/tegra114.dtsi b/arch/arm/boot/dts/tegra114.dtsi
index 1dfaf2874c57..c1110a9b2a91 100644
--- a/arch/arm/boot/dts/tegra114.dtsi
+++ b/arch/arm/boot/dts/tegra114.dtsi
@@ -24,10 +24,11 @@
24 0 42 0x04 24 0 42 0x04
25 0 121 0x04 25 0 121 0x04
26 0 122 0x04>; 26 0 122 0x04>;
27 clocks = <&tegra_car 5>;
27 }; 28 };
28 29
29 tegra_car: clock { 30 tegra_car: clock {
30 compatible = "nvidia,tegra114-car, nvidia,tegra30-car"; 31 compatible = "nvidia,tegra114-car";
31 reg = <0x60006000 0x1000>; 32 reg = <0x60006000 0x1000>;
32 #clock-cells = <1>; 33 #clock-cells = <1>;
33 }; 34 };
@@ -66,6 +67,7 @@
66 reg-shift = <2>; 67 reg-shift = <2>;
67 interrupts = <0 36 0x04>; 68 interrupts = <0 36 0x04>;
68 status = "disabled"; 69 status = "disabled";
70 clocks = <&tegra_car 6>;
69 }; 71 };
70 72
71 serial@70006040 { 73 serial@70006040 {
@@ -74,6 +76,7 @@
74 reg-shift = <2>; 76 reg-shift = <2>;
75 interrupts = <0 37 0x04>; 77 interrupts = <0 37 0x04>;
76 status = "disabled"; 78 status = "disabled";
79 clocks = <&tegra_car 192>;
77 }; 80 };
78 81
79 serial@70006200 { 82 serial@70006200 {
@@ -82,6 +85,7 @@
82 reg-shift = <2>; 85 reg-shift = <2>;
83 interrupts = <0 46 0x04>; 86 interrupts = <0 46 0x04>;
84 status = "disabled"; 87 status = "disabled";
88 clocks = <&tegra_car 55>;
85 }; 89 };
86 90
87 serial@70006300 { 91 serial@70006300 {
@@ -90,17 +94,21 @@
90 reg-shift = <2>; 94 reg-shift = <2>;
91 interrupts = <0 90 0x04>; 95 interrupts = <0 90 0x04>;
92 status = "disabled"; 96 status = "disabled";
97 clocks = <&tegra_car 65>;
93 }; 98 };
94 99
95 rtc { 100 rtc {
96 compatible = "nvidia,tegra114-rtc", "nvidia,tegra20-rtc"; 101 compatible = "nvidia,tegra114-rtc", "nvidia,tegra20-rtc";
97 reg = <0x7000e000 0x100>; 102 reg = <0x7000e000 0x100>;
98 interrupts = <0 2 0x04>; 103 interrupts = <0 2 0x04>;
104 clocks = <&tegra_car 4>;
99 }; 105 };
100 106
101 pmc { 107 pmc {
102 compatible = "nvidia,tegra114-pmc", "nvidia,tegra30-pmc"; 108 compatible = "nvidia,tegra114-pmc";
103 reg = <0x7000e400 0x400>; 109 reg = <0x7000e400 0x400>;
110 clocks = <&tegra_car 261>, <&clk32k_in>;
111 clock-names = "pclk", "clk32k_in";
104 }; 112 };
105 113
106 iommu { 114 iommu {
diff --git a/arch/arm/boot/dts/tegra20-colibri-512.dtsi b/arch/arm/boot/dts/tegra20-colibri-512.dtsi
index 444162090042..4e3afdef28a8 100644
--- a/arch/arm/boot/dts/tegra20-colibri-512.dtsi
+++ b/arch/arm/boot/dts/tegra20-colibri-512.dtsi
@@ -444,7 +444,20 @@
444 }; 444 };
445 445
446 sdhci@c8000600 { 446 sdhci@c8000600 {
447 cd-gpios = <&gpio 23 0>; /* gpio PC7 */ 447 cd-gpios = <&gpio 23 1>; /* gpio PC7 */
448 };
449
450 clocks {
451 compatible = "simple-bus";
452 #address-cells = <1>;
453 #size-cells = <0>;
454
455 clk32k_in: clock {
456 compatible = "fixed-clock";
457 reg=<0>;
458 #clock-cells = <0>;
459 clock-frequency = <32768>;
460 };
448 }; 461 };
449 462
450 sound { 463 sound {
diff --git a/arch/arm/boot/dts/tegra20-harmony.dts b/arch/arm/boot/dts/tegra20-harmony.dts
index 61d027f03617..ae9d5a20834e 100644
--- a/arch/arm/boot/dts/tegra20-harmony.dts
+++ b/arch/arm/boot/dts/tegra20-harmony.dts
@@ -437,7 +437,7 @@
437 437
438 sdhci@c8000200 { 438 sdhci@c8000200 {
439 status = "okay"; 439 status = "okay";
440 cd-gpios = <&gpio 69 0>; /* gpio PI5 */ 440 cd-gpios = <&gpio 69 1>; /* gpio PI5 */
441 wp-gpios = <&gpio 57 0>; /* gpio PH1 */ 441 wp-gpios = <&gpio 57 0>; /* gpio PH1 */
442 power-gpios = <&gpio 155 0>; /* gpio PT3 */ 442 power-gpios = <&gpio 155 0>; /* gpio PT3 */
443 bus-width = <4>; 443 bus-width = <4>;
@@ -445,12 +445,25 @@
445 445
446 sdhci@c8000600 { 446 sdhci@c8000600 {
447 status = "okay"; 447 status = "okay";
448 cd-gpios = <&gpio 58 0>; /* gpio PH2 */ 448 cd-gpios = <&gpio 58 1>; /* gpio PH2 */
449 wp-gpios = <&gpio 59 0>; /* gpio PH3 */ 449 wp-gpios = <&gpio 59 0>; /* gpio PH3 */
450 power-gpios = <&gpio 70 0>; /* gpio PI6 */ 450 power-gpios = <&gpio 70 0>; /* gpio PI6 */
451 bus-width = <8>; 451 bus-width = <8>;
452 }; 452 };
453 453
454 clocks {
455 compatible = "simple-bus";
456 #address-cells = <1>;
457 #size-cells = <0>;
458
459 clk32k_in: clock {
460 compatible = "fixed-clock";
461 reg=<0>;
462 #clock-cells = <0>;
463 clock-frequency = <32768>;
464 };
465 };
466
454 kbc { 467 kbc {
455 status = "okay"; 468 status = "okay";
456 nvidia,debounce-delay-ms = <2>; 469 nvidia,debounce-delay-ms = <2>;
diff --git a/arch/arm/boot/dts/tegra20-paz00.dts b/arch/arm/boot/dts/tegra20-paz00.dts
index 54d6fce00a59..fd60940e4063 100644
--- a/arch/arm/boot/dts/tegra20-paz00.dts
+++ b/arch/arm/boot/dts/tegra20-paz00.dts
@@ -436,7 +436,7 @@
436 436
437 sdhci@c8000000 { 437 sdhci@c8000000 {
438 status = "okay"; 438 status = "okay";
439 cd-gpios = <&gpio 173 0>; /* gpio PV5 */ 439 cd-gpios = <&gpio 173 1>; /* gpio PV5 */
440 wp-gpios = <&gpio 57 0>; /* gpio PH1 */ 440 wp-gpios = <&gpio 57 0>; /* gpio PH1 */
441 power-gpios = <&gpio 169 0>; /* gpio PV1 */ 441 power-gpios = <&gpio 169 0>; /* gpio PV1 */
442 bus-width = <4>; 442 bus-width = <4>;
@@ -447,6 +447,19 @@
447 bus-width = <8>; 447 bus-width = <8>;
448 }; 448 };
449 449
450 clocks {
451 compatible = "simple-bus";
452 #address-cells = <1>;
453 #size-cells = <0>;
454
455 clk32k_in: clock {
456 compatible = "fixed-clock";
457 reg=<0>;
458 #clock-cells = <0>;
459 clock-frequency = <32768>;
460 };
461 };
462
450 gpio-keys { 463 gpio-keys {
451 compatible = "gpio-keys"; 464 compatible = "gpio-keys";
452 465
diff --git a/arch/arm/boot/dts/tegra20-seaboard.dts b/arch/arm/boot/dts/tegra20-seaboard.dts
index 37b3a57ec0f1..4ee700a33ca5 100644
--- a/arch/arm/boot/dts/tegra20-seaboard.dts
+++ b/arch/arm/boot/dts/tegra20-seaboard.dts
@@ -584,7 +584,7 @@
584 584
585 sdhci@c8000400 { 585 sdhci@c8000400 {
586 status = "okay"; 586 status = "okay";
587 cd-gpios = <&gpio 69 0>; /* gpio PI5 */ 587 cd-gpios = <&gpio 69 1>; /* gpio PI5 */
588 wp-gpios = <&gpio 57 0>; /* gpio PH1 */ 588 wp-gpios = <&gpio 57 0>; /* gpio PH1 */
589 power-gpios = <&gpio 70 0>; /* gpio PI6 */ 589 power-gpios = <&gpio 70 0>; /* gpio PI6 */
590 bus-width = <4>; 590 bus-width = <4>;
@@ -595,6 +595,19 @@
595 bus-width = <8>; 595 bus-width = <8>;
596 }; 596 };
597 597
598 clocks {
599 compatible = "simple-bus";
600 #address-cells = <1>;
601 #size-cells = <0>;
602
603 clk32k_in: clock {
604 compatible = "fixed-clock";
605 reg=<0>;
606 #clock-cells = <0>;
607 clock-frequency = <32768>;
608 };
609 };
610
598 gpio-keys { 611 gpio-keys {
599 compatible = "gpio-keys"; 612 compatible = "gpio-keys";
600 613
diff --git a/arch/arm/boot/dts/tegra20-tamonten.dtsi b/arch/arm/boot/dts/tegra20-tamonten.dtsi
index 4766abae7a72..c19025725918 100644
--- a/arch/arm/boot/dts/tegra20-tamonten.dtsi
+++ b/arch/arm/boot/dts/tegra20-tamonten.dtsi
@@ -465,12 +465,25 @@
465 }; 465 };
466 466
467 sdhci@c8000600 { 467 sdhci@c8000600 {
468 cd-gpios = <&gpio 58 0>; /* gpio PH2 */ 468 cd-gpios = <&gpio 58 1>; /* gpio PH2 */
469 wp-gpios = <&gpio 59 0>; /* gpio PH3 */ 469 wp-gpios = <&gpio 59 0>; /* gpio PH3 */
470 bus-width = <4>; 470 bus-width = <4>;
471 status = "okay"; 471 status = "okay";
472 }; 472 };
473 473
474 clocks {
475 compatible = "simple-bus";
476 #address-cells = <1>;
477 #size-cells = <0>;
478
479 clk32k_in: clock {
480 compatible = "fixed-clock";
481 reg=<0>;
482 #clock-cells = <0>;
483 clock-frequency = <32768>;
484 };
485 };
486
474 regulators { 487 regulators {
475 compatible = "simple-bus"; 488 compatible = "simple-bus";
476 489
diff --git a/arch/arm/boot/dts/tegra20-trimslice.dts b/arch/arm/boot/dts/tegra20-trimslice.dts
index 5d79e4fc49a6..a9f3f06580f5 100644
--- a/arch/arm/boot/dts/tegra20-trimslice.dts
+++ b/arch/arm/boot/dts/tegra20-trimslice.dts
@@ -325,11 +325,24 @@
325 325
326 sdhci@c8000600 { 326 sdhci@c8000600 {
327 status = "okay"; 327 status = "okay";
328 cd-gpios = <&gpio 121 0>; /* gpio PP1 */ 328 cd-gpios = <&gpio 121 1>; /* gpio PP1 */
329 wp-gpios = <&gpio 122 0>; /* gpio PP2 */ 329 wp-gpios = <&gpio 122 0>; /* gpio PP2 */
330 bus-width = <4>; 330 bus-width = <4>;
331 }; 331 };
332 332
333 clocks {
334 compatible = "simple-bus";
335 #address-cells = <1>;
336 #size-cells = <0>;
337
338 clk32k_in: clock {
339 compatible = "fixed-clock";
340 reg=<0>;
341 #clock-cells = <0>;
342 clock-frequency = <32768>;
343 };
344 };
345
333 poweroff { 346 poweroff {
334 compatible = "gpio-poweroff"; 347 compatible = "gpio-poweroff";
335 gpios = <&gpio 191 1>; /* gpio PX7, active low */ 348 gpios = <&gpio 191 1>; /* gpio PX7, active low */
diff --git a/arch/arm/boot/dts/tegra20-ventana.dts b/arch/arm/boot/dts/tegra20-ventana.dts
index 425c89000c20..f544806e9618 100644
--- a/arch/arm/boot/dts/tegra20-ventana.dts
+++ b/arch/arm/boot/dts/tegra20-ventana.dts
@@ -520,7 +520,7 @@
520 520
521 sdhci@c8000400 { 521 sdhci@c8000400 {
522 status = "okay"; 522 status = "okay";
523 cd-gpios = <&gpio 69 0>; /* gpio PI5 */ 523 cd-gpios = <&gpio 69 1>; /* gpio PI5 */
524 wp-gpios = <&gpio 57 0>; /* gpio PH1 */ 524 wp-gpios = <&gpio 57 0>; /* gpio PH1 */
525 power-gpios = <&gpio 70 0>; /* gpio PI6 */ 525 power-gpios = <&gpio 70 0>; /* gpio PI6 */
526 bus-width = <4>; 526 bus-width = <4>;
@@ -531,6 +531,19 @@
531 bus-width = <8>; 531 bus-width = <8>;
532 }; 532 };
533 533
534 clocks {
535 compatible = "simple-bus";
536 #address-cells = <1>;
537 #size-cells = <0>;
538
539 clk32k_in: clock {
540 compatible = "fixed-clock";
541 reg=<0>;
542 #clock-cells = <0>;
543 clock-frequency = <32768>;
544 };
545 };
546
534 regulators { 547 regulators {
535 compatible = "simple-bus"; 548 compatible = "simple-bus";
536 #address-cells = <1>; 549 #address-cells = <1>;
diff --git a/arch/arm/boot/dts/tegra20-whistler.dts b/arch/arm/boot/dts/tegra20-whistler.dts
index ea57c0f6dcce..258cf945f515 100644
--- a/arch/arm/boot/dts/tegra20-whistler.dts
+++ b/arch/arm/boot/dts/tegra20-whistler.dts
@@ -510,6 +510,7 @@
510 510
511 sdhci@c8000400 { 511 sdhci@c8000400 {
512 status = "okay"; 512 status = "okay";
513 cd-gpios = <&gpio 69 1>; /* gpio PI5 */
513 wp-gpios = <&gpio 173 0>; /* gpio PV5 */ 514 wp-gpios = <&gpio 173 0>; /* gpio PV5 */
514 bus-width = <8>; 515 bus-width = <8>;
515 }; 516 };
@@ -519,6 +520,19 @@
519 bus-width = <8>; 520 bus-width = <8>;
520 }; 521 };
521 522
523 clocks {
524 compatible = "simple-bus";
525 #address-cells = <1>;
526 #size-cells = <0>;
527
528 clk32k_in: clock {
529 compatible = "fixed-clock";
530 reg=<0>;
531 #clock-cells = <0>;
532 clock-frequency = <32768>;
533 };
534 };
535
522 kbc { 536 kbc {
523 status = "okay"; 537 status = "okay";
524 nvidia,debounce-delay-ms = <20>; 538 nvidia,debounce-delay-ms = <20>;
diff --git a/arch/arm/boot/dts/tegra20.dtsi b/arch/arm/boot/dts/tegra20.dtsi
index 3d3f64d2111a..fc7febc2b386 100644
--- a/arch/arm/boot/dts/tegra20.dtsi
+++ b/arch/arm/boot/dts/tegra20.dtsi
@@ -145,6 +145,7 @@
145 0 1 0x04 145 0 1 0x04
146 0 41 0x04 146 0 41 0x04
147 0 42 0x04>; 147 0 42 0x04>;
148 clocks = <&tegra_car 5>;
148 }; 149 };
149 150
150 tegra_car: clock { 151 tegra_car: clock {
@@ -304,6 +305,7 @@
304 compatible = "nvidia,tegra20-rtc"; 305 compatible = "nvidia,tegra20-rtc";
305 reg = <0x7000e000 0x100>; 306 reg = <0x7000e000 0x100>;
306 interrupts = <0 2 0x04>; 307 interrupts = <0 2 0x04>;
308 clocks = <&tegra_car 4>;
307 }; 309 };
308 310
309 i2c@7000c000 { 311 i2c@7000c000 {
@@ -416,6 +418,8 @@
416 pmc { 418 pmc {
417 compatible = "nvidia,tegra20-pmc"; 419 compatible = "nvidia,tegra20-pmc";
418 reg = <0x7000e400 0x400>; 420 reg = <0x7000e400 0x400>;
421 clocks = <&tegra_car 110>, <&clk32k_in>;
422 clock-names = "pclk", "clk32k_in";
419 }; 423 };
420 424
421 memory-controller@7000f000 { 425 memory-controller@7000f000 {
diff --git a/arch/arm/boot/dts/tegra30-beaver.dts b/arch/arm/boot/dts/tegra30-beaver.dts
index 8ff2ff20e4a3..6248b2445b32 100644
--- a/arch/arm/boot/dts/tegra30-beaver.dts
+++ b/arch/arm/boot/dts/tegra30-beaver.dts
@@ -257,7 +257,7 @@
257 257
258 sdhci@78000000 { 258 sdhci@78000000 {
259 status = "okay"; 259 status = "okay";
260 cd-gpios = <&gpio 69 0>; /* gpio PI5 */ 260 cd-gpios = <&gpio 69 1>; /* gpio PI5 */
261 wp-gpios = <&gpio 155 0>; /* gpio PT3 */ 261 wp-gpios = <&gpio 155 0>; /* gpio PT3 */
262 power-gpios = <&gpio 31 0>; /* gpio PD7 */ 262 power-gpios = <&gpio 31 0>; /* gpio PD7 */
263 bus-width = <4>; 263 bus-width = <4>;
@@ -268,6 +268,19 @@
268 bus-width = <8>; 268 bus-width = <8>;
269 }; 269 };
270 270
271 clocks {
272 compatible = "simple-bus";
273 #address-cells = <1>;
274 #size-cells = <0>;
275
276 clk32k_in: clock {
277 compatible = "fixed-clock";
278 reg=<0>;
279 #clock-cells = <0>;
280 clock-frequency = <32768>;
281 };
282 };
283
271 regulators { 284 regulators {
272 compatible = "simple-bus"; 285 compatible = "simple-bus";
273 #address-cells = <1>; 286 #address-cells = <1>;
diff --git a/arch/arm/boot/dts/tegra30-cardhu.dtsi b/arch/arm/boot/dts/tegra30-cardhu.dtsi
index 17499272a4ef..65bf2b63174e 100644
--- a/arch/arm/boot/dts/tegra30-cardhu.dtsi
+++ b/arch/arm/boot/dts/tegra30-cardhu.dtsi
@@ -311,7 +311,7 @@
311 311
312 sdhci@78000000 { 312 sdhci@78000000 {
313 status = "okay"; 313 status = "okay";
314 cd-gpios = <&gpio 69 0>; /* gpio PI5 */ 314 cd-gpios = <&gpio 69 1>; /* gpio PI5 */
315 wp-gpios = <&gpio 155 0>; /* gpio PT3 */ 315 wp-gpios = <&gpio 155 0>; /* gpio PT3 */
316 power-gpios = <&gpio 31 0>; /* gpio PD7 */ 316 power-gpios = <&gpio 31 0>; /* gpio PD7 */
317 bus-width = <4>; 317 bus-width = <4>;
@@ -322,6 +322,19 @@
322 bus-width = <8>; 322 bus-width = <8>;
323 }; 323 };
324 324
325 clocks {
326 compatible = "simple-bus";
327 #address-cells = <1>;
328 #size-cells = <0>;
329
330 clk32k_in: clock {
331 compatible = "fixed-clock";
332 reg=<0>;
333 #clock-cells = <0>;
334 clock-frequency = <32768>;
335 };
336 };
337
325 regulators { 338 regulators {
326 compatible = "simple-bus"; 339 compatible = "simple-bus";
327 #address-cells = <1>; 340 #address-cells = <1>;
diff --git a/arch/arm/boot/dts/tegra30.dtsi b/arch/arm/boot/dts/tegra30.dtsi
index dbf46c272562..9fe7a92b4c85 100644
--- a/arch/arm/boot/dts/tegra30.dtsi
+++ b/arch/arm/boot/dts/tegra30.dtsi
@@ -148,6 +148,7 @@
148 0 42 0x04 148 0 42 0x04
149 0 121 0x04 149 0 121 0x04
150 0 122 0x04>; 150 0 122 0x04>;
151 clocks = <&tegra_car 5>;
151 }; 152 };
152 153
153 tegra_car: clock { 154 tegra_car: clock {
@@ -291,6 +292,7 @@
291 compatible = "nvidia,tegra30-rtc", "nvidia,tegra20-rtc"; 292 compatible = "nvidia,tegra30-rtc", "nvidia,tegra20-rtc";
292 reg = <0x7000e000 0x100>; 293 reg = <0x7000e000 0x100>;
293 interrupts = <0 2 0x04>; 294 interrupts = <0 2 0x04>;
295 clocks = <&tegra_car 4>;
294 }; 296 };
295 297
296 i2c@7000c000 { 298 i2c@7000c000 {
@@ -423,8 +425,10 @@
423 }; 425 };
424 426
425 pmc { 427 pmc {
426 compatible = "nvidia,tegra20-pmc", "nvidia,tegra30-pmc"; 428 compatible = "nvidia,tegra30-pmc";
427 reg = <0x7000e400 0x400>; 429 reg = <0x7000e400 0x400>;
430 clocks = <&tegra_car 218>, <&clk32k_in>;
431 clock-names = "pclk", "clk32k_in";
428 }; 432 };
429 433
430 memory-controller { 434 memory-controller {
diff --git a/arch/arm/boot/dts/versatile-ab.dts b/arch/arm/boot/dts/versatile-ab.dts
index e2fe3195c0d1..dde75ae8b4b1 100644
--- a/arch/arm/boot/dts/versatile-ab.dts
+++ b/arch/arm/boot/dts/versatile-ab.dts
@@ -121,6 +121,18 @@
121 interrupts = <0>; 121 interrupts = <0>;
122 }; 122 };
123 123
124 timer@101e2000 {
125 compatible = "arm,sp804", "arm,primecell";
126 reg = <0x101e2000 0x1000>;
127 interrupts = <4>;
128 };
129
130 timer@101e3000 {
131 compatible = "arm,sp804", "arm,primecell";
132 reg = <0x101e3000 0x1000>;
133 interrupts = <5>;
134 };
135
124 gpio0: gpio@101e4000 { 136 gpio0: gpio@101e4000 {
125 compatible = "arm,pl061", "arm,primecell"; 137 compatible = "arm,pl061", "arm,primecell";
126 reg = <0x101e4000 0x1000>; 138 reg = <0x101e4000 0x1000>;
diff --git a/arch/arm/boot/dts/vexpress-v2p-ca9.dts b/arch/arm/boot/dts/vexpress-v2p-ca9.dts
index 1420bb14d95c..62d9b225dcce 100644
--- a/arch/arm/boot/dts/vexpress-v2p-ca9.dts
+++ b/arch/arm/boot/dts/vexpress-v2p-ca9.dts
@@ -98,6 +98,7 @@
98 <0 49 4>; 98 <0 49 4>;
99 clocks = <&oscclk2>, <&oscclk2>; 99 clocks = <&oscclk2>, <&oscclk2>;
100 clock-names = "timclk", "apb_pclk"; 100 clock-names = "timclk", "apb_pclk";
101 status = "disabled";
101 }; 102 };
102 103
103 watchdog@100e5000 { 104 watchdog@100e5000 {
diff --git a/arch/arm/boot/dts/vt8500.dtsi b/arch/arm/boot/dts/vt8500.dtsi
index cf31ced46602..e1c3926aca52 100644
--- a/arch/arm/boot/dts/vt8500.dtsi
+++ b/arch/arm/boot/dts/vt8500.dtsi
@@ -25,11 +25,13 @@
25 #interrupt-cells = <1>; 25 #interrupt-cells = <1>;
26 }; 26 };
27 27
28 gpio: gpio-controller@d8110000 { 28 pinctrl: pinctrl@d8110000 {
29 compatible = "via,vt8500-gpio"; 29 compatible = "via,vt8500-pinctrl";
30 gpio-controller;
31 reg = <0xd8110000 0x10000>; 30 reg = <0xd8110000 0x10000>;
32 #gpio-cells = <3>; 31 interrupt-controller;
32 #interrupt-cells = <2>;
33 gpio-controller;
34 #gpio-cells = <2>;
33 }; 35 };
34 36
35 pmc@d8130000 { 37 pmc@d8130000 {
diff --git a/arch/arm/boot/dts/wm8505.dtsi b/arch/arm/boot/dts/wm8505.dtsi
index e74a1c0fb9a2..bb92ef8ce665 100644
--- a/arch/arm/boot/dts/wm8505.dtsi
+++ b/arch/arm/boot/dts/wm8505.dtsi
@@ -40,11 +40,13 @@
40 interrupts = <56 57 58 59 60 61 62 63>; 40 interrupts = <56 57 58 59 60 61 62 63>;
41 }; 41 };
42 42
43 gpio: gpio-controller@d8110000 { 43 pinctrl: pinctrl@d8110000 {
44 compatible = "wm,wm8505-gpio"; 44 compatible = "wm,wm8505-pinctrl";
45 gpio-controller;
46 reg = <0xd8110000 0x10000>; 45 reg = <0xd8110000 0x10000>;
47 #gpio-cells = <3>; 46 interrupt-controller;
47 #interrupt-cells = <2>;
48 gpio-controller;
49 #gpio-cells = <2>;
48 }; 50 };
49 51
50 pmc@d8130000 { 52 pmc@d8130000 {
diff --git a/arch/arm/boot/dts/wm8650.dtsi b/arch/arm/boot/dts/wm8650.dtsi
index db3c0a12e052..bb4af580f40b 100644
--- a/arch/arm/boot/dts/wm8650.dtsi
+++ b/arch/arm/boot/dts/wm8650.dtsi
@@ -34,11 +34,13 @@
34 interrupts = <56 57 58 59 60 61 62 63>; 34 interrupts = <56 57 58 59 60 61 62 63>;
35 }; 35 };
36 36
37 gpio: gpio-controller@d8110000 { 37 pinctrl: pinctrl@d8110000 {
38 compatible = "wm,wm8650-gpio"; 38 compatible = "wm,wm8650-pinctrl";
39 gpio-controller;
40 reg = <0xd8110000 0x10000>; 39 reg = <0xd8110000 0x10000>;
41 #gpio-cells = <3>; 40 interrupt-controller;
41 #interrupt-cells = <2>;
42 gpio-controller;
43 #gpio-cells = <2>;
42 }; 44 };
43 45
44 pmc@d8130000 { 46 pmc@d8130000 {
diff --git a/arch/arm/boot/dts/wm8850.dtsi b/arch/arm/boot/dts/wm8850.dtsi
index e8cbfdc87bba..11cd180c58d3 100644
--- a/arch/arm/boot/dts/wm8850.dtsi
+++ b/arch/arm/boot/dts/wm8850.dtsi
@@ -41,11 +41,13 @@
41 interrupts = <56 57 58 59 60 61 62 63>; 41 interrupts = <56 57 58 59 60 61 62 63>;
42 }; 42 };
43 43
44 gpio: gpio-controller@d8110000 { 44 pinctrl: pinctrl@d8110000 {
45 compatible = "wm,wm8650-gpio"; 45 compatible = "wm,wm8850-pinctrl";
46 gpio-controller;
47 reg = <0xd8110000 0x10000>; 46 reg = <0xd8110000 0x10000>;
48 #gpio-cells = <3>; 47 interrupt-controller;
48 #interrupt-cells = <2>;
49 gpio-controller;
50 #gpio-cells = <2>;
49 }; 51 };
50 52
51 pmc@d8130000 { 53 pmc@d8130000 {
diff --git a/arch/arm/boot/dts/zynq-7000.dtsi b/arch/arm/boot/dts/zynq-7000.dtsi
index 5914b5654591..51243db2e9e4 100644
--- a/arch/arm/boot/dts/zynq-7000.dtsi
+++ b/arch/arm/boot/dts/zynq-7000.dtsi
@@ -111,56 +111,23 @@
111 }; 111 };
112 112
113 ttc0: ttc0@f8001000 { 113 ttc0: ttc0@f8001000 {
114 #address-cells = <1>; 114 interrupt-parent = <&intc>;
115 #size-cells = <0>; 115 interrupts = < 0 10 4 0 11 4 0 12 4 >;
116 compatible = "xlnx,ttc"; 116 compatible = "cdns,ttc";
117 reg = <0xF8001000 0x1000>; 117 reg = <0xF8001000 0x1000>;
118 clocks = <&cpu_clk 3>; 118 clocks = <&cpu_clk 3>;
119 clock-names = "cpu_1x"; 119 clock-names = "cpu_1x";
120 clock-ranges; 120 clock-ranges;
121
122 ttc0_0: ttc0.0 {
123 status = "disabled";
124 reg = <0>;
125 interrupts = <0 10 4>;
126 };
127 ttc0_1: ttc0.1 {
128 status = "disabled";
129 reg = <1>;
130 interrupts = <0 11 4>;
131 };
132 ttc0_2: ttc0.2 {
133 status = "disabled";
134 reg = <2>;
135 interrupts = <0 12 4>;
136 };
137 }; 121 };
138 122
139 ttc1: ttc1@f8002000 { 123 ttc1: ttc1@f8002000 {
140 #interrupt-parent = <&intc>; 124 interrupt-parent = <&intc>;
141 #address-cells = <1>; 125 interrupts = < 0 37 4 0 38 4 0 39 4 >;
142 #size-cells = <0>; 126 compatible = "cdns,ttc";
143 compatible = "xlnx,ttc";
144 reg = <0xF8002000 0x1000>; 127 reg = <0xF8002000 0x1000>;
145 clocks = <&cpu_clk 3>; 128 clocks = <&cpu_clk 3>;
146 clock-names = "cpu_1x"; 129 clock-names = "cpu_1x";
147 clock-ranges; 130 clock-ranges;
148
149 ttc1_0: ttc1.0 {
150 status = "disabled";
151 reg = <0>;
152 interrupts = <0 37 4>;
153 };
154 ttc1_1: ttc1.1 {
155 status = "disabled";
156 reg = <1>;
157 interrupts = <0 38 4>;
158 };
159 ttc1_2: ttc1.2 {
160 status = "disabled";
161 reg = <2>;
162 interrupts = <0 39 4>;
163 };
164 }; 131 };
165 }; 132 };
166}; 133};
diff --git a/arch/arm/boot/dts/zynq-zc702.dts b/arch/arm/boot/dts/zynq-zc702.dts
index c772942a399a..86f44d5b0265 100644
--- a/arch/arm/boot/dts/zynq-zc702.dts
+++ b/arch/arm/boot/dts/zynq-zc702.dts
@@ -32,13 +32,3 @@
32&ps_clk { 32&ps_clk {
33 clock-frequency = <33333330>; 33 clock-frequency = <33333330>;
34}; 34};
35
36&ttc0_0 {
37 status = "ok";
38 compatible = "xlnx,ttc-counter-clocksource";
39};
40
41&ttc0_1 {
42 status = "ok";
43 compatible = "xlnx,ttc-counter-clockevent";
44};
diff --git a/arch/arm/common/timer-sp.c b/arch/arm/common/timer-sp.c
index 9d2d3ba339ff..ddc740769601 100644
--- a/arch/arm/common/timer-sp.c
+++ b/arch/arm/common/timer-sp.c
@@ -25,33 +25,29 @@
25#include <linux/interrupt.h> 25#include <linux/interrupt.h>
26#include <linux/irq.h> 26#include <linux/irq.h>
27#include <linux/io.h> 27#include <linux/io.h>
28#include <linux/of.h>
29#include <linux/of_address.h>
30#include <linux/of_irq.h>
28 31
29#include <asm/sched_clock.h> 32#include <asm/sched_clock.h>
30#include <asm/hardware/arm_timer.h> 33#include <asm/hardware/arm_timer.h>
34#include <asm/hardware/timer-sp.h>
31 35
32static long __init sp804_get_clock_rate(const char *name) 36static long __init sp804_get_clock_rate(struct clk *clk)
33{ 37{
34 struct clk *clk;
35 long rate; 38 long rate;
36 int err; 39 int err;
37 40
38 clk = clk_get_sys("sp804", name);
39 if (IS_ERR(clk)) {
40 pr_err("sp804: %s clock not found: %d\n", name,
41 (int)PTR_ERR(clk));
42 return PTR_ERR(clk);
43 }
44
45 err = clk_prepare(clk); 41 err = clk_prepare(clk);
46 if (err) { 42 if (err) {
47 pr_err("sp804: %s clock failed to prepare: %d\n", name, err); 43 pr_err("sp804: clock failed to prepare: %d\n", err);
48 clk_put(clk); 44 clk_put(clk);
49 return err; 45 return err;
50 } 46 }
51 47
52 err = clk_enable(clk); 48 err = clk_enable(clk);
53 if (err) { 49 if (err) {
54 pr_err("sp804: %s clock failed to enable: %d\n", name, err); 50 pr_err("sp804: clock failed to enable: %d\n", err);
55 clk_unprepare(clk); 51 clk_unprepare(clk);
56 clk_put(clk); 52 clk_put(clk);
57 return err; 53 return err;
@@ -59,7 +55,7 @@ static long __init sp804_get_clock_rate(const char *name)
59 55
60 rate = clk_get_rate(clk); 56 rate = clk_get_rate(clk);
61 if (rate < 0) { 57 if (rate < 0) {
62 pr_err("sp804: %s clock failed to get rate: %ld\n", name, rate); 58 pr_err("sp804: clock failed to get rate: %ld\n", rate);
63 clk_disable(clk); 59 clk_disable(clk);
64 clk_unprepare(clk); 60 clk_unprepare(clk);
65 clk_put(clk); 61 clk_put(clk);
@@ -77,9 +73,21 @@ static u32 sp804_read(void)
77 73
78void __init __sp804_clocksource_and_sched_clock_init(void __iomem *base, 74void __init __sp804_clocksource_and_sched_clock_init(void __iomem *base,
79 const char *name, 75 const char *name,
76 struct clk *clk,
80 int use_sched_clock) 77 int use_sched_clock)
81{ 78{
82 long rate = sp804_get_clock_rate(name); 79 long rate;
80
81 if (!clk) {
82 clk = clk_get_sys("sp804", name);
83 if (IS_ERR(clk)) {
84 pr_err("sp804: clock not found: %d\n",
85 (int)PTR_ERR(clk));
86 return;
87 }
88 }
89
90 rate = sp804_get_clock_rate(clk);
83 91
84 if (rate < 0) 92 if (rate < 0)
85 return; 93 return;
@@ -171,12 +179,20 @@ static struct irqaction sp804_timer_irq = {
171 .dev_id = &sp804_clockevent, 179 .dev_id = &sp804_clockevent,
172}; 180};
173 181
174void __init sp804_clockevents_init(void __iomem *base, unsigned int irq, 182void __init __sp804_clockevents_init(void __iomem *base, unsigned int irq, struct clk *clk, const char *name)
175 const char *name)
176{ 183{
177 struct clock_event_device *evt = &sp804_clockevent; 184 struct clock_event_device *evt = &sp804_clockevent;
178 long rate = sp804_get_clock_rate(name); 185 long rate;
179 186
187 if (!clk)
188 clk = clk_get_sys("sp804", name);
189 if (IS_ERR(clk)) {
190 pr_err("sp804: %s clock not found: %d\n", name,
191 (int)PTR_ERR(clk));
192 return;
193 }
194
195 rate = sp804_get_clock_rate(clk);
180 if (rate < 0) 196 if (rate < 0)
181 return; 197 return;
182 198
@@ -186,6 +202,98 @@ void __init sp804_clockevents_init(void __iomem *base, unsigned int irq,
186 evt->irq = irq; 202 evt->irq = irq;
187 evt->cpumask = cpu_possible_mask; 203 evt->cpumask = cpu_possible_mask;
188 204
205 writel(0, base + TIMER_CTRL);
206
189 setup_irq(irq, &sp804_timer_irq); 207 setup_irq(irq, &sp804_timer_irq);
190 clockevents_config_and_register(evt, rate, 0xf, 0xffffffff); 208 clockevents_config_and_register(evt, rate, 0xf, 0xffffffff);
191} 209}
210
211static void __init sp804_of_init(struct device_node *np)
212{
213 static bool initialized = false;
214 void __iomem *base;
215 int irq;
216 u32 irq_num = 0;
217 struct clk *clk1, *clk2;
218 const char *name = of_get_property(np, "compatible", NULL);
219
220 base = of_iomap(np, 0);
221 if (WARN_ON(!base))
222 return;
223
224 /* Ensure timers are disabled */
225 writel(0, base + TIMER_CTRL);
226 writel(0, base + TIMER_2_BASE + TIMER_CTRL);
227
228 if (initialized || !of_device_is_available(np))
229 goto err;
230
231 clk1 = of_clk_get(np, 0);
232 if (IS_ERR(clk1))
233 clk1 = NULL;
234
235 /* Get the 2nd clock if the timer has 2 timer clocks */
236 if (of_count_phandle_with_args(np, "clocks", "#clock-cells") == 3) {
237 clk2 = of_clk_get(np, 1);
238 if (IS_ERR(clk2)) {
239 pr_err("sp804: %s clock not found: %d\n", np->name,
240 (int)PTR_ERR(clk2));
241 goto err;
242 }
243 } else
244 clk2 = clk1;
245
246 irq = irq_of_parse_and_map(np, 0);
247 if (irq <= 0)
248 goto err;
249
250 of_property_read_u32(np, "arm,sp804-has-irq", &irq_num);
251 if (irq_num == 2) {
252 __sp804_clockevents_init(base + TIMER_2_BASE, irq, clk2, name);
253 __sp804_clocksource_and_sched_clock_init(base, name, clk1, 1);
254 } else {
255 __sp804_clockevents_init(base, irq, clk1 , name);
256 __sp804_clocksource_and_sched_clock_init(base + TIMER_2_BASE,
257 name, clk2, 1);
258 }
259 initialized = true;
260
261 return;
262err:
263 iounmap(base);
264}
265CLOCKSOURCE_OF_DECLARE(sp804, "arm,sp804", sp804_of_init);
266
267static void __init integrator_cp_of_init(struct device_node *np)
268{
269 static int init_count = 0;
270 void __iomem *base;
271 int irq;
272 const char *name = of_get_property(np, "compatible", NULL);
273
274 base = of_iomap(np, 0);
275 if (WARN_ON(!base))
276 return;
277
278 /* Ensure timer is disabled */
279 writel(0, base + TIMER_CTRL);
280
281 if (init_count == 2 || !of_device_is_available(np))
282 goto err;
283
284 if (!init_count)
285 sp804_clocksource_init(base, name);
286 else {
287 irq = irq_of_parse_and_map(np, 0);
288 if (irq <= 0)
289 goto err;
290
291 sp804_clockevents_init(base, irq, name);
292 }
293
294 init_count++;
295 return;
296err:
297 iounmap(base);
298}
299CLOCKSOURCE_OF_DECLARE(intcp, "arm,integrator-cp-timer", integrator_cp_of_init);
diff --git a/arch/arm/include/asm/arch_timer.h b/arch/arm/include/asm/arch_timer.h
index 7ade91d8cc6f..7c1bfc0aea0c 100644
--- a/arch/arm/include/asm/arch_timer.h
+++ b/arch/arm/include/asm/arch_timer.h
@@ -10,8 +10,7 @@
10#include <clocksource/arm_arch_timer.h> 10#include <clocksource/arm_arch_timer.h>
11 11
12#ifdef CONFIG_ARM_ARCH_TIMER 12#ifdef CONFIG_ARM_ARCH_TIMER
13int arch_timer_of_register(void); 13int arch_timer_arch_init(void);
14int arch_timer_sched_clock_init(void);
15 14
16/* 15/*
17 * These register accessors are marked inline so the compiler can 16 * These register accessors are marked inline so the compiler can
@@ -110,16 +109,6 @@ static inline void __cpuinit arch_counter_set_user_access(void)
110 109
111 asm volatile("mcr p15, 0, %0, c14, c1, 0" : : "r" (cntkctl)); 110 asm volatile("mcr p15, 0, %0, c14, c1, 0" : : "r" (cntkctl));
112} 111}
113#else
114static inline int arch_timer_of_register(void)
115{
116 return -ENXIO;
117}
118
119static inline int arch_timer_sched_clock_init(void)
120{
121 return -ENXIO;
122}
123#endif 112#endif
124 113
125#endif 114#endif
diff --git a/arch/arm/include/asm/hardware/timer-sp.h b/arch/arm/include/asm/hardware/timer-sp.h
index 2dd9d3f83f29..bb28af7c32de 100644
--- a/arch/arm/include/asm/hardware/timer-sp.h
+++ b/arch/arm/include/asm/hardware/timer-sp.h
@@ -1,15 +1,23 @@
1struct clk;
2
1void __sp804_clocksource_and_sched_clock_init(void __iomem *, 3void __sp804_clocksource_and_sched_clock_init(void __iomem *,
2 const char *, int); 4 const char *, struct clk *, int);
5void __sp804_clockevents_init(void __iomem *, unsigned int,
6 struct clk *, const char *);
3 7
4static inline void sp804_clocksource_init(void __iomem *base, const char *name) 8static inline void sp804_clocksource_init(void __iomem *base, const char *name)
5{ 9{
6 __sp804_clocksource_and_sched_clock_init(base, name, 0); 10 __sp804_clocksource_and_sched_clock_init(base, name, NULL, 0);
7} 11}
8 12
9static inline void sp804_clocksource_and_sched_clock_init(void __iomem *base, 13static inline void sp804_clocksource_and_sched_clock_init(void __iomem *base,
10 const char *name) 14 const char *name)
11{ 15{
12 __sp804_clocksource_and_sched_clock_init(base, name, 1); 16 __sp804_clocksource_and_sched_clock_init(base, name, NULL, 1);
13} 17}
14 18
15void sp804_clockevents_init(void __iomem *, unsigned int, const char *); 19static inline void sp804_clockevents_init(void __iomem *base, unsigned int irq, const char *name)
20{
21 __sp804_clockevents_init(base, irq, NULL, name);
22
23}
diff --git a/arch/arm/include/asm/sched_clock.h b/arch/arm/include/asm/sched_clock.h
index e3f757263438..3d520ddca61b 100644
--- a/arch/arm/include/asm/sched_clock.h
+++ b/arch/arm/include/asm/sched_clock.h
@@ -11,4 +11,6 @@
11extern void sched_clock_postinit(void); 11extern void sched_clock_postinit(void);
12extern void setup_sched_clock(u32 (*read)(void), int bits, unsigned long rate); 12extern void setup_sched_clock(u32 (*read)(void), int bits, unsigned long rate);
13 13
14extern unsigned long long (*sched_clock_func)(void);
15
14#endif 16#endif
diff --git a/arch/arm/include/asm/smp_twd.h b/arch/arm/include/asm/smp_twd.h
index 0f01f4677bd2..7b2899c2f7fc 100644
--- a/arch/arm/include/asm/smp_twd.h
+++ b/arch/arm/include/asm/smp_twd.h
@@ -34,12 +34,4 @@ struct twd_local_timer name __initdata = { \
34 34
35int twd_local_timer_register(struct twd_local_timer *); 35int twd_local_timer_register(struct twd_local_timer *);
36 36
37#ifdef CONFIG_HAVE_ARM_TWD
38void twd_local_timer_of_register(void);
39#else
40static inline void twd_local_timer_of_register(void)
41{
42}
43#endif
44
45#endif 37#endif
diff --git a/arch/arm/kernel/arch_timer.c b/arch/arm/kernel/arch_timer.c
index d957a51435d8..59dcdced6e30 100644
--- a/arch/arm/kernel/arch_timer.c
+++ b/arch/arm/kernel/arch_timer.c
@@ -22,9 +22,11 @@ static unsigned long arch_timer_read_counter_long(void)
22 return arch_timer_read_counter(); 22 return arch_timer_read_counter();
23} 23}
24 24
25static u32 arch_timer_read_counter_u32(void) 25static u32 sched_clock_mult __read_mostly;
26
27static unsigned long long notrace arch_timer_sched_clock(void)
26{ 28{
27 return arch_timer_read_counter(); 29 return arch_timer_read_counter() * sched_clock_mult;
28} 30}
29 31
30static struct delay_timer arch_delay_timer; 32static struct delay_timer arch_delay_timer;
@@ -37,25 +39,20 @@ static void __init arch_timer_delay_timer_register(void)
37 register_current_timer_delay(&arch_delay_timer); 39 register_current_timer_delay(&arch_delay_timer);
38} 40}
39 41
40int __init arch_timer_of_register(void) 42int __init arch_timer_arch_init(void)
41{ 43{
42 int ret; 44 u32 arch_timer_rate = arch_timer_get_rate();
43 45
44 ret = arch_timer_init(); 46 if (arch_timer_rate == 0)
45 if (ret) 47 return -ENXIO;
46 return ret;
47 48
48 arch_timer_delay_timer_register(); 49 arch_timer_delay_timer_register();
49 50
50 return 0; 51 /* Cache the sched_clock multiplier to save a divide in the hot path. */
51} 52 sched_clock_mult = NSEC_PER_SEC / arch_timer_rate;
52 53 sched_clock_func = arch_timer_sched_clock;
53int __init arch_timer_sched_clock_init(void) 54 pr_info("sched_clock: ARM arch timer >56 bits at %ukHz, resolution %uns\n",
54{ 55 arch_timer_rate / 1000, sched_clock_mult);
55 if (arch_timer_get_rate() == 0)
56 return -ENXIO;
57 56
58 setup_sched_clock(arch_timer_read_counter_u32,
59 32, arch_timer_get_rate());
60 return 0; 57 return 0;
61} 58}
diff --git a/arch/arm/kernel/entry-armv.S b/arch/arm/kernel/entry-armv.S
index 0f82098c9bfe..cd22d821bf74 100644
--- a/arch/arm/kernel/entry-armv.S
+++ b/arch/arm/kernel/entry-armv.S
@@ -562,21 +562,21 @@ ENDPROC(__und_usr)
562 @ Fall-through from Thumb-2 __und_usr 562 @ Fall-through from Thumb-2 __und_usr
563 @ 563 @
564#ifdef CONFIG_NEON 564#ifdef CONFIG_NEON
565 get_thread_info r10 @ get current thread
565 adr r6, .LCneon_thumb_opcodes 566 adr r6, .LCneon_thumb_opcodes
566 b 2f 567 b 2f
567#endif 568#endif
568call_fpe: 569call_fpe:
570 get_thread_info r10 @ get current thread
569#ifdef CONFIG_NEON 571#ifdef CONFIG_NEON
570 adr r6, .LCneon_arm_opcodes 572 adr r6, .LCneon_arm_opcodes
5712: 5732: ldr r5, [r6], #4 @ mask value
572 ldr r7, [r6], #4 @ mask value
573 cmp r7, #0 @ end mask?
574 beq 1f
575 and r8, r0, r7
576 ldr r7, [r6], #4 @ opcode bits matching in mask 574 ldr r7, [r6], #4 @ opcode bits matching in mask
575 cmp r5, #0 @ end mask?
576 beq 1f
577 and r8, r0, r5
577 cmp r8, r7 @ NEON instruction? 578 cmp r8, r7 @ NEON instruction?
578 bne 2b 579 bne 2b
579 get_thread_info r10
580 mov r7, #1 580 mov r7, #1
581 strb r7, [r10, #TI_USED_CP + 10] @ mark CP#10 as used 581 strb r7, [r10, #TI_USED_CP + 10] @ mark CP#10 as used
582 strb r7, [r10, #TI_USED_CP + 11] @ mark CP#11 as used 582 strb r7, [r10, #TI_USED_CP + 11] @ mark CP#11 as used
@@ -586,7 +586,6 @@ call_fpe:
586 tst r0, #0x08000000 @ only CDP/CPRT/LDC/STC have bit 27 586 tst r0, #0x08000000 @ only CDP/CPRT/LDC/STC have bit 27
587 tstne r0, #0x04000000 @ bit 26 set on both ARM and Thumb-2 587 tstne r0, #0x04000000 @ bit 26 set on both ARM and Thumb-2
588 moveq pc, lr 588 moveq pc, lr
589 get_thread_info r10 @ get current thread
590 and r8, r0, #0x00000f00 @ mask out CP number 589 and r8, r0, #0x00000f00 @ mask out CP number
591 THUMB( lsr r8, r8, #8 ) 590 THUMB( lsr r8, r8, #8 )
592 mov r7, #1 591 mov r7, #1
diff --git a/arch/arm/kernel/process.c b/arch/arm/kernel/process.c
index 047d3e40e470..cbd0f51937cc 100644
--- a/arch/arm/kernel/process.c
+++ b/arch/arm/kernel/process.c
@@ -459,15 +459,16 @@ unsigned long arch_randomize_brk(struct mm_struct *mm)
459 * atomic helpers and the signal restart code. Insert it into the 459 * atomic helpers and the signal restart code. Insert it into the
460 * gate_vma so that it is visible through ptrace and /proc/<pid>/mem. 460 * gate_vma so that it is visible through ptrace and /proc/<pid>/mem.
461 */ 461 */
462static struct vm_area_struct gate_vma; 462static struct vm_area_struct gate_vma = {
463 .vm_start = 0xffff0000,
464 .vm_end = 0xffff0000 + PAGE_SIZE,
465 .vm_flags = VM_READ | VM_EXEC | VM_MAYREAD | VM_MAYEXEC,
466 .vm_mm = &init_mm,
467};
463 468
464static int __init gate_vma_init(void) 469static int __init gate_vma_init(void)
465{ 470{
466 gate_vma.vm_start = 0xffff0000; 471 gate_vma.vm_page_prot = PAGE_READONLY_EXEC;
467 gate_vma.vm_end = 0xffff0000 + PAGE_SIZE;
468 gate_vma.vm_page_prot = PAGE_READONLY_EXEC;
469 gate_vma.vm_flags = VM_READ | VM_EXEC |
470 VM_MAYREAD | VM_MAYEXEC;
471 return 0; 472 return 0;
472} 473}
473arch_initcall(gate_vma_init); 474arch_initcall(gate_vma_init);
diff --git a/arch/arm/kernel/sched_clock.c b/arch/arm/kernel/sched_clock.c
index bd6f56b9ec21..880584852fca 100644
--- a/arch/arm/kernel/sched_clock.c
+++ b/arch/arm/kernel/sched_clock.c
@@ -20,6 +20,7 @@ struct clock_data {
20 u64 epoch_ns; 20 u64 epoch_ns;
21 u32 epoch_cyc; 21 u32 epoch_cyc;
22 u32 epoch_cyc_copy; 22 u32 epoch_cyc_copy;
23 unsigned long rate;
23 u32 mult; 24 u32 mult;
24 u32 shift; 25 u32 shift;
25 bool suspended; 26 bool suspended;
@@ -113,11 +114,14 @@ void __init setup_sched_clock(u32 (*read)(void), int bits, unsigned long rate)
113 u64 res, wrap; 114 u64 res, wrap;
114 char r_unit; 115 char r_unit;
115 116
117 if (cd.rate > rate)
118 return;
119
116 BUG_ON(bits > 32); 120 BUG_ON(bits > 32);
117 WARN_ON(!irqs_disabled()); 121 WARN_ON(!irqs_disabled());
118 WARN_ON(read_sched_clock != jiffy_sched_clock_read);
119 read_sched_clock = read; 122 read_sched_clock = read;
120 sched_clock_mask = (1 << bits) - 1; 123 sched_clock_mask = (1 << bits) - 1;
124 cd.rate = rate;
121 125
122 /* calculate the mult/shift to convert counter ticks to ns. */ 126 /* calculate the mult/shift to convert counter ticks to ns. */
123 clocks_calc_mult_shift(&cd.mult, &cd.shift, rate, NSEC_PER_SEC, 0); 127 clocks_calc_mult_shift(&cd.mult, &cd.shift, rate, NSEC_PER_SEC, 0);
@@ -161,12 +165,19 @@ void __init setup_sched_clock(u32 (*read)(void), int bits, unsigned long rate)
161 pr_debug("Registered %pF as sched_clock source\n", read); 165 pr_debug("Registered %pF as sched_clock source\n", read);
162} 166}
163 167
164unsigned long long notrace sched_clock(void) 168static unsigned long long notrace sched_clock_32(void)
165{ 169{
166 u32 cyc = read_sched_clock(); 170 u32 cyc = read_sched_clock();
167 return cyc_to_sched_clock(cyc, sched_clock_mask); 171 return cyc_to_sched_clock(cyc, sched_clock_mask);
168} 172}
169 173
174unsigned long long __read_mostly (*sched_clock_func)(void) = sched_clock_32;
175
176unsigned long long notrace sched_clock(void)
177{
178 return sched_clock_func();
179}
180
170void __init sched_clock_postinit(void) 181void __init sched_clock_postinit(void)
171{ 182{
172 /* 183 /*
diff --git a/arch/arm/kernel/smp_twd.c b/arch/arm/kernel/smp_twd.c
index 3f2565037480..90525d9d290b 100644
--- a/arch/arm/kernel/smp_twd.c
+++ b/arch/arm/kernel/smp_twd.c
@@ -362,25 +362,13 @@ int __init twd_local_timer_register(struct twd_local_timer *tlt)
362} 362}
363 363
364#ifdef CONFIG_OF 364#ifdef CONFIG_OF
365const static struct of_device_id twd_of_match[] __initconst = { 365static void __init twd_local_timer_of_register(struct device_node *np)
366 { .compatible = "arm,cortex-a9-twd-timer", },
367 { .compatible = "arm,cortex-a5-twd-timer", },
368 { .compatible = "arm,arm11mp-twd-timer", },
369 { },
370};
371
372void __init twd_local_timer_of_register(void)
373{ 366{
374 struct device_node *np;
375 int err; 367 int err;
376 368
377 if (!is_smp() || !setup_max_cpus) 369 if (!is_smp() || !setup_max_cpus)
378 return; 370 return;
379 371
380 np = of_find_matching_node(NULL, twd_of_match);
381 if (!np)
382 return;
383
384 twd_ppi = irq_of_parse_and_map(np, 0); 372 twd_ppi = irq_of_parse_and_map(np, 0);
385 if (!twd_ppi) { 373 if (!twd_ppi) {
386 err = -EINVAL; 374 err = -EINVAL;
@@ -398,4 +386,7 @@ void __init twd_local_timer_of_register(void)
398out: 386out:
399 WARN(err, "twd_local_timer_of_register failed (%d)\n", err); 387 WARN(err, "twd_local_timer_of_register failed (%d)\n", err);
400} 388}
389CLOCKSOURCE_OF_DECLARE(arm_twd_a9, "arm,cortex-a9-twd-timer", twd_local_timer_of_register);
390CLOCKSOURCE_OF_DECLARE(arm_twd_a5, "arm,cortex-a5-twd-timer", twd_local_timer_of_register);
391CLOCKSOURCE_OF_DECLARE(arm_twd_11mp, "arm,arm11mp-twd-timer", twd_local_timer_of_register);
401#endif 392#endif
diff --git a/arch/arm/kernel/time.c b/arch/arm/kernel/time.c
index 955d92d265e5..abff4e9aaee0 100644
--- a/arch/arm/kernel/time.c
+++ b/arch/arm/kernel/time.c
@@ -22,6 +22,7 @@
22#include <linux/errno.h> 22#include <linux/errno.h>
23#include <linux/profile.h> 23#include <linux/profile.h>
24#include <linux/timer.h> 24#include <linux/timer.h>
25#include <linux/clocksource.h>
25#include <linux/irq.h> 26#include <linux/irq.h>
26 27
27#include <asm/thread_info.h> 28#include <asm/thread_info.h>
@@ -115,6 +116,10 @@ int __init register_persistent_clock(clock_access_fn read_boot,
115 116
116void __init time_init(void) 117void __init time_init(void)
117{ 118{
118 machine_desc->init_time(); 119 if (machine_desc->init_time)
120 machine_desc->init_time();
121 else
122 clocksource_of_init();
123
119 sched_clock_postinit(); 124 sched_clock_postinit();
120} 125}
diff --git a/arch/arm/mach-at91/at91sam9261.c b/arch/arm/mach-at91/at91sam9261.c
index ac7a341bd0ff..25efb5ac30f1 100644
--- a/arch/arm/mach-at91/at91sam9261.c
+++ b/arch/arm/mach-at91/at91sam9261.c
@@ -169,6 +169,8 @@ static struct clk *periph_clocks[] __initdata = {
169}; 169};
170 170
171static struct clk_lookup periph_clocks_lookups[] = { 171static struct clk_lookup periph_clocks_lookups[] = {
172 CLKDEV_CON_DEV_ID("hclk", "at91sam9261-lcdfb.0", &hck1),
173 CLKDEV_CON_DEV_ID("hclk", "at91sam9g10-lcdfb.0", &hck1),
172 CLKDEV_CON_DEV_ID("spi_clk", "atmel_spi.0", &spi0_clk), 174 CLKDEV_CON_DEV_ID("spi_clk", "atmel_spi.0", &spi0_clk),
173 CLKDEV_CON_DEV_ID("spi_clk", "atmel_spi.1", &spi1_clk), 175 CLKDEV_CON_DEV_ID("spi_clk", "atmel_spi.1", &spi1_clk),
174 CLKDEV_CON_DEV_ID("t0_clk", "atmel_tcb.0", &tc0_clk), 176 CLKDEV_CON_DEV_ID("t0_clk", "atmel_tcb.0", &tc0_clk),
diff --git a/arch/arm/mach-at91/at91sam9261_devices.c b/arch/arm/mach-at91/at91sam9261_devices.c
index 92e0f861084a..629ea5fc95cf 100644
--- a/arch/arm/mach-at91/at91sam9261_devices.c
+++ b/arch/arm/mach-at91/at91sam9261_devices.c
@@ -488,7 +488,6 @@ static struct resource lcdc_resources[] = {
488}; 488};
489 489
490static struct platform_device at91_lcdc_device = { 490static struct platform_device at91_lcdc_device = {
491 .name = "atmel_lcdfb",
492 .id = 0, 491 .id = 0,
493 .dev = { 492 .dev = {
494 .dma_mask = &lcdc_dmamask, 493 .dma_mask = &lcdc_dmamask,
@@ -505,6 +504,11 @@ void __init at91_add_device_lcdc(struct atmel_lcdfb_info *data)
505 return; 504 return;
506 } 505 }
507 506
507 if (cpu_is_at91sam9g10())
508 at91_lcdc_device.name = "at91sam9g10-lcdfb";
509 else
510 at91_lcdc_device.name = "at91sam9261-lcdfb";
511
508#if defined(CONFIG_FB_ATMEL_STN) 512#if defined(CONFIG_FB_ATMEL_STN)
509 at91_set_A_periph(AT91_PIN_PB0, 0); /* LCDVSYNC */ 513 at91_set_A_periph(AT91_PIN_PB0, 0); /* LCDVSYNC */
510 at91_set_A_periph(AT91_PIN_PB1, 0); /* LCDHSYNC */ 514 at91_set_A_periph(AT91_PIN_PB1, 0); /* LCDHSYNC */
diff --git a/arch/arm/mach-at91/at91sam9263.c b/arch/arm/mach-at91/at91sam9263.c
index 8e2d9f4a9a45..f44ffd2105a7 100644
--- a/arch/arm/mach-at91/at91sam9263.c
+++ b/arch/arm/mach-at91/at91sam9263.c
@@ -190,6 +190,7 @@ static struct clk_lookup periph_clocks_lookups[] = {
190 CLKDEV_CON_DEV_ID("pclk", "at91rm9200_ssc.1", &ssc1_clk), 190 CLKDEV_CON_DEV_ID("pclk", "at91rm9200_ssc.1", &ssc1_clk),
191 CLKDEV_CON_DEV_ID("pclk", "fff98000.ssc", &ssc0_clk), 191 CLKDEV_CON_DEV_ID("pclk", "fff98000.ssc", &ssc0_clk),
192 CLKDEV_CON_DEV_ID("pclk", "fff9c000.ssc", &ssc1_clk), 192 CLKDEV_CON_DEV_ID("pclk", "fff9c000.ssc", &ssc1_clk),
193 CLKDEV_CON_DEV_ID("hclk", "at91sam9263-lcdfb.0", &lcdc_clk),
193 CLKDEV_CON_DEV_ID("mci_clk", "atmel_mci.0", &mmc0_clk), 194 CLKDEV_CON_DEV_ID("mci_clk", "atmel_mci.0", &mmc0_clk),
194 CLKDEV_CON_DEV_ID("mci_clk", "atmel_mci.1", &mmc1_clk), 195 CLKDEV_CON_DEV_ID("mci_clk", "atmel_mci.1", &mmc1_clk),
195 CLKDEV_CON_DEV_ID("spi_clk", "atmel_spi.0", &spi0_clk), 196 CLKDEV_CON_DEV_ID("spi_clk", "atmel_spi.0", &spi0_clk),
diff --git a/arch/arm/mach-at91/at91sam9263_devices.c b/arch/arm/mach-at91/at91sam9263_devices.c
index ed666f5cb01d..858c8aac2daf 100644
--- a/arch/arm/mach-at91/at91sam9263_devices.c
+++ b/arch/arm/mach-at91/at91sam9263_devices.c
@@ -848,7 +848,7 @@ static struct resource lcdc_resources[] = {
848}; 848};
849 849
850static struct platform_device at91_lcdc_device = { 850static struct platform_device at91_lcdc_device = {
851 .name = "atmel_lcdfb", 851 .name = "at91sam9263-lcdfb",
852 .id = 0, 852 .id = 0,
853 .dev = { 853 .dev = {
854 .dma_mask = &lcdc_dmamask, 854 .dma_mask = &lcdc_dmamask,
diff --git a/arch/arm/mach-at91/at91sam9g45.c b/arch/arm/mach-at91/at91sam9g45.c
index 4fcbe7b5b58d..dc49c2c45d49 100644
--- a/arch/arm/mach-at91/at91sam9g45.c
+++ b/arch/arm/mach-at91/at91sam9g45.c
@@ -228,6 +228,8 @@ static struct clk_lookup periph_clocks_lookups[] = {
228 CLKDEV_CON_ID("hclk", &macb_clk), 228 CLKDEV_CON_ID("hclk", &macb_clk),
229 /* One additional fake clock for ohci */ 229 /* One additional fake clock for ohci */
230 CLKDEV_CON_ID("ohci_clk", &uhphs_clk), 230 CLKDEV_CON_ID("ohci_clk", &uhphs_clk),
231 CLKDEV_CON_DEV_ID("hclk", "at91sam9g45-lcdfb.0", &lcdc_clk),
232 CLKDEV_CON_DEV_ID("hclk", "at91sam9g45es-lcdfb.0", &lcdc_clk),
231 CLKDEV_CON_DEV_ID("ehci_clk", "atmel-ehci", &uhphs_clk), 233 CLKDEV_CON_DEV_ID("ehci_clk", "atmel-ehci", &uhphs_clk),
232 CLKDEV_CON_DEV_ID("hclk", "atmel_usba_udc", &utmi_clk), 234 CLKDEV_CON_DEV_ID("hclk", "atmel_usba_udc", &utmi_clk),
233 CLKDEV_CON_DEV_ID("pclk", "atmel_usba_udc", &udphs_clk), 235 CLKDEV_CON_DEV_ID("pclk", "atmel_usba_udc", &udphs_clk),
diff --git a/arch/arm/mach-at91/at91sam9g45_devices.c b/arch/arm/mach-at91/at91sam9g45_devices.c
index 827c9f2a70fb..fe626d431b69 100644
--- a/arch/arm/mach-at91/at91sam9g45_devices.c
+++ b/arch/arm/mach-at91/at91sam9g45_devices.c
@@ -981,7 +981,6 @@ static struct resource lcdc_resources[] = {
981}; 981};
982 982
983static struct platform_device at91_lcdc_device = { 983static struct platform_device at91_lcdc_device = {
984 .name = "atmel_lcdfb",
985 .id = 0, 984 .id = 0,
986 .dev = { 985 .dev = {
987 .dma_mask = &lcdc_dmamask, 986 .dma_mask = &lcdc_dmamask,
@@ -997,6 +996,11 @@ void __init at91_add_device_lcdc(struct atmel_lcdfb_info *data)
997 if (!data) 996 if (!data)
998 return; 997 return;
999 998
999 if (cpu_is_at91sam9g45es())
1000 at91_lcdc_device.name = "at91sam9g45es-lcdfb";
1001 else
1002 at91_lcdc_device.name = "at91sam9g45-lcdfb";
1003
1000 at91_set_A_periph(AT91_PIN_PE0, 0); /* LCDDPWR */ 1004 at91_set_A_periph(AT91_PIN_PE0, 0); /* LCDDPWR */
1001 1005
1002 at91_set_A_periph(AT91_PIN_PE2, 0); /* LCDCC */ 1006 at91_set_A_periph(AT91_PIN_PE2, 0); /* LCDCC */
diff --git a/arch/arm/mach-at91/at91sam9rl.c b/arch/arm/mach-at91/at91sam9rl.c
index c39600764236..f77fae5591bc 100644
--- a/arch/arm/mach-at91/at91sam9rl.c
+++ b/arch/arm/mach-at91/at91sam9rl.c
@@ -179,6 +179,7 @@ static struct clk *periph_clocks[] __initdata = {
179}; 179};
180 180
181static struct clk_lookup periph_clocks_lookups[] = { 181static struct clk_lookup periph_clocks_lookups[] = {
182 CLKDEV_CON_DEV_ID("hclk", "at91sam9rl-lcdfb.0", &lcdc_clk),
182 CLKDEV_CON_DEV_ID("hclk", "atmel_usba_udc", &utmi_clk), 183 CLKDEV_CON_DEV_ID("hclk", "atmel_usba_udc", &utmi_clk),
183 CLKDEV_CON_DEV_ID("pclk", "atmel_usba_udc", &udphs_clk), 184 CLKDEV_CON_DEV_ID("pclk", "atmel_usba_udc", &udphs_clk),
184 CLKDEV_CON_DEV_ID("t0_clk", "atmel_tcb.0", &tc0_clk), 185 CLKDEV_CON_DEV_ID("t0_clk", "atmel_tcb.0", &tc0_clk),
diff --git a/arch/arm/mach-at91/at91sam9rl_devices.c b/arch/arm/mach-at91/at91sam9rl_devices.c
index ddf223ff35c4..352468f265a9 100644
--- a/arch/arm/mach-at91/at91sam9rl_devices.c
+++ b/arch/arm/mach-at91/at91sam9rl_devices.c
@@ -514,7 +514,7 @@ static struct resource lcdc_resources[] = {
514}; 514};
515 515
516static struct platform_device at91_lcdc_device = { 516static struct platform_device at91_lcdc_device = {
517 .name = "atmel_lcdfb", 517 .name = "at91sam9rl-lcdfb",
518 .id = 0, 518 .id = 0,
519 .dev = { 519 .dev = {
520 .dma_mask = &lcdc_dmamask, 520 .dma_mask = &lcdc_dmamask,
diff --git a/arch/arm/mach-exynos/Kconfig b/arch/arm/mach-exynos/Kconfig
index 70f94c87479d..faca4326b46a 100644
--- a/arch/arm/mach-exynos/Kconfig
+++ b/arch/arm/mach-exynos/Kconfig
@@ -79,12 +79,6 @@ config SOC_EXYNOS5440
79 help 79 help
80 Enable EXYNOS5440 SoC support 80 Enable EXYNOS5440 SoC support
81 81
82config EXYNOS4_MCT
83 bool
84 default y
85 help
86 Use MCT (Multi Core Timer) as kernel timers
87
88config EXYNOS_DEV_DMA 82config EXYNOS_DEV_DMA
89 bool 83 bool
90 help 84 help
@@ -276,8 +270,8 @@ config MACH_UNIVERSAL_C210
276 select S5P_DEV_ONENAND 270 select S5P_DEV_ONENAND
277 select S5P_DEV_TV 271 select S5P_DEV_TV
278 select S5P_GPIO_INT 272 select S5P_GPIO_INT
279 select S5P_HRT
280 select S5P_SETUP_MIPIPHY 273 select S5P_SETUP_MIPIPHY
274 select SAMSUNG_HRT
281 help 275 help
282 Machine support for Samsung Mobile Universal S5PC210 Reference 276 Machine support for Samsung Mobile Universal S5PC210 Reference
283 Board. 277 Board.
@@ -406,6 +400,7 @@ config MACH_EXYNOS4_DT
406 bool "Samsung Exynos4 Machine using device tree" 400 bool "Samsung Exynos4 Machine using device tree"
407 depends on ARCH_EXYNOS4 401 depends on ARCH_EXYNOS4
408 select ARM_AMBA 402 select ARM_AMBA
403 select CLKSRC_OF
409 select CPU_EXYNOS4210 404 select CPU_EXYNOS4210
410 select HAVE_SAMSUNG_KEYPAD if INPUT_KEYBOARD 405 select HAVE_SAMSUNG_KEYPAD if INPUT_KEYBOARD
411 select PINCTRL 406 select PINCTRL
@@ -422,6 +417,7 @@ config MACH_EXYNOS5_DT
422 default y 417 default y
423 depends on ARCH_EXYNOS5 418 depends on ARCH_EXYNOS5
424 select ARM_AMBA 419 select ARM_AMBA
420 select CLKSRC_OF
425 select USE_OF 421 select USE_OF
426 help 422 help
427 Machine support for Samsung EXYNOS5 machine with device tree enabled. 423 Machine support for Samsung EXYNOS5 machine with device tree enabled.
diff --git a/arch/arm/mach-exynos/Makefile b/arch/arm/mach-exynos/Makefile
index 435757e57bb4..daf289b21486 100644
--- a/arch/arm/mach-exynos/Makefile
+++ b/arch/arm/mach-exynos/Makefile
@@ -26,8 +26,6 @@ obj-$(CONFIG_ARCH_EXYNOS) += pmu.o
26 26
27obj-$(CONFIG_SMP) += platsmp.o headsmp.o 27obj-$(CONFIG_SMP) += platsmp.o headsmp.o
28 28
29obj-$(CONFIG_EXYNOS4_MCT) += mct.o
30
31obj-$(CONFIG_HOTPLUG_CPU) += hotplug.o 29obj-$(CONFIG_HOTPLUG_CPU) += hotplug.o
32 30
33# machine support 31# machine support
diff --git a/arch/arm/mach-exynos/common.c b/arch/arm/mach-exynos/common.c
index d63d399c7bae..db7dbd0eb6b4 100644
--- a/arch/arm/mach-exynos/common.c
+++ b/arch/arm/mach-exynos/common.c
@@ -257,11 +257,6 @@ static struct map_desc exynos5_iodesc[] __initdata = {
257 .length = SZ_4K, 257 .length = SZ_4K,
258 .type = MT_DEVICE, 258 .type = MT_DEVICE,
259 }, { 259 }, {
260 .virtual = (unsigned long)S5P_VA_SYSTIMER,
261 .pfn = __phys_to_pfn(EXYNOS5_PA_SYSTIMER),
262 .length = SZ_4K,
263 .type = MT_DEVICE,
264 }, {
265 .virtual = (unsigned long)S5P_VA_SYSRAM, 260 .virtual = (unsigned long)S5P_VA_SYSRAM,
266 .pfn = __phys_to_pfn(EXYNOS5_PA_SYSRAM), 261 .pfn = __phys_to_pfn(EXYNOS5_PA_SYSRAM),
267 .length = SZ_4K, 262 .length = SZ_4K,
@@ -822,6 +817,7 @@ static int __init exynos_init_irq_eint(void)
822 static const struct of_device_id exynos_pinctrl_ids[] = { 817 static const struct of_device_id exynos_pinctrl_ids[] = {
823 { .compatible = "samsung,exynos4210-pinctrl", }, 818 { .compatible = "samsung,exynos4210-pinctrl", },
824 { .compatible = "samsung,exynos4x12-pinctrl", }, 819 { .compatible = "samsung,exynos4x12-pinctrl", },
820 { .compatible = "samsung,exynos5250-pinctrl", },
825 }; 821 };
826 struct device_node *pctrl_np, *wkup_np; 822 struct device_node *pctrl_np, *wkup_np;
827 const char *wkup_compat = "samsung,exynos4210-wakeup-eint"; 823 const char *wkup_compat = "samsung,exynos4210-wakeup-eint";
diff --git a/arch/arm/mach-exynos/common.h b/arch/arm/mach-exynos/common.h
index 9339bb8954be..3b186eaaaa7b 100644
--- a/arch/arm/mach-exynos/common.h
+++ b/arch/arm/mach-exynos/common.h
@@ -12,7 +12,7 @@
12#ifndef __ARCH_ARM_MACH_EXYNOS_COMMON_H 12#ifndef __ARCH_ARM_MACH_EXYNOS_COMMON_H
13#define __ARCH_ARM_MACH_EXYNOS_COMMON_H 13#define __ARCH_ARM_MACH_EXYNOS_COMMON_H
14 14
15extern void exynos4_timer_init(void); 15extern void mct_init(void);
16 16
17struct map_desc; 17struct map_desc;
18void exynos_init_io(struct map_desc *mach_desc, int size); 18void exynos_init_io(struct map_desc *mach_desc, int size);
diff --git a/arch/arm/mach-exynos/include/mach/irqs.h b/arch/arm/mach-exynos/include/mach/irqs.h
index 1f4dc35cd4b9..c0e75d8dd737 100644
--- a/arch/arm/mach-exynos/include/mach/irqs.h
+++ b/arch/arm/mach-exynos/include/mach/irqs.h
@@ -30,8 +30,6 @@
30 30
31/* For EXYNOS4 and EXYNOS5 */ 31/* For EXYNOS4 and EXYNOS5 */
32 32
33#define EXYNOS_IRQ_MCT_LOCALTIMER IRQ_PPI(12)
34
35#define EXYNOS_IRQ_EINT16_31 IRQ_SPI(32) 33#define EXYNOS_IRQ_EINT16_31 IRQ_SPI(32)
36 34
37/* For EXYNOS4 SoCs */ 35/* For EXYNOS4 SoCs */
@@ -323,8 +321,6 @@
323#define EXYNOS5_IRQ_CEC IRQ_SPI(114) 321#define EXYNOS5_IRQ_CEC IRQ_SPI(114)
324#define EXYNOS5_IRQ_SATA IRQ_SPI(115) 322#define EXYNOS5_IRQ_SATA IRQ_SPI(115)
325 323
326#define EXYNOS5_IRQ_MCT_L0 IRQ_SPI(120)
327#define EXYNOS5_IRQ_MCT_L1 IRQ_SPI(121)
328#define EXYNOS5_IRQ_MMC44 IRQ_SPI(123) 324#define EXYNOS5_IRQ_MMC44 IRQ_SPI(123)
329#define EXYNOS5_IRQ_MDMA1 IRQ_SPI(124) 325#define EXYNOS5_IRQ_MDMA1 IRQ_SPI(124)
330#define EXYNOS5_IRQ_FIMC_LITE0 IRQ_SPI(125) 326#define EXYNOS5_IRQ_FIMC_LITE0 IRQ_SPI(125)
@@ -419,8 +415,6 @@
419#define EXYNOS5_IRQ_PMU_CPU1 COMBINER_IRQ(22, 4) 415#define EXYNOS5_IRQ_PMU_CPU1 COMBINER_IRQ(22, 4)
420 416
421#define EXYNOS5_IRQ_EINT0 COMBINER_IRQ(23, 0) 417#define EXYNOS5_IRQ_EINT0 COMBINER_IRQ(23, 0)
422#define EXYNOS5_IRQ_MCT_G0 COMBINER_IRQ(23, 3)
423#define EXYNOS5_IRQ_MCT_G1 COMBINER_IRQ(23, 4)
424 418
425#define EXYNOS5_IRQ_EINT1 COMBINER_IRQ(24, 0) 419#define EXYNOS5_IRQ_EINT1 COMBINER_IRQ(24, 0)
426#define EXYNOS5_IRQ_SYSMMU_LITE1_0 COMBINER_IRQ(24, 1) 420#define EXYNOS5_IRQ_SYSMMU_LITE1_0 COMBINER_IRQ(24, 1)
diff --git a/arch/arm/mach-exynos/include/mach/map.h b/arch/arm/mach-exynos/include/mach/map.h
index 1df6abbf53b8..7f99b7b187d6 100644
--- a/arch/arm/mach-exynos/include/mach/map.h
+++ b/arch/arm/mach-exynos/include/mach/map.h
@@ -65,7 +65,6 @@
65#define EXYNOS5_PA_CMU 0x10010000 65#define EXYNOS5_PA_CMU 0x10010000
66 66
67#define EXYNOS4_PA_SYSTIMER 0x10050000 67#define EXYNOS4_PA_SYSTIMER 0x10050000
68#define EXYNOS5_PA_SYSTIMER 0x101C0000
69 68
70#define EXYNOS4_PA_WATCHDOG 0x10060000 69#define EXYNOS4_PA_WATCHDOG 0x10060000
71#define EXYNOS5_PA_WATCHDOG 0x101D0000 70#define EXYNOS5_PA_WATCHDOG 0x101D0000
diff --git a/arch/arm/mach-exynos/include/mach/regs-mct.h b/arch/arm/mach-exynos/include/mach/regs-mct.h
deleted file mode 100644
index 80dd02ad6d61..000000000000
--- a/arch/arm/mach-exynos/include/mach/regs-mct.h
+++ /dev/null
@@ -1,53 +0,0 @@
1/* arch/arm/mach-exynos4/include/mach/regs-mct.h
2 *
3 * Copyright (c) 2011 Samsung Electronics Co., Ltd.
4 * http://www.samsung.com
5 *
6 * EXYNOS4 MCT configutation
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#ifndef __ASM_ARCH_REGS_MCT_H
14#define __ASM_ARCH_REGS_MCT_H __FILE__
15
16#include <mach/map.h>
17
18#define EXYNOS4_MCTREG(x) (S5P_VA_SYSTIMER + (x))
19
20#define EXYNOS4_MCT_G_CNT_L EXYNOS4_MCTREG(0x100)
21#define EXYNOS4_MCT_G_CNT_U EXYNOS4_MCTREG(0x104)
22#define EXYNOS4_MCT_G_CNT_WSTAT EXYNOS4_MCTREG(0x110)
23
24#define EXYNOS4_MCT_G_COMP0_L EXYNOS4_MCTREG(0x200)
25#define EXYNOS4_MCT_G_COMP0_U EXYNOS4_MCTREG(0x204)
26#define EXYNOS4_MCT_G_COMP0_ADD_INCR EXYNOS4_MCTREG(0x208)
27
28#define EXYNOS4_MCT_G_TCON EXYNOS4_MCTREG(0x240)
29
30#define EXYNOS4_MCT_G_INT_CSTAT EXYNOS4_MCTREG(0x244)
31#define EXYNOS4_MCT_G_INT_ENB EXYNOS4_MCTREG(0x248)
32#define EXYNOS4_MCT_G_WSTAT EXYNOS4_MCTREG(0x24C)
33
34#define _EXYNOS4_MCT_L_BASE EXYNOS4_MCTREG(0x300)
35#define EXYNOS4_MCT_L_BASE(x) (_EXYNOS4_MCT_L_BASE + (0x100 * x))
36#define EXYNOS4_MCT_L_MASK (0xffffff00)
37
38#define MCT_L_TCNTB_OFFSET (0x00)
39#define MCT_L_ICNTB_OFFSET (0x08)
40#define MCT_L_TCON_OFFSET (0x20)
41#define MCT_L_INT_CSTAT_OFFSET (0x30)
42#define MCT_L_INT_ENB_OFFSET (0x34)
43#define MCT_L_WSTAT_OFFSET (0x40)
44
45#define MCT_G_TCON_START (1 << 8)
46#define MCT_G_TCON_COMP0_AUTO_INC (1 << 1)
47#define MCT_G_TCON_COMP0_ENABLE (1 << 0)
48
49#define MCT_L_TCON_INTERVAL_MODE (1 << 2)
50#define MCT_L_TCON_INT_START (1 << 1)
51#define MCT_L_TCON_TIMER_START (1 << 0)
52
53#endif /* __ASM_ARCH_REGS_MCT_H */
diff --git a/arch/arm/mach-exynos/mach-armlex4210.c b/arch/arm/mach-exynos/mach-armlex4210.c
index 685f29173afa..3b1a34742679 100644
--- a/arch/arm/mach-exynos/mach-armlex4210.c
+++ b/arch/arm/mach-exynos/mach-armlex4210.c
@@ -202,6 +202,6 @@ MACHINE_START(ARMLEX4210, "ARMLEX4210")
202 .map_io = armlex4210_map_io, 202 .map_io = armlex4210_map_io,
203 .init_machine = armlex4210_machine_init, 203 .init_machine = armlex4210_machine_init,
204 .init_late = exynos_init_late, 204 .init_late = exynos_init_late,
205 .init_time = exynos4_timer_init, 205 .init_time = mct_init,
206 .restart = exynos4_restart, 206 .restart = exynos4_restart,
207MACHINE_END 207MACHINE_END
diff --git a/arch/arm/mach-exynos/mach-exynos4-dt.c b/arch/arm/mach-exynos/mach-exynos4-dt.c
index 3358088c822a..c4ae108e192d 100644
--- a/arch/arm/mach-exynos/mach-exynos4-dt.c
+++ b/arch/arm/mach-exynos/mach-exynos4-dt.c
@@ -13,6 +13,7 @@
13 13
14#include <linux/of_platform.h> 14#include <linux/of_platform.h>
15#include <linux/serial_core.h> 15#include <linux/serial_core.h>
16#include <linux/clocksource.h>
16 17
17#include <asm/mach/arch.h> 18#include <asm/mach/arch.h>
18#include <mach/map.h> 19#include <mach/map.h>
@@ -142,7 +143,7 @@ DT_MACHINE_START(EXYNOS4210_DT, "Samsung Exynos4 (Flattened Device Tree)")
142 .map_io = exynos4_dt_map_io, 143 .map_io = exynos4_dt_map_io,
143 .init_machine = exynos4_dt_machine_init, 144 .init_machine = exynos4_dt_machine_init,
144 .init_late = exynos_init_late, 145 .init_late = exynos_init_late,
145 .init_time = exynos4_timer_init, 146 .init_time = clocksource_of_init,
146 .dt_compat = exynos4_dt_compat, 147 .dt_compat = exynos4_dt_compat,
147 .restart = exynos4_restart, 148 .restart = exynos4_restart,
148MACHINE_END 149MACHINE_END
diff --git a/arch/arm/mach-exynos/mach-exynos5-dt.c b/arch/arm/mach-exynos/mach-exynos5-dt.c
index acaeb14db54b..be7eaac0df01 100644
--- a/arch/arm/mach-exynos/mach-exynos5-dt.c
+++ b/arch/arm/mach-exynos/mach-exynos5-dt.c
@@ -14,6 +14,7 @@
14#include <linux/serial_core.h> 14#include <linux/serial_core.h>
15#include <linux/memblock.h> 15#include <linux/memblock.h>
16#include <linux/io.h> 16#include <linux/io.h>
17#include <linux/clocksource.h>
17 18
18#include <asm/mach/arch.h> 19#include <asm/mach/arch.h>
19#include <mach/map.h> 20#include <mach/map.h>
@@ -216,7 +217,6 @@ DT_MACHINE_START(EXYNOS5_DT, "SAMSUNG EXYNOS5 (Flattened Device Tree)")
216 .map_io = exynos5_dt_map_io, 217 .map_io = exynos5_dt_map_io,
217 .init_machine = exynos5_dt_machine_init, 218 .init_machine = exynos5_dt_machine_init,
218 .init_late = exynos_init_late, 219 .init_late = exynos_init_late,
219 .init_time = exynos4_timer_init,
220 .dt_compat = exynos5_dt_compat, 220 .dt_compat = exynos5_dt_compat,
221 .restart = exynos5_restart, 221 .restart = exynos5_restart,
222 .reserve = exynos5_reserve, 222 .reserve = exynos5_reserve,
diff --git a/arch/arm/mach-exynos/mach-nuri.c b/arch/arm/mach-exynos/mach-nuri.c
index 1ea79730187f..da3605d15110 100644
--- a/arch/arm/mach-exynos/mach-nuri.c
+++ b/arch/arm/mach-exynos/mach-nuri.c
@@ -1380,7 +1380,7 @@ MACHINE_START(NURI, "NURI")
1380 .map_io = nuri_map_io, 1380 .map_io = nuri_map_io,
1381 .init_machine = nuri_machine_init, 1381 .init_machine = nuri_machine_init,
1382 .init_late = exynos_init_late, 1382 .init_late = exynos_init_late,
1383 .init_time = exynos4_timer_init, 1383 .init_time = mct_init,
1384 .reserve = &nuri_reserve, 1384 .reserve = &nuri_reserve,
1385 .restart = exynos4_restart, 1385 .restart = exynos4_restart,
1386MACHINE_END 1386MACHINE_END
diff --git a/arch/arm/mach-exynos/mach-origen.c b/arch/arm/mach-exynos/mach-origen.c
index 579d2d171daa..1772cd284f4c 100644
--- a/arch/arm/mach-exynos/mach-origen.c
+++ b/arch/arm/mach-exynos/mach-origen.c
@@ -815,7 +815,7 @@ MACHINE_START(ORIGEN, "ORIGEN")
815 .map_io = origen_map_io, 815 .map_io = origen_map_io,
816 .init_machine = origen_machine_init, 816 .init_machine = origen_machine_init,
817 .init_late = exynos_init_late, 817 .init_late = exynos_init_late,
818 .init_time = exynos4_timer_init, 818 .init_time = mct_init,
819 .reserve = &origen_reserve, 819 .reserve = &origen_reserve,
820 .restart = exynos4_restart, 820 .restart = exynos4_restart,
821MACHINE_END 821MACHINE_END
diff --git a/arch/arm/mach-exynos/mach-smdk4x12.c b/arch/arm/mach-exynos/mach-smdk4x12.c
index fe6149624b84..34a6356364eb 100644
--- a/arch/arm/mach-exynos/mach-smdk4x12.c
+++ b/arch/arm/mach-exynos/mach-smdk4x12.c
@@ -376,7 +376,7 @@ MACHINE_START(SMDK4212, "SMDK4212")
376 .init_irq = exynos4_init_irq, 376 .init_irq = exynos4_init_irq,
377 .map_io = smdk4x12_map_io, 377 .map_io = smdk4x12_map_io,
378 .init_machine = smdk4x12_machine_init, 378 .init_machine = smdk4x12_machine_init,
379 .init_time = exynos4_timer_init, 379 .init_time = mct_init,
380 .restart = exynos4_restart, 380 .restart = exynos4_restart,
381 .reserve = &smdk4x12_reserve, 381 .reserve = &smdk4x12_reserve,
382MACHINE_END 382MACHINE_END
@@ -390,7 +390,7 @@ MACHINE_START(SMDK4412, "SMDK4412")
390 .map_io = smdk4x12_map_io, 390 .map_io = smdk4x12_map_io,
391 .init_machine = smdk4x12_machine_init, 391 .init_machine = smdk4x12_machine_init,
392 .init_late = exynos_init_late, 392 .init_late = exynos_init_late,
393 .init_time = exynos4_timer_init, 393 .init_time = mct_init,
394 .restart = exynos4_restart, 394 .restart = exynos4_restart,
395 .reserve = &smdk4x12_reserve, 395 .reserve = &smdk4x12_reserve,
396MACHINE_END 396MACHINE_END
diff --git a/arch/arm/mach-exynos/mach-smdkv310.c b/arch/arm/mach-exynos/mach-smdkv310.c
index d71672922b19..893b14e8c62a 100644
--- a/arch/arm/mach-exynos/mach-smdkv310.c
+++ b/arch/arm/mach-exynos/mach-smdkv310.c
@@ -423,7 +423,7 @@ MACHINE_START(SMDKV310, "SMDKV310")
423 .init_irq = exynos4_init_irq, 423 .init_irq = exynos4_init_irq,
424 .map_io = smdkv310_map_io, 424 .map_io = smdkv310_map_io,
425 .init_machine = smdkv310_machine_init, 425 .init_machine = smdkv310_machine_init,
426 .init_time = exynos4_timer_init, 426 .init_time = mct_init,
427 .reserve = &smdkv310_reserve, 427 .reserve = &smdkv310_reserve,
428 .restart = exynos4_restart, 428 .restart = exynos4_restart,
429MACHINE_END 429MACHINE_END
@@ -436,7 +436,7 @@ MACHINE_START(SMDKC210, "SMDKC210")
436 .map_io = smdkv310_map_io, 436 .map_io = smdkv310_map_io,
437 .init_machine = smdkv310_machine_init, 437 .init_machine = smdkv310_machine_init,
438 .init_late = exynos_init_late, 438 .init_late = exynos_init_late,
439 .init_time = exynos4_timer_init, 439 .init_time = mct_init,
440 .reserve = &smdkv310_reserve, 440 .reserve = &smdkv310_reserve,
441 .restart = exynos4_restart, 441 .restart = exynos4_restart,
442MACHINE_END 442MACHINE_END
diff --git a/arch/arm/mach-exynos/mach-universal_c210.c b/arch/arm/mach-exynos/mach-universal_c210.c
index 497fcb793dc1..c870b0aaa5e0 100644
--- a/arch/arm/mach-exynos/mach-universal_c210.c
+++ b/arch/arm/mach-exynos/mach-universal_c210.c
@@ -41,7 +41,7 @@
41#include <plat/mfc.h> 41#include <plat/mfc.h>
42#include <plat/sdhci.h> 42#include <plat/sdhci.h>
43#include <plat/fimc-core.h> 43#include <plat/fimc-core.h>
44#include <plat/s5p-time.h> 44#include <plat/samsung-time.h>
45#include <plat/camport.h> 45#include <plat/camport.h>
46 46
47#include <mach/map.h> 47#include <mach/map.h>
@@ -1094,7 +1094,7 @@ static void __init universal_map_io(void)
1094 exynos_init_io(NULL, 0); 1094 exynos_init_io(NULL, 0);
1095 s3c24xx_init_clocks(clk_xusbxti.rate); 1095 s3c24xx_init_clocks(clk_xusbxti.rate);
1096 s3c24xx_init_uarts(universal_uartcfgs, ARRAY_SIZE(universal_uartcfgs)); 1096 s3c24xx_init_uarts(universal_uartcfgs, ARRAY_SIZE(universal_uartcfgs));
1097 s5p_set_timer_source(S5P_PWM2, S5P_PWM4); 1097 samsung_set_timer_source(SAMSUNG_PWM2, SAMSUNG_PWM4);
1098} 1098}
1099 1099
1100static void s5p_tv_setup(void) 1100static void s5p_tv_setup(void)
@@ -1152,7 +1152,7 @@ MACHINE_START(UNIVERSAL_C210, "UNIVERSAL_C210")
1152 .map_io = universal_map_io, 1152 .map_io = universal_map_io,
1153 .init_machine = universal_machine_init, 1153 .init_machine = universal_machine_init,
1154 .init_late = exynos_init_late, 1154 .init_late = exynos_init_late,
1155 .init_time = s5p_timer_init, 1155 .init_time = samsung_timer_init,
1156 .reserve = &universal_reserve, 1156 .reserve = &universal_reserve,
1157 .restart = exynos4_restart, 1157 .restart = exynos4_restart,
1158MACHINE_END 1158MACHINE_END
diff --git a/arch/arm/mach-exynos/mct.c b/arch/arm/mach-exynos/mct.c
deleted file mode 100644
index c9d6650f9b5d..000000000000
--- a/arch/arm/mach-exynos/mct.c
+++ /dev/null
@@ -1,485 +0,0 @@
1/* linux/arch/arm/mach-exynos4/mct.c
2 *
3 * Copyright (c) 2011 Samsung Electronics Co., Ltd.
4 * http://www.samsung.com
5 *
6 * EXYNOS4 MCT(Multi-Core Timer) support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#include <linux/sched.h>
14#include <linux/interrupt.h>
15#include <linux/irq.h>
16#include <linux/err.h>
17#include <linux/clk.h>
18#include <linux/clockchips.h>
19#include <linux/platform_device.h>
20#include <linux/delay.h>
21#include <linux/percpu.h>
22#include <linux/of.h>
23
24#include <asm/arch_timer.h>
25#include <asm/localtimer.h>
26
27#include <plat/cpu.h>
28
29#include <mach/map.h>
30#include <mach/irqs.h>
31#include <mach/regs-mct.h>
32#include <asm/mach/time.h>
33
34#define TICK_BASE_CNT 1
35
36enum {
37 MCT_INT_SPI,
38 MCT_INT_PPI
39};
40
41static unsigned long clk_rate;
42static unsigned int mct_int_type;
43
44struct mct_clock_event_device {
45 struct clock_event_device *evt;
46 void __iomem *base;
47 char name[10];
48};
49
50static void exynos4_mct_write(unsigned int value, void *addr)
51{
52 void __iomem *stat_addr;
53 u32 mask;
54 u32 i;
55
56 __raw_writel(value, addr);
57
58 if (likely(addr >= EXYNOS4_MCT_L_BASE(0))) {
59 u32 base = (u32) addr & EXYNOS4_MCT_L_MASK;
60 switch ((u32) addr & ~EXYNOS4_MCT_L_MASK) {
61 case (u32) MCT_L_TCON_OFFSET:
62 stat_addr = (void __iomem *) base + MCT_L_WSTAT_OFFSET;
63 mask = 1 << 3; /* L_TCON write status */
64 break;
65 case (u32) MCT_L_ICNTB_OFFSET:
66 stat_addr = (void __iomem *) base + MCT_L_WSTAT_OFFSET;
67 mask = 1 << 1; /* L_ICNTB write status */
68 break;
69 case (u32) MCT_L_TCNTB_OFFSET:
70 stat_addr = (void __iomem *) base + MCT_L_WSTAT_OFFSET;
71 mask = 1 << 0; /* L_TCNTB write status */
72 break;
73 default:
74 return;
75 }
76 } else {
77 switch ((u32) addr) {
78 case (u32) EXYNOS4_MCT_G_TCON:
79 stat_addr = EXYNOS4_MCT_G_WSTAT;
80 mask = 1 << 16; /* G_TCON write status */
81 break;
82 case (u32) EXYNOS4_MCT_G_COMP0_L:
83 stat_addr = EXYNOS4_MCT_G_WSTAT;
84 mask = 1 << 0; /* G_COMP0_L write status */
85 break;
86 case (u32) EXYNOS4_MCT_G_COMP0_U:
87 stat_addr = EXYNOS4_MCT_G_WSTAT;
88 mask = 1 << 1; /* G_COMP0_U write status */
89 break;
90 case (u32) EXYNOS4_MCT_G_COMP0_ADD_INCR:
91 stat_addr = EXYNOS4_MCT_G_WSTAT;
92 mask = 1 << 2; /* G_COMP0_ADD_INCR w status */
93 break;
94 case (u32) EXYNOS4_MCT_G_CNT_L:
95 stat_addr = EXYNOS4_MCT_G_CNT_WSTAT;
96 mask = 1 << 0; /* G_CNT_L write status */
97 break;
98 case (u32) EXYNOS4_MCT_G_CNT_U:
99 stat_addr = EXYNOS4_MCT_G_CNT_WSTAT;
100 mask = 1 << 1; /* G_CNT_U write status */
101 break;
102 default:
103 return;
104 }
105 }
106
107 /* Wait maximum 1 ms until written values are applied */
108 for (i = 0; i < loops_per_jiffy / 1000 * HZ; i++)
109 if (__raw_readl(stat_addr) & mask) {
110 __raw_writel(mask, stat_addr);
111 return;
112 }
113
114 panic("MCT hangs after writing %d (addr:0x%08x)\n", value, (u32)addr);
115}
116
117/* Clocksource handling */
118static void exynos4_mct_frc_start(u32 hi, u32 lo)
119{
120 u32 reg;
121
122 exynos4_mct_write(lo, EXYNOS4_MCT_G_CNT_L);
123 exynos4_mct_write(hi, EXYNOS4_MCT_G_CNT_U);
124
125 reg = __raw_readl(EXYNOS4_MCT_G_TCON);
126 reg |= MCT_G_TCON_START;
127 exynos4_mct_write(reg, EXYNOS4_MCT_G_TCON);
128}
129
130static cycle_t exynos4_frc_read(struct clocksource *cs)
131{
132 unsigned int lo, hi;
133 u32 hi2 = __raw_readl(EXYNOS4_MCT_G_CNT_U);
134
135 do {
136 hi = hi2;
137 lo = __raw_readl(EXYNOS4_MCT_G_CNT_L);
138 hi2 = __raw_readl(EXYNOS4_MCT_G_CNT_U);
139 } while (hi != hi2);
140
141 return ((cycle_t)hi << 32) | lo;
142}
143
144static void exynos4_frc_resume(struct clocksource *cs)
145{
146 exynos4_mct_frc_start(0, 0);
147}
148
149struct clocksource mct_frc = {
150 .name = "mct-frc",
151 .rating = 400,
152 .read = exynos4_frc_read,
153 .mask = CLOCKSOURCE_MASK(64),
154 .flags = CLOCK_SOURCE_IS_CONTINUOUS,
155 .resume = exynos4_frc_resume,
156};
157
158static void __init exynos4_clocksource_init(void)
159{
160 exynos4_mct_frc_start(0, 0);
161
162 if (clocksource_register_hz(&mct_frc, clk_rate))
163 panic("%s: can't register clocksource\n", mct_frc.name);
164}
165
166static void exynos4_mct_comp0_stop(void)
167{
168 unsigned int tcon;
169
170 tcon = __raw_readl(EXYNOS4_MCT_G_TCON);
171 tcon &= ~(MCT_G_TCON_COMP0_ENABLE | MCT_G_TCON_COMP0_AUTO_INC);
172
173 exynos4_mct_write(tcon, EXYNOS4_MCT_G_TCON);
174 exynos4_mct_write(0, EXYNOS4_MCT_G_INT_ENB);
175}
176
177static void exynos4_mct_comp0_start(enum clock_event_mode mode,
178 unsigned long cycles)
179{
180 unsigned int tcon;
181 cycle_t comp_cycle;
182
183 tcon = __raw_readl(EXYNOS4_MCT_G_TCON);
184
185 if (mode == CLOCK_EVT_MODE_PERIODIC) {
186 tcon |= MCT_G_TCON_COMP0_AUTO_INC;
187 exynos4_mct_write(cycles, EXYNOS4_MCT_G_COMP0_ADD_INCR);
188 }
189
190 comp_cycle = exynos4_frc_read(&mct_frc) + cycles;
191 exynos4_mct_write((u32)comp_cycle, EXYNOS4_MCT_G_COMP0_L);
192 exynos4_mct_write((u32)(comp_cycle >> 32), EXYNOS4_MCT_G_COMP0_U);
193
194 exynos4_mct_write(0x1, EXYNOS4_MCT_G_INT_ENB);
195
196 tcon |= MCT_G_TCON_COMP0_ENABLE;
197 exynos4_mct_write(tcon , EXYNOS4_MCT_G_TCON);
198}
199
200static int exynos4_comp_set_next_event(unsigned long cycles,
201 struct clock_event_device *evt)
202{
203 exynos4_mct_comp0_start(evt->mode, cycles);
204
205 return 0;
206}
207
208static void exynos4_comp_set_mode(enum clock_event_mode mode,
209 struct clock_event_device *evt)
210{
211 unsigned long cycles_per_jiffy;
212 exynos4_mct_comp0_stop();
213
214 switch (mode) {
215 case CLOCK_EVT_MODE_PERIODIC:
216 cycles_per_jiffy =
217 (((unsigned long long) NSEC_PER_SEC / HZ * evt->mult) >> evt->shift);
218 exynos4_mct_comp0_start(mode, cycles_per_jiffy);
219 break;
220
221 case CLOCK_EVT_MODE_ONESHOT:
222 case CLOCK_EVT_MODE_UNUSED:
223 case CLOCK_EVT_MODE_SHUTDOWN:
224 case CLOCK_EVT_MODE_RESUME:
225 break;
226 }
227}
228
229static struct clock_event_device mct_comp_device = {
230 .name = "mct-comp",
231 .features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT,
232 .rating = 250,
233 .set_next_event = exynos4_comp_set_next_event,
234 .set_mode = exynos4_comp_set_mode,
235};
236
237static irqreturn_t exynos4_mct_comp_isr(int irq, void *dev_id)
238{
239 struct clock_event_device *evt = dev_id;
240
241 exynos4_mct_write(0x1, EXYNOS4_MCT_G_INT_CSTAT);
242
243 evt->event_handler(evt);
244
245 return IRQ_HANDLED;
246}
247
248static struct irqaction mct_comp_event_irq = {
249 .name = "mct_comp_irq",
250 .flags = IRQF_TIMER | IRQF_IRQPOLL,
251 .handler = exynos4_mct_comp_isr,
252 .dev_id = &mct_comp_device,
253};
254
255static void exynos4_clockevent_init(void)
256{
257 mct_comp_device.cpumask = cpumask_of(0);
258 clockevents_config_and_register(&mct_comp_device, clk_rate,
259 0xf, 0xffffffff);
260
261 if (soc_is_exynos5250())
262 setup_irq(EXYNOS5_IRQ_MCT_G0, &mct_comp_event_irq);
263 else
264 setup_irq(EXYNOS4_IRQ_MCT_G0, &mct_comp_event_irq);
265}
266
267#ifdef CONFIG_LOCAL_TIMERS
268
269static DEFINE_PER_CPU(struct mct_clock_event_device, percpu_mct_tick);
270
271/* Clock event handling */
272static void exynos4_mct_tick_stop(struct mct_clock_event_device *mevt)
273{
274 unsigned long tmp;
275 unsigned long mask = MCT_L_TCON_INT_START | MCT_L_TCON_TIMER_START;
276 void __iomem *addr = mevt->base + MCT_L_TCON_OFFSET;
277
278 tmp = __raw_readl(addr);
279 if (tmp & mask) {
280 tmp &= ~mask;
281 exynos4_mct_write(tmp, addr);
282 }
283}
284
285static void exynos4_mct_tick_start(unsigned long cycles,
286 struct mct_clock_event_device *mevt)
287{
288 unsigned long tmp;
289
290 exynos4_mct_tick_stop(mevt);
291
292 tmp = (1 << 31) | cycles; /* MCT_L_UPDATE_ICNTB */
293
294 /* update interrupt count buffer */
295 exynos4_mct_write(tmp, mevt->base + MCT_L_ICNTB_OFFSET);
296
297 /* enable MCT tick interrupt */
298 exynos4_mct_write(0x1, mevt->base + MCT_L_INT_ENB_OFFSET);
299
300 tmp = __raw_readl(mevt->base + MCT_L_TCON_OFFSET);
301 tmp |= MCT_L_TCON_INT_START | MCT_L_TCON_TIMER_START |
302 MCT_L_TCON_INTERVAL_MODE;
303 exynos4_mct_write(tmp, mevt->base + MCT_L_TCON_OFFSET);
304}
305
306static int exynos4_tick_set_next_event(unsigned long cycles,
307 struct clock_event_device *evt)
308{
309 struct mct_clock_event_device *mevt = this_cpu_ptr(&percpu_mct_tick);
310
311 exynos4_mct_tick_start(cycles, mevt);
312
313 return 0;
314}
315
316static inline void exynos4_tick_set_mode(enum clock_event_mode mode,
317 struct clock_event_device *evt)
318{
319 struct mct_clock_event_device *mevt = this_cpu_ptr(&percpu_mct_tick);
320 unsigned long cycles_per_jiffy;
321
322 exynos4_mct_tick_stop(mevt);
323
324 switch (mode) {
325 case CLOCK_EVT_MODE_PERIODIC:
326 cycles_per_jiffy =
327 (((unsigned long long) NSEC_PER_SEC / HZ * evt->mult) >> evt->shift);
328 exynos4_mct_tick_start(cycles_per_jiffy, mevt);
329 break;
330
331 case CLOCK_EVT_MODE_ONESHOT:
332 case CLOCK_EVT_MODE_UNUSED:
333 case CLOCK_EVT_MODE_SHUTDOWN:
334 case CLOCK_EVT_MODE_RESUME:
335 break;
336 }
337}
338
339static int exynos4_mct_tick_clear(struct mct_clock_event_device *mevt)
340{
341 struct clock_event_device *evt = mevt->evt;
342
343 /*
344 * This is for supporting oneshot mode.
345 * Mct would generate interrupt periodically
346 * without explicit stopping.
347 */
348 if (evt->mode != CLOCK_EVT_MODE_PERIODIC)
349 exynos4_mct_tick_stop(mevt);
350
351 /* Clear the MCT tick interrupt */
352 if (__raw_readl(mevt->base + MCT_L_INT_CSTAT_OFFSET) & 1) {
353 exynos4_mct_write(0x1, mevt->base + MCT_L_INT_CSTAT_OFFSET);
354 return 1;
355 } else {
356 return 0;
357 }
358}
359
360static irqreturn_t exynos4_mct_tick_isr(int irq, void *dev_id)
361{
362 struct mct_clock_event_device *mevt = dev_id;
363 struct clock_event_device *evt = mevt->evt;
364
365 exynos4_mct_tick_clear(mevt);
366
367 evt->event_handler(evt);
368
369 return IRQ_HANDLED;
370}
371
372static struct irqaction mct_tick0_event_irq = {
373 .name = "mct_tick0_irq",
374 .flags = IRQF_TIMER | IRQF_NOBALANCING,
375 .handler = exynos4_mct_tick_isr,
376};
377
378static struct irqaction mct_tick1_event_irq = {
379 .name = "mct_tick1_irq",
380 .flags = IRQF_TIMER | IRQF_NOBALANCING,
381 .handler = exynos4_mct_tick_isr,
382};
383
384static int __cpuinit exynos4_local_timer_setup(struct clock_event_device *evt)
385{
386 struct mct_clock_event_device *mevt;
387 unsigned int cpu = smp_processor_id();
388 int mct_lx_irq;
389
390 mevt = this_cpu_ptr(&percpu_mct_tick);
391 mevt->evt = evt;
392
393 mevt->base = EXYNOS4_MCT_L_BASE(cpu);
394 sprintf(mevt->name, "mct_tick%d", cpu);
395
396 evt->name = mevt->name;
397 evt->cpumask = cpumask_of(cpu);
398 evt->set_next_event = exynos4_tick_set_next_event;
399 evt->set_mode = exynos4_tick_set_mode;
400 evt->features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT;
401 evt->rating = 450;
402 clockevents_config_and_register(evt, clk_rate / (TICK_BASE_CNT + 1),
403 0xf, 0x7fffffff);
404
405 exynos4_mct_write(TICK_BASE_CNT, mevt->base + MCT_L_TCNTB_OFFSET);
406
407 if (mct_int_type == MCT_INT_SPI) {
408 if (cpu == 0) {
409 mct_lx_irq = soc_is_exynos4210() ? EXYNOS4_IRQ_MCT_L0 :
410 EXYNOS5_IRQ_MCT_L0;
411 mct_tick0_event_irq.dev_id = mevt;
412 evt->irq = mct_lx_irq;
413 setup_irq(mct_lx_irq, &mct_tick0_event_irq);
414 } else {
415 mct_lx_irq = soc_is_exynos4210() ? EXYNOS4_IRQ_MCT_L1 :
416 EXYNOS5_IRQ_MCT_L1;
417 mct_tick1_event_irq.dev_id = mevt;
418 evt->irq = mct_lx_irq;
419 setup_irq(mct_lx_irq, &mct_tick1_event_irq);
420 irq_set_affinity(mct_lx_irq, cpumask_of(1));
421 }
422 } else {
423 enable_percpu_irq(EXYNOS_IRQ_MCT_LOCALTIMER, 0);
424 }
425
426 return 0;
427}
428
429static void exynos4_local_timer_stop(struct clock_event_device *evt)
430{
431 unsigned int cpu = smp_processor_id();
432 evt->set_mode(CLOCK_EVT_MODE_UNUSED, evt);
433 if (mct_int_type == MCT_INT_SPI)
434 if (cpu == 0)
435 remove_irq(evt->irq, &mct_tick0_event_irq);
436 else
437 remove_irq(evt->irq, &mct_tick1_event_irq);
438 else
439 disable_percpu_irq(EXYNOS_IRQ_MCT_LOCALTIMER);
440}
441
442static struct local_timer_ops exynos4_mct_tick_ops __cpuinitdata = {
443 .setup = exynos4_local_timer_setup,
444 .stop = exynos4_local_timer_stop,
445};
446#endif /* CONFIG_LOCAL_TIMERS */
447
448static void __init exynos4_timer_resources(void)
449{
450 struct clk *mct_clk;
451 mct_clk = clk_get(NULL, "xtal");
452
453 clk_rate = clk_get_rate(mct_clk);
454
455#ifdef CONFIG_LOCAL_TIMERS
456 if (mct_int_type == MCT_INT_PPI) {
457 int err;
458
459 err = request_percpu_irq(EXYNOS_IRQ_MCT_LOCALTIMER,
460 exynos4_mct_tick_isr, "MCT",
461 &percpu_mct_tick);
462 WARN(err, "MCT: can't request IRQ %d (%d)\n",
463 EXYNOS_IRQ_MCT_LOCALTIMER, err);
464 }
465
466 local_timer_register(&exynos4_mct_tick_ops);
467#endif /* CONFIG_LOCAL_TIMERS */
468}
469
470void __init exynos4_timer_init(void)
471{
472 if (soc_is_exynos5440()) {
473 arch_timer_of_register();
474 return;
475 }
476
477 if ((soc_is_exynos4210()) || (soc_is_exynos5250()))
478 mct_int_type = MCT_INT_SPI;
479 else
480 mct_int_type = MCT_INT_PPI;
481
482 exynos4_timer_resources();
483 exynos4_clocksource_init();
484 exynos4_clockevent_init();
485}
diff --git a/arch/arm/mach-highbank/highbank.c b/arch/arm/mach-highbank/highbank.c
index a4f9f50247d4..e7df2dd43a40 100644
--- a/arch/arm/mach-highbank/highbank.c
+++ b/arch/arm/mach-highbank/highbank.c
@@ -15,6 +15,7 @@
15 */ 15 */
16#include <linux/clk.h> 16#include <linux/clk.h>
17#include <linux/clkdev.h> 17#include <linux/clkdev.h>
18#include <linux/clocksource.h>
18#include <linux/dma-mapping.h> 19#include <linux/dma-mapping.h>
19#include <linux/io.h> 20#include <linux/io.h>
20#include <linux/irq.h> 21#include <linux/irq.h>
@@ -28,13 +29,9 @@
28#include <linux/amba/bus.h> 29#include <linux/amba/bus.h>
29#include <linux/clk-provider.h> 30#include <linux/clk-provider.h>
30 31
31#include <asm/arch_timer.h>
32#include <asm/cacheflush.h> 32#include <asm/cacheflush.h>
33#include <asm/cputype.h> 33#include <asm/cputype.h>
34#include <asm/smp_plat.h> 34#include <asm/smp_plat.h>
35#include <asm/smp_twd.h>
36#include <asm/hardware/arm_timer.h>
37#include <asm/hardware/timer-sp.h>
38#include <asm/hardware/cache-l2x0.h> 35#include <asm/hardware/cache-l2x0.h>
39#include <asm/mach/arch.h> 36#include <asm/mach/arch.h>
40#include <asm/mach/map.h> 37#include <asm/mach/map.h>
@@ -91,38 +88,18 @@ static void __init highbank_init_irq(void)
91#endif 88#endif
92} 89}
93 90
94static struct clk_lookup lookup = {
95 .dev_id = "sp804",
96 .con_id = NULL,
97};
98
99static void __init highbank_timer_init(void) 91static void __init highbank_timer_init(void)
100{ 92{
101 int irq;
102 struct device_node *np; 93 struct device_node *np;
103 void __iomem *timer_base;
104 94
105 /* Map system registers */ 95 /* Map system registers */
106 np = of_find_compatible_node(NULL, NULL, "calxeda,hb-sregs"); 96 np = of_find_compatible_node(NULL, NULL, "calxeda,hb-sregs");
107 sregs_base = of_iomap(np, 0); 97 sregs_base = of_iomap(np, 0);
108 WARN_ON(!sregs_base); 98 WARN_ON(!sregs_base);
109 99
110 np = of_find_compatible_node(NULL, NULL, "arm,sp804");
111 timer_base = of_iomap(np, 0);
112 WARN_ON(!timer_base);
113 irq = irq_of_parse_and_map(np, 0);
114
115 of_clk_init(NULL); 100 of_clk_init(NULL);
116 lookup.clk = of_clk_get(np, 0);
117 clkdev_add(&lookup);
118
119 sp804_clocksource_and_sched_clock_init(timer_base + 0x20, "timer1");
120 sp804_clockevents_init(timer_base, irq, "timer0");
121
122 twd_local_timer_of_register();
123 101
124 arch_timer_of_register(); 102 clocksource_of_init();
125 arch_timer_sched_clock_init();
126} 103}
127 104
128static void highbank_power_off(void) 105static void highbank_power_off(void)
diff --git a/arch/arm/mach-imx/clk-busy.c b/arch/arm/mach-imx/clk-busy.c
index 1ab91b5209e6..85b728cc27ab 100644
--- a/arch/arm/mach-imx/clk-busy.c
+++ b/arch/arm/mach-imx/clk-busy.c
@@ -169,7 +169,7 @@ struct clk *imx_clk_busy_mux(const char *name, void __iomem *reg, u8 shift,
169 169
170 busy->mux.reg = reg; 170 busy->mux.reg = reg;
171 busy->mux.shift = shift; 171 busy->mux.shift = shift;
172 busy->mux.width = width; 172 busy->mux.mask = BIT(width) - 1;
173 busy->mux.lock = &imx_ccm_lock; 173 busy->mux.lock = &imx_ccm_lock;
174 busy->mux_ops = &clk_mux_ops; 174 busy->mux_ops = &clk_mux_ops;
175 175
diff --git a/arch/arm/mach-imx/mach-imx6q.c b/arch/arm/mach-imx/mach-imx6q.c
index 9ffd103b27e4..b59ddcb57c78 100644
--- a/arch/arm/mach-imx/mach-imx6q.c
+++ b/arch/arm/mach-imx/mach-imx6q.c
@@ -12,6 +12,7 @@
12 12
13#include <linux/clk.h> 13#include <linux/clk.h>
14#include <linux/clkdev.h> 14#include <linux/clkdev.h>
15#include <linux/clocksource.h>
15#include <linux/cpu.h> 16#include <linux/cpu.h>
16#include <linux/delay.h> 17#include <linux/delay.h>
17#include <linux/export.h> 18#include <linux/export.h>
@@ -28,11 +29,9 @@
28#include <linux/regmap.h> 29#include <linux/regmap.h>
29#include <linux/micrel_phy.h> 30#include <linux/micrel_phy.h>
30#include <linux/mfd/syscon.h> 31#include <linux/mfd/syscon.h>
31#include <asm/smp_twd.h>
32#include <asm/hardware/cache-l2x0.h> 32#include <asm/hardware/cache-l2x0.h>
33#include <asm/mach/arch.h> 33#include <asm/mach/arch.h>
34#include <asm/mach/map.h> 34#include <asm/mach/map.h>
35#include <asm/mach/time.h>
36#include <asm/system_misc.h> 35#include <asm/system_misc.h>
37 36
38#include "common.h" 37#include "common.h"
@@ -292,7 +291,7 @@ static void __init imx6q_init_irq(void)
292static void __init imx6q_timer_init(void) 291static void __init imx6q_timer_init(void)
293{ 292{
294 mx6q_clocks_init(); 293 mx6q_clocks_init();
295 twd_local_timer_of_register(); 294 clocksource_of_init();
296 imx_print_silicon_rev("i.MX6Q", imx6q_revision()); 295 imx_print_silicon_rev("i.MX6Q", imx6q_revision());
297} 296}
298 297
diff --git a/arch/arm/mach-integrator/integrator_ap.c b/arch/arm/mach-integrator/integrator_ap.c
index ea961445e0e9..b23c8e4f28e8 100644
--- a/arch/arm/mach-integrator/integrator_ap.c
+++ b/arch/arm/mach-integrator/integrator_ap.c
@@ -536,16 +536,14 @@ static void __init ap_init_of(void)
536 'A' + (ap_sc_id & 0x0f)); 536 'A' + (ap_sc_id & 0x0f));
537 537
538 soc_dev = soc_device_register(soc_dev_attr); 538 soc_dev = soc_device_register(soc_dev_attr);
539 if (IS_ERR_OR_NULL(soc_dev)) { 539 if (IS_ERR(soc_dev)) {
540 kfree(soc_dev_attr->revision); 540 kfree(soc_dev_attr->revision);
541 kfree(soc_dev_attr); 541 kfree(soc_dev_attr);
542 return; 542 return;
543 } 543 }
544 544
545 parent = soc_device_to_device(soc_dev); 545 parent = soc_device_to_device(soc_dev);
546 546 integrator_init_sysfs(parent, ap_sc_id);
547 if (!IS_ERR_OR_NULL(parent))
548 integrator_init_sysfs(parent, ap_sc_id);
549 547
550 of_platform_populate(root, of_default_bus_match_table, 548 of_platform_populate(root, of_default_bus_match_table,
551 ap_auxdata_lookup, parent); 549 ap_auxdata_lookup, parent);
diff --git a/arch/arm/mach-integrator/integrator_cp.c b/arch/arm/mach-integrator/integrator_cp.c
index 2b0db82a5381..8c60fcb08a98 100644
--- a/arch/arm/mach-integrator/integrator_cp.c
+++ b/arch/arm/mach-integrator/integrator_cp.c
@@ -250,39 +250,6 @@ static void __init intcp_init_early(void)
250} 250}
251 251
252#ifdef CONFIG_OF 252#ifdef CONFIG_OF
253
254static void __init cp_of_timer_init(void)
255{
256 struct device_node *node;
257 const char *path;
258 void __iomem *base;
259 int err;
260 int irq;
261
262 err = of_property_read_string(of_aliases,
263 "arm,timer-primary", &path);
264 if (WARN_ON(err))
265 return;
266 node = of_find_node_by_path(path);
267 base = of_iomap(node, 0);
268 if (WARN_ON(!base))
269 return;
270 writel(0, base + TIMER_CTRL);
271 sp804_clocksource_init(base, node->name);
272
273 err = of_property_read_string(of_aliases,
274 "arm,timer-secondary", &path);
275 if (WARN_ON(err))
276 return;
277 node = of_find_node_by_path(path);
278 base = of_iomap(node, 0);
279 if (WARN_ON(!base))
280 return;
281 irq = irq_of_parse_and_map(node, 0);
282 writel(0, base + TIMER_CTRL);
283 sp804_clockevents_init(base, irq, node->name);
284}
285
286static const struct of_device_id fpga_irq_of_match[] __initconst = { 253static const struct of_device_id fpga_irq_of_match[] __initconst = {
287 { .compatible = "arm,versatile-fpga-irq", .data = fpga_irq_of_init, }, 254 { .compatible = "arm,versatile-fpga-irq", .data = fpga_irq_of_init, },
288 { /* Sentinel */ } 255 { /* Sentinel */ }
@@ -360,17 +327,14 @@ static void __init intcp_init_of(void)
360 'A' + (intcp_sc_id & 0x0f)); 327 'A' + (intcp_sc_id & 0x0f));
361 328
362 soc_dev = soc_device_register(soc_dev_attr); 329 soc_dev = soc_device_register(soc_dev_attr);
363 if (IS_ERR_OR_NULL(soc_dev)) { 330 if (IS_ERR(soc_dev)) {
364 kfree(soc_dev_attr->revision); 331 kfree(soc_dev_attr->revision);
365 kfree(soc_dev_attr); 332 kfree(soc_dev_attr);
366 return; 333 return;
367 } 334 }
368 335
369 parent = soc_device_to_device(soc_dev); 336 parent = soc_device_to_device(soc_dev);
370 337 integrator_init_sysfs(parent, intcp_sc_id);
371 if (!IS_ERR_OR_NULL(parent))
372 integrator_init_sysfs(parent, intcp_sc_id);
373
374 of_platform_populate(root, of_default_bus_match_table, 338 of_platform_populate(root, of_default_bus_match_table,
375 intcp_auxdata_lookup, parent); 339 intcp_auxdata_lookup, parent);
376} 340}
@@ -386,7 +350,6 @@ DT_MACHINE_START(INTEGRATOR_CP_DT, "ARM Integrator/CP (Device Tree)")
386 .init_early = intcp_init_early, 350 .init_early = intcp_init_early,
387 .init_irq = intcp_init_irq_of, 351 .init_irq = intcp_init_irq_of,
388 .handle_irq = fpga_handle_irq, 352 .handle_irq = fpga_handle_irq,
389 .init_time = cp_of_timer_init,
390 .init_machine = intcp_init_of, 353 .init_machine = intcp_init_of,
391 .restart = integrator_restart, 354 .restart = integrator_restart,
392 .dt_compat = intcp_dt_board_compat, 355 .dt_compat = intcp_dt_board_compat,
diff --git a/arch/arm/mach-omap2/board-3430sdp.c b/arch/arm/mach-omap2/board-3430sdp.c
index 594c6335496e..23b004afa3f8 100644
--- a/arch/arm/mach-omap2/board-3430sdp.c
+++ b/arch/arm/mach-omap2/board-3430sdp.c
@@ -428,16 +428,23 @@ static void enable_board_wakeup_source(void)
428 OMAP_WAKEUP_EN | OMAP_PIN_INPUT_PULLUP); 428 OMAP_WAKEUP_EN | OMAP_PIN_INPUT_PULLUP);
429} 429}
430 430
431static struct usbhs_phy_data phy_data[] __initdata = {
432 {
433 .port = 1,
434 .reset_gpio = 57,
435 .vcc_gpio = -EINVAL,
436 },
437 {
438 .port = 2,
439 .reset_gpio = 61,
440 .vcc_gpio = -EINVAL,
441 },
442};
443
431static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 444static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
432 445
433 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 446 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
434 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 447 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
435 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
436
437 .phy_reset = true,
438 .reset_gpio_port[0] = 57,
439 .reset_gpio_port[1] = 61,
440 .reset_gpio_port[2] = -EINVAL
441}; 448};
442 449
443#ifdef CONFIG_OMAP_MUX 450#ifdef CONFIG_OMAP_MUX
@@ -589,6 +596,8 @@ static void __init omap_3430sdp_init(void)
589 board_flash_init(sdp_flash_partitions, chip_sel_3430, 0); 596 board_flash_init(sdp_flash_partitions, chip_sel_3430, 0);
590 sdp3430_display_init(); 597 sdp3430_display_init();
591 enable_board_wakeup_source(); 598 enable_board_wakeup_source();
599
600 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
592 usbhs_init(&usbhs_bdata); 601 usbhs_init(&usbhs_bdata);
593} 602}
594 603
diff --git a/arch/arm/mach-omap2/board-3630sdp.c b/arch/arm/mach-omap2/board-3630sdp.c
index 67447bd4564f..20d6d8189240 100644
--- a/arch/arm/mach-omap2/board-3630sdp.c
+++ b/arch/arm/mach-omap2/board-3630sdp.c
@@ -53,16 +53,23 @@ static void enable_board_wakeup_source(void)
53 OMAP_WAKEUP_EN | OMAP_PIN_INPUT_PULLUP); 53 OMAP_WAKEUP_EN | OMAP_PIN_INPUT_PULLUP);
54} 54}
55 55
56static struct usbhs_phy_data phy_data[] __initdata = {
57 {
58 .port = 1,
59 .reset_gpio = 126,
60 .vcc_gpio = -EINVAL,
61 },
62 {
63 .port = 2,
64 .reset_gpio = 61,
65 .vcc_gpio = -EINVAL,
66 },
67};
68
56static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 69static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
57 70
58 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 71 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
59 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 72 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
60 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
61
62 .phy_reset = true,
63 .reset_gpio_port[0] = 126,
64 .reset_gpio_port[1] = 61,
65 .reset_gpio_port[2] = -EINVAL
66}; 73};
67 74
68#ifdef CONFIG_OMAP_MUX 75#ifdef CONFIG_OMAP_MUX
@@ -199,6 +206,8 @@ static void __init omap_sdp_init(void)
199 board_smc91x_init(); 206 board_smc91x_init();
200 board_flash_init(sdp_flash_partitions, chip_sel_sdp, NAND_BUSWIDTH_16); 207 board_flash_init(sdp_flash_partitions, chip_sel_sdp, NAND_BUSWIDTH_16);
201 enable_board_wakeup_source(); 208 enable_board_wakeup_source();
209
210 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
202 usbhs_init(&usbhs_bdata); 211 usbhs_init(&usbhs_bdata);
203} 212}
204 213
diff --git a/arch/arm/mach-omap2/board-am3517crane.c b/arch/arm/mach-omap2/board-am3517crane.c
index 7d3358b2e593..fc53911d0d13 100644
--- a/arch/arm/mach-omap2/board-am3517crane.c
+++ b/arch/arm/mach-omap2/board-am3517crane.c
@@ -47,15 +47,17 @@ static struct omap_board_mux board_mux[] __initdata = {
47}; 47};
48#endif 48#endif
49 49
50static struct usbhs_phy_data phy_data[] __initdata = {
51 {
52 .port = 1,
53 .reset_gpio = GPIO_USB_NRESET,
54 .vcc_gpio = GPIO_USB_POWER,
55 .vcc_polarity = 1,
56 },
57};
58
50static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 59static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
51 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 60 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
52 .port_mode[1] = OMAP_USBHS_PORT_MODE_UNUSED,
53 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
54
55 .phy_reset = true,
56 .reset_gpio_port[0] = GPIO_USB_NRESET,
57 .reset_gpio_port[1] = -EINVAL,
58 .reset_gpio_port[2] = -EINVAL
59}; 61};
60 62
61static struct mtd_partition crane_nand_partitions[] = { 63static struct mtd_partition crane_nand_partitions[] = {
@@ -131,13 +133,7 @@ static void __init am3517_crane_init(void)
131 return; 133 return;
132 } 134 }
133 135
134 ret = gpio_request_one(GPIO_USB_POWER, GPIOF_OUT_INIT_HIGH, 136 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
135 "usb_ehci_enable");
136 if (ret < 0) {
137 pr_err("Can not request GPIO %d\n", GPIO_USB_POWER);
138 return;
139 }
140
141 usbhs_init(&usbhs_bdata); 137 usbhs_init(&usbhs_bdata);
142 am35xx_emac_init(AM35XX_DEFAULT_MDIO_FREQUENCY, 1); 138 am35xx_emac_init(AM35XX_DEFAULT_MDIO_FREQUENCY, 1);
143} 139}
diff --git a/arch/arm/mach-omap2/board-am3517evm.c b/arch/arm/mach-omap2/board-am3517evm.c
index 2b9eb3de7aa6..d63f14b534b5 100644
--- a/arch/arm/mach-omap2/board-am3517evm.c
+++ b/arch/arm/mach-omap2/board-am3517evm.c
@@ -213,6 +213,14 @@ static __init void am3517_evm_mcbsp1_init(void)
213 omap_ctrl_writel(devconf0, OMAP2_CONTROL_DEVCONF0); 213 omap_ctrl_writel(devconf0, OMAP2_CONTROL_DEVCONF0);
214} 214}
215 215
216static struct usbhs_phy_data phy_data[] __initdata = {
217 {
218 .port = 1,
219 .reset_gpio = 57,
220 .vcc_gpio = -EINVAL,
221 },
222};
223
216static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 224static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
217 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 225 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
218#if defined(CONFIG_PANEL_SHARP_LQ043T1DG01) || \ 226#if defined(CONFIG_PANEL_SHARP_LQ043T1DG01) || \
@@ -221,12 +229,6 @@ static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
221#else 229#else
222 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 230 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
223#endif 231#endif
224 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
225
226 .phy_reset = true,
227 .reset_gpio_port[0] = 57,
228 .reset_gpio_port[1] = -EINVAL,
229 .reset_gpio_port[2] = -EINVAL
230}; 232};
231 233
232#ifdef CONFIG_OMAP_MUX 234#ifdef CONFIG_OMAP_MUX
@@ -288,7 +290,6 @@ static struct omap2_hsmmc_info mmc[] = {
288 {} /* Terminator */ 290 {} /* Terminator */
289}; 291};
290 292
291
292static void __init am3517_evm_init(void) 293static void __init am3517_evm_init(void)
293{ 294{
294 omap3_mux_init(board_mux, OMAP_PACKAGE_CBB); 295 omap3_mux_init(board_mux, OMAP_PACKAGE_CBB);
@@ -300,6 +301,8 @@ static void __init am3517_evm_init(void)
300 301
301 /* Configure GPIO for EHCI port */ 302 /* Configure GPIO for EHCI port */
302 omap_mux_init_gpio(57, OMAP_PIN_OUTPUT); 303 omap_mux_init_gpio(57, OMAP_PIN_OUTPUT);
304
305 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
303 usbhs_init(&usbhs_bdata); 306 usbhs_init(&usbhs_bdata);
304 am3517_evm_hecc_init(&am3517_evm_hecc_pdata); 307 am3517_evm_hecc_init(&am3517_evm_hecc_pdata);
305 308
diff --git a/arch/arm/mach-omap2/board-cm-t35.c b/arch/arm/mach-omap2/board-cm-t35.c
index 710e99da266c..ee6218c74807 100644
--- a/arch/arm/mach-omap2/board-cm-t35.c
+++ b/arch/arm/mach-omap2/board-cm-t35.c
@@ -376,15 +376,22 @@ static struct omap2_hsmmc_info mmc[] = {
376 {} /* Terminator */ 376 {} /* Terminator */
377}; 377};
378 378
379static struct usbhs_phy_data phy_data[] __initdata = {
380 {
381 .port = 1,
382 .reset_gpio = OMAP_MAX_GPIO_LINES + 6,
383 .vcc_gpio = -EINVAL,
384 },
385 {
386 .port = 2,
387 .reset_gpio = OMAP_MAX_GPIO_LINES + 7,
388 .vcc_gpio = -EINVAL,
389 },
390};
391
379static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 392static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
380 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 393 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
381 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 394 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
382 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
383
384 .phy_reset = true,
385 .reset_gpio_port[0] = OMAP_MAX_GPIO_LINES + 6,
386 .reset_gpio_port[1] = OMAP_MAX_GPIO_LINES + 7,
387 .reset_gpio_port[2] = -EINVAL
388}; 395};
389 396
390static void __init cm_t35_init_usbh(void) 397static void __init cm_t35_init_usbh(void)
@@ -401,6 +408,7 @@ static void __init cm_t35_init_usbh(void)
401 msleep(1); 408 msleep(1);
402 } 409 }
403 410
411 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
404 usbhs_init(&usbhs_bdata); 412 usbhs_init(&usbhs_bdata);
405} 413}
406 414
diff --git a/arch/arm/mach-omap2/board-cm-t3517.c b/arch/arm/mach-omap2/board-cm-t3517.c
index a66da808cc4a..4eb5e6f2f7f5 100644
--- a/arch/arm/mach-omap2/board-cm-t3517.c
+++ b/arch/arm/mach-omap2/board-cm-t3517.c
@@ -188,15 +188,22 @@ static inline void cm_t3517_init_rtc(void) {}
188#define HSUSB2_RESET_GPIO (147) 188#define HSUSB2_RESET_GPIO (147)
189#define USB_HUB_RESET_GPIO (152) 189#define USB_HUB_RESET_GPIO (152)
190 190
191static struct usbhs_phy_data phy_data[] __initdata = {
192 {
193 .port = 1,
194 .reset_gpio = HSUSB1_RESET_GPIO,
195 .vcc_gpio = -EINVAL,
196 },
197 {
198 .port = 2,
199 .reset_gpio = HSUSB2_RESET_GPIO,
200 .vcc_gpio = -EINVAL,
201 },
202};
203
191static struct usbhs_omap_platform_data cm_t3517_ehci_pdata __initdata = { 204static struct usbhs_omap_platform_data cm_t3517_ehci_pdata __initdata = {
192 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 205 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
193 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 206 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
194 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
195
196 .phy_reset = true,
197 .reset_gpio_port[0] = HSUSB1_RESET_GPIO,
198 .reset_gpio_port[1] = HSUSB2_RESET_GPIO,
199 .reset_gpio_port[2] = -EINVAL,
200}; 207};
201 208
202static int __init cm_t3517_init_usbh(void) 209static int __init cm_t3517_init_usbh(void)
@@ -213,6 +220,7 @@ static int __init cm_t3517_init_usbh(void)
213 msleep(1); 220 msleep(1);
214 } 221 }
215 222
223 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
216 usbhs_init(&cm_t3517_ehci_pdata); 224 usbhs_init(&cm_t3517_ehci_pdata);
217 225
218 return 0; 226 return 0;
@@ -324,6 +332,6 @@ MACHINE_START(CM_T3517, "Compulab CM-T3517")
324 .handle_irq = omap3_intc_handle_irq, 332 .handle_irq = omap3_intc_handle_irq,
325 .init_machine = cm_t3517_init, 333 .init_machine = cm_t3517_init,
326 .init_late = am35xx_init_late, 334 .init_late = am35xx_init_late,
327 .init_time = omap3_gp_gptimer_timer_init, 335 .init_time = omap3_gptimer_timer_init,
328 .restart = omap3xxx_restart, 336 .restart = omap3xxx_restart,
329MACHINE_END 337MACHINE_END
diff --git a/arch/arm/mach-omap2/board-devkit8000.c b/arch/arm/mach-omap2/board-devkit8000.c
index 34944cfdfbd9..576420544178 100644
--- a/arch/arm/mach-omap2/board-devkit8000.c
+++ b/arch/arm/mach-omap2/board-devkit8000.c
@@ -415,15 +415,7 @@ static struct platform_device *devkit8000_devices[] __initdata = {
415}; 415};
416 416
417static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 417static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
418
419 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 418 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
420 .port_mode[1] = OMAP_USBHS_PORT_MODE_UNUSED,
421 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
422
423 .phy_reset = true,
424 .reset_gpio_port[0] = -EINVAL,
425 .reset_gpio_port[1] = -EINVAL,
426 .reset_gpio_port[2] = -EINVAL
427}; 419};
428 420
429#ifdef CONFIG_OMAP_MUX 421#ifdef CONFIG_OMAP_MUX
diff --git a/arch/arm/mach-omap2/board-generic.c b/arch/arm/mach-omap2/board-generic.c
index e54a48060198..78813b397209 100644
--- a/arch/arm/mach-omap2/board-generic.c
+++ b/arch/arm/mach-omap2/board-generic.c
@@ -140,7 +140,7 @@ DT_MACHINE_START(AM33XX_DT, "Generic AM33XX (Flattened Device Tree)")
140 .init_irq = omap_intc_of_init, 140 .init_irq = omap_intc_of_init,
141 .handle_irq = omap3_intc_handle_irq, 141 .handle_irq = omap3_intc_handle_irq,
142 .init_machine = omap_generic_init, 142 .init_machine = omap_generic_init,
143 .init_time = omap3_am33xx_gptimer_timer_init, 143 .init_time = omap3_gptimer_timer_init,
144 .dt_compat = am33xx_boards_compat, 144 .dt_compat = am33xx_boards_compat,
145 .restart = am33xx_restart, 145 .restart = am33xx_restart,
146MACHINE_END 146MACHINE_END
diff --git a/arch/arm/mach-omap2/board-igep0020.c b/arch/arm/mach-omap2/board-igep0020.c
index e979d48270c9..b54562d1235e 100644
--- a/arch/arm/mach-omap2/board-igep0020.c
+++ b/arch/arm/mach-omap2/board-igep0020.c
@@ -527,26 +527,28 @@ static void __init igep_i2c_init(void)
527 omap3_pmic_init("twl4030", &igep_twldata); 527 omap3_pmic_init("twl4030", &igep_twldata);
528} 528}
529 529
530static struct usbhs_phy_data igep2_phy_data[] __initdata = {
531 {
532 .port = 1,
533 .reset_gpio = IGEP2_GPIO_USBH_NRESET,
534 .vcc_gpio = -EINVAL,
535 },
536};
537
538static struct usbhs_phy_data igep3_phy_data[] __initdata = {
539 {
540 .port = 2,
541 .reset_gpio = IGEP3_GPIO_USBH_NRESET,
542 .vcc_gpio = -EINVAL,
543 },
544};
545
530static struct usbhs_omap_platform_data igep2_usbhs_bdata __initdata = { 546static struct usbhs_omap_platform_data igep2_usbhs_bdata __initdata = {
531 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 547 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
532 .port_mode[1] = OMAP_USBHS_PORT_MODE_UNUSED,
533 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
534
535 .phy_reset = true,
536 .reset_gpio_port[0] = IGEP2_GPIO_USBH_NRESET,
537 .reset_gpio_port[1] = -EINVAL,
538 .reset_gpio_port[2] = -EINVAL,
539}; 548};
540 549
541static struct usbhs_omap_platform_data igep3_usbhs_bdata __initdata = { 550static struct usbhs_omap_platform_data igep3_usbhs_bdata __initdata = {
542 .port_mode[0] = OMAP_USBHS_PORT_MODE_UNUSED,
543 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 551 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
544 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
545
546 .phy_reset = true,
547 .reset_gpio_port[0] = -EINVAL,
548 .reset_gpio_port[1] = IGEP3_GPIO_USBH_NRESET,
549 .reset_gpio_port[2] = -EINVAL,
550}; 552};
551 553
552#ifdef CONFIG_OMAP_MUX 554#ifdef CONFIG_OMAP_MUX
@@ -642,8 +644,10 @@ static void __init igep_init(void)
642 if (machine_is_igep0020()) { 644 if (machine_is_igep0020()) {
643 omap_display_init(&igep2_dss_data); 645 omap_display_init(&igep2_dss_data);
644 igep2_init_smsc911x(); 646 igep2_init_smsc911x();
647 usbhs_init_phys(igep2_phy_data, ARRAY_SIZE(igep2_phy_data));
645 usbhs_init(&igep2_usbhs_bdata); 648 usbhs_init(&igep2_usbhs_bdata);
646 } else { 649 } else {
650 usbhs_init_phys(igep3_phy_data, ARRAY_SIZE(igep3_phy_data));
647 usbhs_init(&igep3_usbhs_bdata); 651 usbhs_init(&igep3_usbhs_bdata);
648 } 652 }
649} 653}
diff --git a/arch/arm/mach-omap2/board-omap3beagle.c b/arch/arm/mach-omap2/board-omap3beagle.c
index 0ce91af753fa..6de78605c0af 100644
--- a/arch/arm/mach-omap2/board-omap3beagle.c
+++ b/arch/arm/mach-omap2/board-omap3beagle.c
@@ -33,6 +33,7 @@
33#include <linux/mtd/nand.h> 33#include <linux/mtd/nand.h>
34#include <linux/mmc/host.h> 34#include <linux/mmc/host.h>
35#include <linux/usb/phy.h> 35#include <linux/usb/phy.h>
36#include <linux/usb/nop-usb-xceiv.h>
36 37
37#include <linux/regulator/machine.h> 38#include <linux/regulator/machine.h>
38#include <linux/i2c/twl.h> 39#include <linux/i2c/twl.h>
@@ -277,6 +278,21 @@ static struct regulator_consumer_supply beagle_vsim_supply[] = {
277 278
278static struct gpio_led gpio_leds[]; 279static struct gpio_led gpio_leds[];
279 280
281/* PHY's VCC regulator might be added later, so flag that we need it */
282static struct nop_usb_xceiv_platform_data hsusb2_phy_data = {
283 .needs_vcc = true,
284};
285
286static struct usbhs_phy_data phy_data[] = {
287 {
288 .port = 2,
289 .reset_gpio = 147,
290 .vcc_gpio = -1, /* updated in beagle_twl_gpio_setup */
291 .vcc_polarity = 1, /* updated in beagle_twl_gpio_setup */
292 .platform_data = &hsusb2_phy_data,
293 },
294};
295
280static int beagle_twl_gpio_setup(struct device *dev, 296static int beagle_twl_gpio_setup(struct device *dev,
281 unsigned gpio, unsigned ngpio) 297 unsigned gpio, unsigned ngpio)
282{ 298{
@@ -318,9 +334,11 @@ static int beagle_twl_gpio_setup(struct device *dev,
318 } 334 }
319 dvi_panel.power_down_gpio = beagle_config.dvi_pd_gpio; 335 dvi_panel.power_down_gpio = beagle_config.dvi_pd_gpio;
320 336
321 gpio_request_one(gpio + TWL4030_GPIO_MAX, beagle_config.usb_pwr_level, 337 /* TWL4030_GPIO_MAX i.e. LED_GPO controls HS USB Port 2 power */
322 "nEN_USB_PWR"); 338 phy_data[0].vcc_gpio = gpio + TWL4030_GPIO_MAX;
339 phy_data[0].vcc_polarity = beagle_config.usb_pwr_level;
323 340
341 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
324 return 0; 342 return 0;
325} 343}
326 344
@@ -453,15 +471,7 @@ static struct platform_device *omap3_beagle_devices[] __initdata = {
453}; 471};
454 472
455static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 473static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
456
457 .port_mode[0] = OMAP_USBHS_PORT_MODE_UNUSED,
458 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 474 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
459 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
460
461 .phy_reset = true,
462 .reset_gpio_port[0] = -EINVAL,
463 .reset_gpio_port[1] = 147,
464 .reset_gpio_port[2] = -EINVAL
465}; 475};
466 476
467#ifdef CONFIG_OMAP_MUX 477#ifdef CONFIG_OMAP_MUX
@@ -479,7 +489,7 @@ static int __init beagle_opp_init(void)
479 489
480 /* Initialize the omap3 opp table if not already created. */ 490 /* Initialize the omap3 opp table if not already created. */
481 r = omap3_opp_init(); 491 r = omap3_opp_init();
482 if (IS_ERR_VALUE(r) && (r != -EEXIST)) { 492 if (r < 0 && (r != -EEXIST)) {
483 pr_err("%s: opp default init failed\n", __func__); 493 pr_err("%s: opp default init failed\n", __func__);
484 return r; 494 return r;
485 } 495 }
@@ -543,7 +553,9 @@ static void __init omap3_beagle_init(void)
543 553
544 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb"); 554 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb");
545 usb_musb_init(NULL); 555 usb_musb_init(NULL);
556
546 usbhs_init(&usbhs_bdata); 557 usbhs_init(&usbhs_bdata);
558
547 board_nand_init(omap3beagle_nand_partitions, 559 board_nand_init(omap3beagle_nand_partitions,
548 ARRAY_SIZE(omap3beagle_nand_partitions), NAND_CS, 560 ARRAY_SIZE(omap3beagle_nand_partitions), NAND_CS,
549 NAND_BUSWIDTH_16, NULL); 561 NAND_BUSWIDTH_16, NULL);
diff --git a/arch/arm/mach-omap2/board-omap3evm.c b/arch/arm/mach-omap2/board-omap3evm.c
index 5eecc178f8bf..f76d0de7b406 100644
--- a/arch/arm/mach-omap2/board-omap3evm.c
+++ b/arch/arm/mach-omap2/board-omap3evm.c
@@ -466,7 +466,7 @@ struct wl12xx_platform_data omap3evm_wlan_data __initdata = {
466static struct regulator_consumer_supply omap3evm_vaux2_supplies[] = { 466static struct regulator_consumer_supply omap3evm_vaux2_supplies[] = {
467 REGULATOR_SUPPLY("VDD_CSIPHY1", "omap3isp"), /* OMAP ISP */ 467 REGULATOR_SUPPLY("VDD_CSIPHY1", "omap3isp"), /* OMAP ISP */
468 REGULATOR_SUPPLY("VDD_CSIPHY2", "omap3isp"), /* OMAP ISP */ 468 REGULATOR_SUPPLY("VDD_CSIPHY2", "omap3isp"), /* OMAP ISP */
469 REGULATOR_SUPPLY("hsusb1", "ehci-omap.0"), 469 REGULATOR_SUPPLY("vcc", "nop_usb_xceiv.2"), /* hsusb port 2 */
470 REGULATOR_SUPPLY("vaux2", NULL), 470 REGULATOR_SUPPLY("vaux2", NULL),
471}; 471};
472 472
@@ -509,17 +509,16 @@ static int __init omap3_evm_i2c_init(void)
509 return 0; 509 return 0;
510} 510}
511 511
512static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 512static struct usbhs_phy_data phy_data[] __initdata = {
513 {
514 .port = 2,
515 .reset_gpio = -1, /* set at runtime */
516 .vcc_gpio = -EINVAL,
517 },
518};
513 519
514 .port_mode[0] = OMAP_USBHS_PORT_MODE_UNUSED, 520static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
515 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 521 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
516 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
517
518 .phy_reset = true,
519 /* PHY reset GPIO will be runtime programmed based on EVM version */
520 .reset_gpio_port[0] = -EINVAL,
521 .reset_gpio_port[1] = -EINVAL,
522 .reset_gpio_port[2] = -EINVAL
523}; 522};
524 523
525#ifdef CONFIG_OMAP_MUX 524#ifdef CONFIG_OMAP_MUX
@@ -695,7 +694,7 @@ static void __init omap3_evm_init(void)
695 694
696 /* setup EHCI phy reset config */ 695 /* setup EHCI phy reset config */
697 omap_mux_init_gpio(21, OMAP_PIN_INPUT_PULLUP); 696 omap_mux_init_gpio(21, OMAP_PIN_INPUT_PULLUP);
698 usbhs_bdata.reset_gpio_port[1] = 21; 697 phy_data[0].reset_gpio = 21;
699 698
700 /* EVM REV >= E can supply 500mA with EXTVBUS programming */ 699 /* EVM REV >= E can supply 500mA with EXTVBUS programming */
701 musb_board_data.power = 500; 700 musb_board_data.power = 500;
@@ -703,10 +702,12 @@ static void __init omap3_evm_init(void)
703 } else { 702 } else {
704 /* setup EHCI phy reset on MDC */ 703 /* setup EHCI phy reset on MDC */
705 omap_mux_init_gpio(135, OMAP_PIN_OUTPUT); 704 omap_mux_init_gpio(135, OMAP_PIN_OUTPUT);
706 usbhs_bdata.reset_gpio_port[1] = 135; 705 phy_data[0].reset_gpio = 135;
707 } 706 }
708 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb"); 707 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb");
709 usb_musb_init(&musb_board_data); 708 usb_musb_init(&musb_board_data);
709
710 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
710 usbhs_init(&usbhs_bdata); 711 usbhs_init(&usbhs_bdata);
711 board_nand_init(omap3evm_nand_partitions, 712 board_nand_init(omap3evm_nand_partitions,
712 ARRAY_SIZE(omap3evm_nand_partitions), NAND_CS, 713 ARRAY_SIZE(omap3evm_nand_partitions), NAND_CS,
diff --git a/arch/arm/mach-omap2/board-omap3pandora.c b/arch/arm/mach-omap2/board-omap3pandora.c
index 533180f8bf41..28133d5b4fed 100644
--- a/arch/arm/mach-omap2/board-omap3pandora.c
+++ b/arch/arm/mach-omap2/board-omap3pandora.c
@@ -351,7 +351,7 @@ static struct regulator_consumer_supply pandora_vcc_lcd_supply[] = {
351}; 351};
352 352
353static struct regulator_consumer_supply pandora_usb_phy_supply[] = { 353static struct regulator_consumer_supply pandora_usb_phy_supply[] = {
354 REGULATOR_SUPPLY("hsusb1", "ehci-omap.0"), 354 REGULATOR_SUPPLY("vcc", "nop_usb_xceiv.2"), /* hsusb port 2 */
355}; 355};
356 356
357/* ads7846 on SPI and 2 nub controllers on I2C */ 357/* ads7846 on SPI and 2 nub controllers on I2C */
@@ -566,6 +566,14 @@ fail:
566 printk(KERN_ERR "wl1251 board initialisation failed\n"); 566 printk(KERN_ERR "wl1251 board initialisation failed\n");
567} 567}
568 568
569static struct usbhs_phy_data phy_data[] __initdata = {
570 {
571 .port = 2,
572 .reset_gpio = 16,
573 .vcc_gpio = -EINVAL,
574 },
575};
576
569static struct platform_device *omap3pandora_devices[] __initdata = { 577static struct platform_device *omap3pandora_devices[] __initdata = {
570 &pandora_leds_gpio, 578 &pandora_leds_gpio,
571 &pandora_keys_gpio, 579 &pandora_keys_gpio,
@@ -574,15 +582,7 @@ static struct platform_device *omap3pandora_devices[] __initdata = {
574}; 582};
575 583
576static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 584static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
577
578 .port_mode[0] = OMAP_USBHS_PORT_MODE_UNUSED,
579 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 585 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
580 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
581
582 .phy_reset = true,
583 .reset_gpio_port[0] = -EINVAL,
584 .reset_gpio_port[1] = 16,
585 .reset_gpio_port[2] = -EINVAL
586}; 586};
587 587
588#ifdef CONFIG_OMAP_MUX 588#ifdef CONFIG_OMAP_MUX
@@ -606,7 +606,10 @@ static void __init omap3pandora_init(void)
606 spi_register_board_info(omap3pandora_spi_board_info, 606 spi_register_board_info(omap3pandora_spi_board_info,
607 ARRAY_SIZE(omap3pandora_spi_board_info)); 607 ARRAY_SIZE(omap3pandora_spi_board_info));
608 omap_ads7846_init(1, OMAP3_PANDORA_TS_GPIO, 0, NULL); 608 omap_ads7846_init(1, OMAP3_PANDORA_TS_GPIO, 0, NULL);
609
610 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
609 usbhs_init(&usbhs_bdata); 611 usbhs_init(&usbhs_bdata);
612
610 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb"); 613 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb");
611 usb_musb_init(NULL); 614 usb_musb_init(NULL);
612 gpmc_nand_init(&pandora_nand_data, NULL); 615 gpmc_nand_init(&pandora_nand_data, NULL);
diff --git a/arch/arm/mach-omap2/board-omap3stalker.c b/arch/arm/mach-omap2/board-omap3stalker.c
index 5e63f0758cef..d37e6b187ae4 100644
--- a/arch/arm/mach-omap2/board-omap3stalker.c
+++ b/arch/arm/mach-omap2/board-omap3stalker.c
@@ -346,19 +346,20 @@ static int __init omap3_stalker_i2c_init(void)
346 346
347#define OMAP3_STALKER_TS_GPIO 175 347#define OMAP3_STALKER_TS_GPIO 175
348 348
349static struct usbhs_phy_data phy_data[] __initdata = {
350 {
351 .port = 2,
352 .reset_gpio = 21,
353 .vcc_gpio = -EINVAL,
354 },
355};
356
349static struct platform_device *omap3_stalker_devices[] __initdata = { 357static struct platform_device *omap3_stalker_devices[] __initdata = {
350 &keys_gpio, 358 &keys_gpio,
351}; 359};
352 360
353static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 361static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
354 .port_mode[0] = OMAP_USBHS_PORT_MODE_UNUSED,
355 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 362 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
356 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
357
358 .phy_reset = true,
359 .reset_gpio_port[0] = -EINVAL,
360 .reset_gpio_port[1] = 21,
361 .reset_gpio_port[2] = -EINVAL,
362}; 363};
363 364
364#ifdef CONFIG_OMAP_MUX 365#ifdef CONFIG_OMAP_MUX
@@ -395,6 +396,8 @@ static void __init omap3_stalker_init(void)
395 omap_sdrc_init(mt46h32m32lf6_sdrc_params, NULL); 396 omap_sdrc_init(mt46h32m32lf6_sdrc_params, NULL);
396 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb"); 397 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb");
397 usb_musb_init(NULL); 398 usb_musb_init(NULL);
399
400 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
398 usbhs_init(&usbhs_bdata); 401 usbhs_init(&usbhs_bdata);
399 omap_ads7846_init(1, OMAP3_STALKER_TS_GPIO, 310, NULL); 402 omap_ads7846_init(1, OMAP3_STALKER_TS_GPIO, 310, NULL);
400 403
diff --git a/arch/arm/mach-omap2/board-omap3touchbook.c b/arch/arm/mach-omap2/board-omap3touchbook.c
index bcd44fbcd877..7da48bc42bbf 100644
--- a/arch/arm/mach-omap2/board-omap3touchbook.c
+++ b/arch/arm/mach-omap2/board-omap3touchbook.c
@@ -305,21 +305,22 @@ static struct omap_board_mux board_mux[] __initdata = {
305}; 305};
306#endif 306#endif
307 307
308static struct usbhs_phy_data phy_data[] __initdata = {
309 {
310 .port = 2,
311 .reset_gpio = 147,
312 .vcc_gpio = -EINVAL,
313 },
314};
315
308static struct platform_device *omap3_touchbook_devices[] __initdata = { 316static struct platform_device *omap3_touchbook_devices[] __initdata = {
309 &leds_gpio, 317 &leds_gpio,
310 &keys_gpio, 318 &keys_gpio,
311}; 319};
312 320
313static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 321static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
314
315 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 322 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
316 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 323 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
317 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
318
319 .phy_reset = true,
320 .reset_gpio_port[0] = -EINVAL,
321 .reset_gpio_port[1] = 147,
322 .reset_gpio_port[2] = -EINVAL
323}; 324};
324 325
325static void omap3_touchbook_poweroff(void) 326static void omap3_touchbook_poweroff(void)
@@ -368,6 +369,8 @@ static void __init omap3_touchbook_init(void)
368 omap_ads7846_init(4, OMAP3_TS_GPIO, 310, &ads7846_pdata); 369 omap_ads7846_init(4, OMAP3_TS_GPIO, 310, &ads7846_pdata);
369 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb"); 370 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb");
370 usb_musb_init(NULL); 371 usb_musb_init(NULL);
372
373 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
371 usbhs_init(&usbhs_bdata); 374 usbhs_init(&usbhs_bdata);
372 board_nand_init(omap3touchbook_nand_partitions, 375 board_nand_init(omap3touchbook_nand_partitions,
373 ARRAY_SIZE(omap3touchbook_nand_partitions), NAND_CS, 376 ARRAY_SIZE(omap3touchbook_nand_partitions), NAND_CS,
diff --git a/arch/arm/mach-omap2/board-omap4panda.c b/arch/arm/mach-omap2/board-omap4panda.c
index b02c2f00609b..a71ad345f20d 100644
--- a/arch/arm/mach-omap2/board-omap4panda.c
+++ b/arch/arm/mach-omap2/board-omap4panda.c
@@ -31,6 +31,7 @@
31#include <linux/ti_wilink_st.h> 31#include <linux/ti_wilink_st.h>
32#include <linux/usb/musb.h> 32#include <linux/usb/musb.h>
33#include <linux/usb/phy.h> 33#include <linux/usb/phy.h>
34#include <linux/usb/nop-usb-xceiv.h>
34#include <linux/wl12xx.h> 35#include <linux/wl12xx.h>
35#include <linux/irqchip/arm-gic.h> 36#include <linux/irqchip/arm-gic.h>
36#include <linux/platform_data/omap-abe-twl6040.h> 37#include <linux/platform_data/omap-abe-twl6040.h>
@@ -132,6 +133,22 @@ static struct platform_device btwilink_device = {
132 .id = -1, 133 .id = -1,
133}; 134};
134 135
136/* PHY device on HS USB Port 1 i.e. nop_usb_xceiv.1 */
137static struct nop_usb_xceiv_platform_data hsusb1_phy_data = {
138 /* FREF_CLK3 provides the 19.2 MHz reference clock to the PHY */
139 .clk_rate = 19200000,
140};
141
142static struct usbhs_phy_data phy_data[] __initdata = {
143 {
144 .port = 1,
145 .reset_gpio = GPIO_HUB_NRESET,
146 .vcc_gpio = GPIO_HUB_POWER,
147 .vcc_polarity = 1,
148 .platform_data = &hsusb1_phy_data,
149 },
150};
151
135static struct platform_device *panda_devices[] __initdata = { 152static struct platform_device *panda_devices[] __initdata = {
136 &leds_gpio, 153 &leds_gpio,
137 &wl1271_device, 154 &wl1271_device,
@@ -142,49 +159,19 @@ static struct platform_device *panda_devices[] __initdata = {
142 159
143static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 160static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
144 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY, 161 .port_mode[0] = OMAP_EHCI_PORT_MODE_PHY,
145 .port_mode[1] = OMAP_USBHS_PORT_MODE_UNUSED,
146 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
147 .phy_reset = false,
148 .reset_gpio_port[0] = -EINVAL,
149 .reset_gpio_port[1] = -EINVAL,
150 .reset_gpio_port[2] = -EINVAL
151};
152
153static struct gpio panda_ehci_gpios[] __initdata = {
154 { GPIO_HUB_POWER, GPIOF_OUT_INIT_LOW, "hub_power" },
155 { GPIO_HUB_NRESET, GPIOF_OUT_INIT_LOW, "hub_nreset" },
156}; 162};
157 163
158static void __init omap4_ehci_init(void) 164static void __init omap4_ehci_init(void)
159{ 165{
160 int ret; 166 int ret;
161 struct clk *phy_ref_clk;
162 167
163 /* FREF_CLK3 provides the 19.2 MHz reference clock to the PHY */ 168 /* FREF_CLK3 provides the 19.2 MHz reference clock to the PHY */
164 phy_ref_clk = clk_get(NULL, "auxclk3_ck"); 169 ret = clk_add_alias("main_clk", "nop_usb_xceiv.1", "auxclk3_ck", NULL);
165 if (IS_ERR(phy_ref_clk)) { 170 if (ret)
166 pr_err("Cannot request auxclk3\n"); 171 pr_err("Failed to add main_clk alias to auxclk3_ck\n");
167 return;
168 }
169 clk_set_rate(phy_ref_clk, 19200000);
170 clk_prepare_enable(phy_ref_clk);
171
172 /* disable the power to the usb hub prior to init and reset phy+hub */
173 ret = gpio_request_array(panda_ehci_gpios,
174 ARRAY_SIZE(panda_ehci_gpios));
175 if (ret) {
176 pr_err("Unable to initialize EHCI power/reset\n");
177 return;
178 }
179
180 gpio_export(GPIO_HUB_POWER, 0);
181 gpio_export(GPIO_HUB_NRESET, 0);
182 gpio_set_value(GPIO_HUB_NRESET, 1);
183 172
173 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
184 usbhs_init(&usbhs_bdata); 174 usbhs_init(&usbhs_bdata);
185
186 /* enable power to hub */
187 gpio_set_value(GPIO_HUB_POWER, 1);
188} 175}
189 176
190static struct omap_musb_board_data musb_board_data = { 177static struct omap_musb_board_data musb_board_data = {
diff --git a/arch/arm/mach-omap2/board-overo.c b/arch/arm/mach-omap2/board-overo.c
index f790ce5aaa34..4ca6b680aa72 100644
--- a/arch/arm/mach-omap2/board-overo.c
+++ b/arch/arm/mach-omap2/board-overo.c
@@ -428,14 +428,16 @@ static int __init overo_spi_init(void)
428 return 0; 428 return 0;
429} 429}
430 430
431static struct usbhs_phy_data phy_data[] __initdata = {
432 {
433 .port = 2,
434 .reset_gpio = OVERO_GPIO_USBH_NRESET,
435 .vcc_gpio = -EINVAL,
436 },
437};
438
431static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 439static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
432 .port_mode[0] = OMAP_USBHS_PORT_MODE_UNUSED,
433 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 440 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
434 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
435 .phy_reset = true,
436 .reset_gpio_port[0] = -EINVAL,
437 .reset_gpio_port[1] = OVERO_GPIO_USBH_NRESET,
438 .reset_gpio_port[2] = -EINVAL
439}; 441};
440 442
441#ifdef CONFIG_OMAP_MUX 443#ifdef CONFIG_OMAP_MUX
@@ -472,6 +474,8 @@ static void __init overo_init(void)
472 ARRAY_SIZE(overo_nand_partitions), NAND_CS, 0, NULL); 474 ARRAY_SIZE(overo_nand_partitions), NAND_CS, 0, NULL);
473 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb"); 475 usb_bind_phy("musb-hdrc.0.auto", 0, "twl4030_usb");
474 usb_musb_init(NULL); 476 usb_musb_init(NULL);
477
478 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
475 usbhs_init(&usbhs_bdata); 479 usbhs_init(&usbhs_bdata);
476 overo_spi_init(); 480 overo_spi_init();
477 overo_init_smsc911x(); 481 overo_init_smsc911x();
diff --git a/arch/arm/mach-omap2/board-zoom.c b/arch/arm/mach-omap2/board-zoom.c
index 5e4d4c9fe61a..1a3dd865d8eb 100644
--- a/arch/arm/mach-omap2/board-zoom.c
+++ b/arch/arm/mach-omap2/board-zoom.c
@@ -92,14 +92,16 @@ static struct mtd_partition zoom_nand_partitions[] = {
92 }, 92 },
93}; 93};
94 94
95static struct usbhs_phy_data phy_data[] __initdata = {
96 {
97 .port = 2,
98 .reset_gpio = ZOOM3_EHCI_RESET_GPIO,
99 .vcc_gpio = -EINVAL,
100 },
101};
102
95static struct usbhs_omap_platform_data usbhs_bdata __initdata = { 103static struct usbhs_omap_platform_data usbhs_bdata __initdata = {
96 .port_mode[0] = OMAP_USBHS_PORT_MODE_UNUSED,
97 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY, 104 .port_mode[1] = OMAP_EHCI_PORT_MODE_PHY,
98 .port_mode[2] = OMAP_USBHS_PORT_MODE_UNUSED,
99 .phy_reset = true,
100 .reset_gpio_port[0] = -EINVAL,
101 .reset_gpio_port[1] = ZOOM3_EHCI_RESET_GPIO,
102 .reset_gpio_port[2] = -EINVAL,
103}; 105};
104 106
105static void __init omap_zoom_init(void) 107static void __init omap_zoom_init(void)
@@ -109,6 +111,8 @@ static void __init omap_zoom_init(void)
109 } else if (machine_is_omap_zoom3()) { 111 } else if (machine_is_omap_zoom3()) {
110 omap3_mux_init(board_mux, OMAP_PACKAGE_CBP); 112 omap3_mux_init(board_mux, OMAP_PACKAGE_CBP);
111 omap_mux_init_gpio(ZOOM3_EHCI_RESET_GPIO, OMAP_PIN_OUTPUT); 113 omap_mux_init_gpio(ZOOM3_EHCI_RESET_GPIO, OMAP_PIN_OUTPUT);
114
115 usbhs_init_phys(phy_data, ARRAY_SIZE(phy_data));
112 usbhs_init(&usbhs_bdata); 116 usbhs_init(&usbhs_bdata);
113 } 117 }
114 118
diff --git a/arch/arm/mach-omap2/clock.c b/arch/arm/mach-omap2/clock.c
index e4ec3a69ee2e..2191f25ad21b 100644
--- a/arch/arm/mach-omap2/clock.c
+++ b/arch/arm/mach-omap2/clock.c
@@ -596,7 +596,7 @@ int __init omap2_clk_switch_mpurate_at_boot(const char *mpurate_ck_name)
596 return -ENOENT; 596 return -ENOENT;
597 597
598 r = clk_set_rate(mpurate_ck, mpurate); 598 r = clk_set_rate(mpurate_ck, mpurate);
599 if (IS_ERR_VALUE(r)) { 599 if (r < 0) {
600 WARN(1, "clock: %s: unable to set MPU rate to %d: %d\n", 600 WARN(1, "clock: %s: unable to set MPU rate to %d: %d\n",
601 mpurate_ck_name, mpurate, r); 601 mpurate_ck_name, mpurate, r);
602 clk_put(mpurate_ck); 602 clk_put(mpurate_ck);
diff --git a/arch/arm/mach-omap2/common.h b/arch/arm/mach-omap2/common.h
index d6ba13e1c540..272490e72ee0 100644
--- a/arch/arm/mach-omap2/common.h
+++ b/arch/arm/mach-omap2/common.h
@@ -82,8 +82,7 @@ extern void omap2_init_common_infrastructure(void);
82extern void omap2_sync32k_timer_init(void); 82extern void omap2_sync32k_timer_init(void);
83extern void omap3_sync32k_timer_init(void); 83extern void omap3_sync32k_timer_init(void);
84extern void omap3_secure_sync32k_timer_init(void); 84extern void omap3_secure_sync32k_timer_init(void);
85extern void omap3_gp_gptimer_timer_init(void); 85extern void omap3_gptimer_timer_init(void);
86extern void omap3_am33xx_gptimer_timer_init(void);
87extern void omap4_local_timer_init(void); 86extern void omap4_local_timer_init(void);
88extern void omap5_realtime_timer_init(void); 87extern void omap5_realtime_timer_init(void);
89 88
diff --git a/arch/arm/mach-omap2/gpmc-nand.c b/arch/arm/mach-omap2/gpmc-nand.c
index afc1e8c32d6c..d9c27195caf0 100644
--- a/arch/arm/mach-omap2/gpmc-nand.c
+++ b/arch/arm/mach-omap2/gpmc-nand.c
@@ -74,14 +74,6 @@ static int omap2_nand_gpmc_retime(
74 t.cs_wr_off = gpmc_t->cs_wr_off; 74 t.cs_wr_off = gpmc_t->cs_wr_off;
75 t.wr_cycle = gpmc_t->wr_cycle; 75 t.wr_cycle = gpmc_t->wr_cycle;
76 76
77 /* Configure GPMC */
78 if (gpmc_nand_data->devsize == NAND_BUSWIDTH_16)
79 gpmc_cs_configure(gpmc_nand_data->cs, GPMC_CONFIG_DEV_SIZE, 1);
80 else
81 gpmc_cs_configure(gpmc_nand_data->cs, GPMC_CONFIG_DEV_SIZE, 0);
82 gpmc_cs_configure(gpmc_nand_data->cs,
83 GPMC_CONFIG_DEV_TYPE, GPMC_DEVICETYPE_NAND);
84 gpmc_cs_configure(gpmc_nand_data->cs, GPMC_CONFIG_WP, 0);
85 err = gpmc_cs_set_timings(gpmc_nand_data->cs, &t); 77 err = gpmc_cs_set_timings(gpmc_nand_data->cs, &t);
86 if (err) 78 if (err)
87 return err; 79 return err;
@@ -115,14 +107,18 @@ int gpmc_nand_init(struct omap_nand_platform_data *gpmc_nand_data,
115 struct gpmc_timings *gpmc_t) 107 struct gpmc_timings *gpmc_t)
116{ 108{
117 int err = 0; 109 int err = 0;
110 struct gpmc_settings s;
118 struct device *dev = &gpmc_nand_device.dev; 111 struct device *dev = &gpmc_nand_device.dev;
119 112
113 memset(&s, 0, sizeof(struct gpmc_settings));
114
120 gpmc_nand_device.dev.platform_data = gpmc_nand_data; 115 gpmc_nand_device.dev.platform_data = gpmc_nand_data;
121 116
122 err = gpmc_cs_request(gpmc_nand_data->cs, NAND_IO_SIZE, 117 err = gpmc_cs_request(gpmc_nand_data->cs, NAND_IO_SIZE,
123 (unsigned long *)&gpmc_nand_resource[0].start); 118 (unsigned long *)&gpmc_nand_resource[0].start);
124 if (err < 0) { 119 if (err < 0) {
125 dev_err(dev, "Cannot request GPMC CS\n"); 120 dev_err(dev, "Cannot request GPMC CS %d, error %d\n",
121 gpmc_nand_data->cs, err);
126 return err; 122 return err;
127 } 123 }
128 124
@@ -140,11 +136,31 @@ int gpmc_nand_init(struct omap_nand_platform_data *gpmc_nand_data,
140 dev_err(dev, "Unable to set gpmc timings: %d\n", err); 136 dev_err(dev, "Unable to set gpmc timings: %d\n", err);
141 return err; 137 return err;
142 } 138 }
143 }
144 139
145 /* Enable RD PIN Monitoring Reg */ 140 if (gpmc_nand_data->of_node) {
146 if (gpmc_nand_data->dev_ready) { 141 gpmc_read_settings_dt(gpmc_nand_data->of_node, &s);
147 gpmc_cs_configure(gpmc_nand_data->cs, GPMC_CONFIG_RDY_BSY, 1); 142 } else {
143 s.device_nand = true;
144
145 /* Enable RD PIN Monitoring Reg */
146 if (gpmc_nand_data->dev_ready) {
147 s.wait_on_read = true;
148 s.wait_on_write = true;
149 }
150 }
151
152 if (gpmc_nand_data->devsize == NAND_BUSWIDTH_16)
153 s.device_width = GPMC_DEVWIDTH_16BIT;
154 else
155 s.device_width = GPMC_DEVWIDTH_8BIT;
156
157 err = gpmc_cs_program_settings(gpmc_nand_data->cs, &s);
158 if (err < 0)
159 goto out_free_cs;
160
161 err = gpmc_configure(GPMC_CONFIG_WP, 0);
162 if (err < 0)
163 goto out_free_cs;
148 } 164 }
149 165
150 gpmc_update_nand_reg(&gpmc_nand_data->reg, gpmc_nand_data->cs); 166 gpmc_update_nand_reg(&gpmc_nand_data->reg, gpmc_nand_data->cs);
diff --git a/arch/arm/mach-omap2/gpmc-onenand.c b/arch/arm/mach-omap2/gpmc-onenand.c
index fadd87435cd0..64b5a8346982 100644
--- a/arch/arm/mach-omap2/gpmc-onenand.c
+++ b/arch/arm/mach-omap2/gpmc-onenand.c
@@ -47,11 +47,23 @@ static struct platform_device gpmc_onenand_device = {
47 .resource = &gpmc_onenand_resource, 47 .resource = &gpmc_onenand_resource,
48}; 48};
49 49
50static struct gpmc_timings omap2_onenand_calc_async_timings(void) 50static struct gpmc_settings onenand_async = {
51 .device_width = GPMC_DEVWIDTH_16BIT,
52 .mux_add_data = GPMC_MUX_AD,
53};
54
55static struct gpmc_settings onenand_sync = {
56 .burst_read = true,
57 .burst_wrap = true,
58 .burst_len = GPMC_BURST_16,
59 .device_width = GPMC_DEVWIDTH_16BIT,
60 .mux_add_data = GPMC_MUX_AD,
61 .wait_pin = 0,
62};
63
64static void omap2_onenand_calc_async_timings(struct gpmc_timings *t)
51{ 65{
52 struct gpmc_device_timings dev_t; 66 struct gpmc_device_timings dev_t;
53 struct gpmc_timings t;
54
55 const int t_cer = 15; 67 const int t_cer = 15;
56 const int t_avdp = 12; 68 const int t_avdp = 12;
57 const int t_aavdh = 7; 69 const int t_aavdh = 7;
@@ -64,7 +76,6 @@ static struct gpmc_timings omap2_onenand_calc_async_timings(void)
64 76
65 memset(&dev_t, 0, sizeof(dev_t)); 77 memset(&dev_t, 0, sizeof(dev_t));
66 78
67 dev_t.mux = true;
68 dev_t.t_avdp_r = max_t(int, t_avdp, t_cer) * 1000; 79 dev_t.t_avdp_r = max_t(int, t_avdp, t_cer) * 1000;
69 dev_t.t_avdp_w = dev_t.t_avdp_r; 80 dev_t.t_avdp_w = dev_t.t_avdp_r;
70 dev_t.t_aavdh = t_aavdh * 1000; 81 dev_t.t_aavdh = t_aavdh * 1000;
@@ -76,19 +87,7 @@ static struct gpmc_timings omap2_onenand_calc_async_timings(void)
76 dev_t.t_wpl = t_wpl * 1000; 87 dev_t.t_wpl = t_wpl * 1000;
77 dev_t.t_wph = t_wph * 1000; 88 dev_t.t_wph = t_wph * 1000;
78 89
79 gpmc_calc_timings(&t, &dev_t); 90 gpmc_calc_timings(t, &onenand_async, &dev_t);
80
81 return t;
82}
83
84static int gpmc_set_async_mode(int cs, struct gpmc_timings *t)
85{
86 /* Configure GPMC for asynchronous read */
87 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG1,
88 GPMC_CONFIG1_DEVICESIZE_16 |
89 GPMC_CONFIG1_MUXADDDATA);
90
91 return gpmc_cs_set_timings(cs, t);
92} 91}
93 92
94static void omap2_onenand_set_async_mode(void __iomem *onenand_base) 93static void omap2_onenand_set_async_mode(void __iomem *onenand_base)
@@ -158,12 +157,11 @@ static int omap2_onenand_get_freq(struct omap_onenand_platform_data *cfg,
158 return freq; 157 return freq;
159} 158}
160 159
161static struct gpmc_timings 160static void omap2_onenand_calc_sync_timings(struct gpmc_timings *t,
162omap2_onenand_calc_sync_timings(struct omap_onenand_platform_data *cfg, 161 unsigned int flags,
163 int freq) 162 int freq)
164{ 163{
165 struct gpmc_device_timings dev_t; 164 struct gpmc_device_timings dev_t;
166 struct gpmc_timings t;
167 const int t_cer = 15; 165 const int t_cer = 15;
168 const int t_avdp = 12; 166 const int t_avdp = 12;
169 const int t_cez = 20; /* max of t_cez, t_oez */ 167 const int t_cez = 20; /* max of t_cez, t_oez */
@@ -172,9 +170,9 @@ omap2_onenand_calc_sync_timings(struct omap_onenand_platform_data *cfg,
172 int min_gpmc_clk_period, t_ces, t_avds, t_avdh, t_ach, t_aavdh, t_rdyo; 170 int min_gpmc_clk_period, t_ces, t_avds, t_avdh, t_ach, t_aavdh, t_rdyo;
173 int div, gpmc_clk_ns; 171 int div, gpmc_clk_ns;
174 172
175 if (cfg->flags & ONENAND_SYNC_READ) 173 if (flags & ONENAND_SYNC_READ)
176 onenand_flags = ONENAND_FLAG_SYNCREAD; 174 onenand_flags = ONENAND_FLAG_SYNCREAD;
177 else if (cfg->flags & ONENAND_SYNC_READWRITE) 175 else if (flags & ONENAND_SYNC_READWRITE)
178 onenand_flags = ONENAND_FLAG_SYNCREAD | ONENAND_FLAG_SYNCWRITE; 176 onenand_flags = ONENAND_FLAG_SYNCREAD | ONENAND_FLAG_SYNCWRITE;
179 177
180 switch (freq) { 178 switch (freq) {
@@ -239,10 +237,11 @@ omap2_onenand_calc_sync_timings(struct omap_onenand_platform_data *cfg,
239 /* Set synchronous read timings */ 237 /* Set synchronous read timings */
240 memset(&dev_t, 0, sizeof(dev_t)); 238 memset(&dev_t, 0, sizeof(dev_t));
241 239
242 dev_t.mux = true; 240 if (onenand_flags & ONENAND_FLAG_SYNCREAD)
243 dev_t.sync_read = true; 241 onenand_sync.sync_read = true;
244 if (onenand_flags & ONENAND_FLAG_SYNCWRITE) { 242 if (onenand_flags & ONENAND_FLAG_SYNCWRITE) {
245 dev_t.sync_write = true; 243 onenand_sync.sync_write = true;
244 onenand_sync.burst_write = true;
246 } else { 245 } else {
247 dev_t.t_avdp_w = max(t_avdp, t_cer) * 1000; 246 dev_t.t_avdp_w = max(t_avdp, t_cer) * 1000;
248 dev_t.t_wpl = t_wpl * 1000; 247 dev_t.t_wpl = t_wpl * 1000;
@@ -265,32 +264,7 @@ omap2_onenand_calc_sync_timings(struct omap_onenand_platform_data *cfg,
265 dev_t.cyc_aavdh_oe = 1; 264 dev_t.cyc_aavdh_oe = 1;
266 dev_t.t_rdyo = t_rdyo * 1000 + min_gpmc_clk_period; 265 dev_t.t_rdyo = t_rdyo * 1000 + min_gpmc_clk_period;
267 266
268 gpmc_calc_timings(&t, &dev_t); 267 gpmc_calc_timings(t, &onenand_sync, &dev_t);
269
270 return t;
271}
272
273static int gpmc_set_sync_mode(int cs, struct gpmc_timings *t)
274{
275 unsigned sync_read = onenand_flags & ONENAND_FLAG_SYNCREAD;
276 unsigned sync_write = onenand_flags & ONENAND_FLAG_SYNCWRITE;
277
278 /* Configure GPMC for synchronous read */
279 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG1,
280 GPMC_CONFIG1_WRAPBURST_SUPP |
281 GPMC_CONFIG1_READMULTIPLE_SUPP |
282 (sync_read ? GPMC_CONFIG1_READTYPE_SYNC : 0) |
283 (sync_write ? GPMC_CONFIG1_WRITEMULTIPLE_SUPP : 0) |
284 (sync_write ? GPMC_CONFIG1_WRITETYPE_SYNC : 0) |
285 GPMC_CONFIG1_PAGE_LEN(2) |
286 (cpu_is_omap34xx() ? 0 :
287 (GPMC_CONFIG1_WAIT_READ_MON |
288 GPMC_CONFIG1_WAIT_PIN_SEL(0))) |
289 GPMC_CONFIG1_DEVICESIZE_16 |
290 GPMC_CONFIG1_DEVICETYPE_NOR |
291 GPMC_CONFIG1_MUXADDDATA);
292
293 return gpmc_cs_set_timings(cs, t);
294} 268}
295 269
296static int omap2_onenand_setup_async(void __iomem *onenand_base) 270static int omap2_onenand_setup_async(void __iomem *onenand_base)
@@ -298,12 +272,20 @@ static int omap2_onenand_setup_async(void __iomem *onenand_base)
298 struct gpmc_timings t; 272 struct gpmc_timings t;
299 int ret; 273 int ret;
300 274
275 if (gpmc_onenand_data->of_node)
276 gpmc_read_settings_dt(gpmc_onenand_data->of_node,
277 &onenand_async);
278
301 omap2_onenand_set_async_mode(onenand_base); 279 omap2_onenand_set_async_mode(onenand_base);
302 280
303 t = omap2_onenand_calc_async_timings(); 281 omap2_onenand_calc_async_timings(&t);
282
283 ret = gpmc_cs_program_settings(gpmc_onenand_data->cs, &onenand_async);
284 if (ret < 0)
285 return ret;
304 286
305 ret = gpmc_set_async_mode(gpmc_onenand_data->cs, &t); 287 ret = gpmc_cs_set_timings(gpmc_onenand_data->cs, &t);
306 if (IS_ERR_VALUE(ret)) 288 if (ret < 0)
307 return ret; 289 return ret;
308 290
309 omap2_onenand_set_async_mode(onenand_base); 291 omap2_onenand_set_async_mode(onenand_base);
@@ -322,10 +304,26 @@ static int omap2_onenand_setup_sync(void __iomem *onenand_base, int *freq_ptr)
322 set_onenand_cfg(onenand_base); 304 set_onenand_cfg(onenand_base);
323 } 305 }
324 306
325 t = omap2_onenand_calc_sync_timings(gpmc_onenand_data, freq); 307 if (gpmc_onenand_data->of_node) {
308 gpmc_read_settings_dt(gpmc_onenand_data->of_node,
309 &onenand_sync);
310 } else {
311 /*
312 * FIXME: Appears to be legacy code from initial ONENAND commit.
313 * Unclear what boards this is for and if this can be removed.
314 */
315 if (!cpu_is_omap34xx())
316 onenand_sync.wait_on_read = true;
317 }
318
319 omap2_onenand_calc_sync_timings(&t, gpmc_onenand_data->flags, freq);
326 320
327 ret = gpmc_set_sync_mode(gpmc_onenand_data->cs, &t); 321 ret = gpmc_cs_program_settings(gpmc_onenand_data->cs, &onenand_sync);
328 if (IS_ERR_VALUE(ret)) 322 if (ret < 0)
323 return ret;
324
325 ret = gpmc_cs_set_timings(gpmc_onenand_data->cs, &t);
326 if (ret < 0)
329 return ret; 327 return ret;
330 328
331 set_onenand_cfg(onenand_base); 329 set_onenand_cfg(onenand_base);
@@ -359,6 +357,7 @@ static int gpmc_onenand_setup(void __iomem *onenand_base, int *freq_ptr)
359void gpmc_onenand_init(struct omap_onenand_platform_data *_onenand_data) 357void gpmc_onenand_init(struct omap_onenand_platform_data *_onenand_data)
360{ 358{
361 int err; 359 int err;
360 struct device *dev = &gpmc_onenand_device.dev;
362 361
363 gpmc_onenand_data = _onenand_data; 362 gpmc_onenand_data = _onenand_data;
364 gpmc_onenand_data->onenand_setup = gpmc_onenand_setup; 363 gpmc_onenand_data->onenand_setup = gpmc_onenand_setup;
@@ -366,7 +365,7 @@ void gpmc_onenand_init(struct omap_onenand_platform_data *_onenand_data)
366 365
367 if (cpu_is_omap24xx() && 366 if (cpu_is_omap24xx() &&
368 (gpmc_onenand_data->flags & ONENAND_SYNC_READWRITE)) { 367 (gpmc_onenand_data->flags & ONENAND_SYNC_READWRITE)) {
369 printk(KERN_ERR "Onenand using only SYNC_READ on 24xx\n"); 368 dev_warn(dev, "OneNAND using only SYNC_READ on 24xx\n");
370 gpmc_onenand_data->flags &= ~ONENAND_SYNC_READWRITE; 369 gpmc_onenand_data->flags &= ~ONENAND_SYNC_READWRITE;
371 gpmc_onenand_data->flags |= ONENAND_SYNC_READ; 370 gpmc_onenand_data->flags |= ONENAND_SYNC_READ;
372 } 371 }
@@ -379,7 +378,8 @@ void gpmc_onenand_init(struct omap_onenand_platform_data *_onenand_data)
379 err = gpmc_cs_request(gpmc_onenand_data->cs, ONENAND_IO_SIZE, 378 err = gpmc_cs_request(gpmc_onenand_data->cs, ONENAND_IO_SIZE,
380 (unsigned long *)&gpmc_onenand_resource.start); 379 (unsigned long *)&gpmc_onenand_resource.start);
381 if (err < 0) { 380 if (err < 0) {
382 pr_err("%s: Cannot request GPMC CS\n", __func__); 381 dev_err(dev, "Cannot request GPMC CS %d, error %d\n",
382 gpmc_onenand_data->cs, err);
383 return; 383 return;
384 } 384 }
385 385
@@ -387,7 +387,7 @@ void gpmc_onenand_init(struct omap_onenand_platform_data *_onenand_data)
387 ONENAND_IO_SIZE - 1; 387 ONENAND_IO_SIZE - 1;
388 388
389 if (platform_device_register(&gpmc_onenand_device) < 0) { 389 if (platform_device_register(&gpmc_onenand_device) < 0) {
390 pr_err("%s: Unable to register OneNAND device\n", __func__); 390 dev_err(dev, "Unable to register OneNAND device\n");
391 gpmc_cs_free(gpmc_onenand_data->cs); 391 gpmc_cs_free(gpmc_onenand_data->cs);
392 return; 392 return;
393 } 393 }
diff --git a/arch/arm/mach-omap2/gpmc-smc91x.c b/arch/arm/mach-omap2/gpmc-smc91x.c
index 11d0b756f098..61a063595e66 100644
--- a/arch/arm/mach-omap2/gpmc-smc91x.c
+++ b/arch/arm/mach-omap2/gpmc-smc91x.c
@@ -49,6 +49,10 @@ static struct platform_device gpmc_smc91x_device = {
49 .resource = gpmc_smc91x_resources, 49 .resource = gpmc_smc91x_resources,
50}; 50};
51 51
52static struct gpmc_settings smc91x_settings = {
53 .device_width = GPMC_DEVWIDTH_16BIT,
54};
55
52/* 56/*
53 * Set the gpmc timings for smc91c96. The timings are taken 57 * Set the gpmc timings for smc91c96. The timings are taken
54 * from the data sheet available at: 58 * from the data sheet available at:
@@ -67,18 +71,6 @@ static int smc91c96_gpmc_retime(void)
67 const int t7 = 5; /* Figure 12.4 write */ 71 const int t7 = 5; /* Figure 12.4 write */
68 const int t8 = 5; /* Figure 12.4 write */ 72 const int t8 = 5; /* Figure 12.4 write */
69 const int t20 = 185; /* Figure 12.2 read and 12.4 write */ 73 const int t20 = 185; /* Figure 12.2 read and 12.4 write */
70 u32 l;
71
72 l = GPMC_CONFIG1_DEVICESIZE_16;
73 if (gpmc_cfg->flags & GPMC_MUX_ADD_DATA)
74 l |= GPMC_CONFIG1_MUXADDDATA;
75 if (gpmc_cfg->flags & GPMC_READ_MON)
76 l |= GPMC_CONFIG1_WAIT_READ_MON;
77 if (gpmc_cfg->flags & GPMC_WRITE_MON)
78 l |= GPMC_CONFIG1_WAIT_WRITE_MON;
79 if (gpmc_cfg->wait_pin)
80 l |= GPMC_CONFIG1_WAIT_PIN_SEL(gpmc_cfg->wait_pin);
81 gpmc_cs_write_reg(gpmc_cfg->cs, GPMC_CS_CONFIG1, l);
82 74
83 /* 75 /*
84 * FIXME: Calculate the address and data bus muxed timings. 76 * FIXME: Calculate the address and data bus muxed timings.
@@ -104,7 +96,7 @@ static int smc91c96_gpmc_retime(void)
104 dev_t.t_cez_w = t4_w * 1000; 96 dev_t.t_cez_w = t4_w * 1000;
105 dev_t.t_wr_cycle = (t20 - t3) * 1000; 97 dev_t.t_wr_cycle = (t20 - t3) * 1000;
106 98
107 gpmc_calc_timings(&t, &dev_t); 99 gpmc_calc_timings(&t, &smc91x_settings, &dev_t);
108 100
109 return gpmc_cs_set_timings(gpmc_cfg->cs, &t); 101 return gpmc_cs_set_timings(gpmc_cfg->cs, &t);
110} 102}
@@ -133,6 +125,18 @@ void __init gpmc_smc91x_init(struct omap_smc91x_platform_data *board_data)
133 gpmc_smc91x_resources[0].end = cs_mem_base + 0x30f; 125 gpmc_smc91x_resources[0].end = cs_mem_base + 0x30f;
134 gpmc_smc91x_resources[1].flags |= (gpmc_cfg->flags & IRQF_TRIGGER_MASK); 126 gpmc_smc91x_resources[1].flags |= (gpmc_cfg->flags & IRQF_TRIGGER_MASK);
135 127
128 if (gpmc_cfg->flags & GPMC_MUX_ADD_DATA)
129 smc91x_settings.mux_add_data = GPMC_MUX_AD;
130 if (gpmc_cfg->flags & GPMC_READ_MON)
131 smc91x_settings.wait_on_read = true;
132 if (gpmc_cfg->flags & GPMC_WRITE_MON)
133 smc91x_settings.wait_on_write = true;
134 if (gpmc_cfg->wait_pin)
135 smc91x_settings.wait_pin = gpmc_cfg->wait_pin;
136 ret = gpmc_cs_program_settings(gpmc_cfg->cs, &smc91x_settings);
137 if (ret < 0)
138 goto free1;
139
136 if (gpmc_cfg->retime) { 140 if (gpmc_cfg->retime) {
137 ret = gpmc_cfg->retime(); 141 ret = gpmc_cfg->retime();
138 if (ret != 0) 142 if (ret != 0)
diff --git a/arch/arm/mach-omap2/gpmc.c b/arch/arm/mach-omap2/gpmc.c
index 410e1bac7815..ed946df5ad8a 100644
--- a/arch/arm/mach-omap2/gpmc.c
+++ b/arch/arm/mach-omap2/gpmc.c
@@ -26,6 +26,7 @@
26#include <linux/interrupt.h> 26#include <linux/interrupt.h>
27#include <linux/platform_device.h> 27#include <linux/platform_device.h>
28#include <linux/of.h> 28#include <linux/of.h>
29#include <linux/of_address.h>
29#include <linux/of_mtd.h> 30#include <linux/of_mtd.h>
30#include <linux/of_device.h> 31#include <linux/of_device.h>
31#include <linux/mtd/nand.h> 32#include <linux/mtd/nand.h>
@@ -91,9 +92,7 @@
91#define GPMC_CS_SIZE 0x30 92#define GPMC_CS_SIZE 0x30
92#define GPMC_BCH_SIZE 0x10 93#define GPMC_BCH_SIZE 0x10
93 94
94#define GPMC_MEM_START 0x00000000
95#define GPMC_MEM_END 0x3FFFFFFF 95#define GPMC_MEM_END 0x3FFFFFFF
96#define BOOT_ROM_SPACE 0x100000 /* 1MB */
97 96
98#define GPMC_CHUNK_SHIFT 24 /* 16 MB */ 97#define GPMC_CHUNK_SHIFT 24 /* 16 MB */
99#define GPMC_SECTION_SHIFT 28 /* 128 MB */ 98#define GPMC_SECTION_SHIFT 28 /* 128 MB */
@@ -107,6 +106,9 @@
107 106
108#define GPMC_HAS_WR_ACCESS 0x1 107#define GPMC_HAS_WR_ACCESS 0x1
109#define GPMC_HAS_WR_DATA_MUX_BUS 0x2 108#define GPMC_HAS_WR_DATA_MUX_BUS 0x2
109#define GPMC_HAS_MUX_AAD 0x4
110
111#define GPMC_NR_WAITPINS 4
110 112
111/* XXX: Only NAND irq has been considered,currently these are the only ones used 113/* XXX: Only NAND irq has been considered,currently these are the only ones used
112 */ 114 */
@@ -153,6 +155,7 @@ static struct resource gpmc_cs_mem[GPMC_CS_NUM];
153static DEFINE_SPINLOCK(gpmc_mem_lock); 155static DEFINE_SPINLOCK(gpmc_mem_lock);
154/* Define chip-selects as reserved by default until probe completes */ 156/* Define chip-selects as reserved by default until probe completes */
155static unsigned int gpmc_cs_map = ((1 << GPMC_CS_NUM) - 1); 157static unsigned int gpmc_cs_map = ((1 << GPMC_CS_NUM) - 1);
158static unsigned int gpmc_nr_waitpins;
156static struct device *gpmc_dev; 159static struct device *gpmc_dev;
157static int gpmc_irq; 160static int gpmc_irq;
158static resource_size_t phys_base, mem_size; 161static resource_size_t phys_base, mem_size;
@@ -181,7 +184,7 @@ void gpmc_cs_write_reg(int cs, int idx, u32 val)
181 __raw_writel(val, reg_addr); 184 __raw_writel(val, reg_addr);
182} 185}
183 186
184u32 gpmc_cs_read_reg(int cs, int idx) 187static u32 gpmc_cs_read_reg(int cs, int idx)
185{ 188{
186 void __iomem *reg_addr; 189 void __iomem *reg_addr;
187 190
@@ -190,7 +193,7 @@ u32 gpmc_cs_read_reg(int cs, int idx)
190} 193}
191 194
192/* TODO: Add support for gpmc_fck to clock framework and use it */ 195/* TODO: Add support for gpmc_fck to clock framework and use it */
193unsigned long gpmc_get_fclk_period(void) 196static unsigned long gpmc_get_fclk_period(void)
194{ 197{
195 unsigned long rate = clk_get_rate(gpmc_l3_clk); 198 unsigned long rate = clk_get_rate(gpmc_l3_clk);
196 199
@@ -205,7 +208,7 @@ unsigned long gpmc_get_fclk_period(void)
205 return rate; 208 return rate;
206} 209}
207 210
208unsigned int gpmc_ns_to_ticks(unsigned int time_ns) 211static unsigned int gpmc_ns_to_ticks(unsigned int time_ns)
209{ 212{
210 unsigned long tick_ps; 213 unsigned long tick_ps;
211 214
@@ -215,7 +218,7 @@ unsigned int gpmc_ns_to_ticks(unsigned int time_ns)
215 return (time_ns * 1000 + tick_ps - 1) / tick_ps; 218 return (time_ns * 1000 + tick_ps - 1) / tick_ps;
216} 219}
217 220
218unsigned int gpmc_ps_to_ticks(unsigned int time_ps) 221static unsigned int gpmc_ps_to_ticks(unsigned int time_ps)
219{ 222{
220 unsigned long tick_ps; 223 unsigned long tick_ps;
221 224
@@ -230,13 +233,6 @@ unsigned int gpmc_ticks_to_ns(unsigned int ticks)
230 return ticks * gpmc_get_fclk_period() / 1000; 233 return ticks * gpmc_get_fclk_period() / 1000;
231} 234}
232 235
233unsigned int gpmc_round_ns_to_ticks(unsigned int time_ns)
234{
235 unsigned long ticks = gpmc_ns_to_ticks(time_ns);
236
237 return ticks * gpmc_get_fclk_period() / 1000;
238}
239
240static unsigned int gpmc_ticks_to_ps(unsigned int ticks) 236static unsigned int gpmc_ticks_to_ps(unsigned int ticks)
241{ 237{
242 return ticks * gpmc_get_fclk_period(); 238 return ticks * gpmc_get_fclk_period();
@@ -405,11 +401,18 @@ int gpmc_cs_set_timings(int cs, const struct gpmc_timings *t)
405 return 0; 401 return 0;
406} 402}
407 403
408static void gpmc_cs_enable_mem(int cs, u32 base, u32 size) 404static int gpmc_cs_enable_mem(int cs, u32 base, u32 size)
409{ 405{
410 u32 l; 406 u32 l;
411 u32 mask; 407 u32 mask;
412 408
409 /*
410 * Ensure that base address is aligned on a
411 * boundary equal to or greater than size.
412 */
413 if (base & (size - 1))
414 return -EINVAL;
415
413 mask = (1 << GPMC_SECTION_SHIFT) - size; 416 mask = (1 << GPMC_SECTION_SHIFT) - size;
414 l = gpmc_cs_read_reg(cs, GPMC_CS_CONFIG7); 417 l = gpmc_cs_read_reg(cs, GPMC_CS_CONFIG7);
415 l &= ~0x3f; 418 l &= ~0x3f;
@@ -418,6 +421,8 @@ static void gpmc_cs_enable_mem(int cs, u32 base, u32 size)
418 l |= ((mask >> GPMC_CHUNK_SHIFT) & 0x0f) << 8; 421 l |= ((mask >> GPMC_CHUNK_SHIFT) & 0x0f) << 8;
419 l |= GPMC_CONFIG7_CSVALID; 422 l |= GPMC_CONFIG7_CSVALID;
420 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG7, l); 423 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG7, l);
424
425 return 0;
421} 426}
422 427
423static void gpmc_cs_disable_mem(int cs) 428static void gpmc_cs_disable_mem(int cs)
@@ -448,22 +453,14 @@ static int gpmc_cs_mem_enabled(int cs)
448 return l & GPMC_CONFIG7_CSVALID; 453 return l & GPMC_CONFIG7_CSVALID;
449} 454}
450 455
451int gpmc_cs_set_reserved(int cs, int reserved) 456static void gpmc_cs_set_reserved(int cs, int reserved)
452{ 457{
453 if (cs > GPMC_CS_NUM)
454 return -ENODEV;
455
456 gpmc_cs_map &= ~(1 << cs); 458 gpmc_cs_map &= ~(1 << cs);
457 gpmc_cs_map |= (reserved ? 1 : 0) << cs; 459 gpmc_cs_map |= (reserved ? 1 : 0) << cs;
458
459 return 0;
460} 460}
461 461
462int gpmc_cs_reserved(int cs) 462static bool gpmc_cs_reserved(int cs)
463{ 463{
464 if (cs > GPMC_CS_NUM)
465 return -ENODEV;
466
467 return gpmc_cs_map & (1 << cs); 464 return gpmc_cs_map & (1 << cs);
468} 465}
469 466
@@ -510,6 +507,39 @@ static int gpmc_cs_delete_mem(int cs)
510 return r; 507 return r;
511} 508}
512 509
510/**
511 * gpmc_cs_remap - remaps a chip-select physical base address
512 * @cs: chip-select to remap
513 * @base: physical base address to re-map chip-select to
514 *
515 * Re-maps a chip-select to a new physical base address specified by
516 * "base". Returns 0 on success and appropriate negative error code
517 * on failure.
518 */
519static int gpmc_cs_remap(int cs, u32 base)
520{
521 int ret;
522 u32 old_base, size;
523
524 if (cs > GPMC_CS_NUM)
525 return -ENODEV;
526 gpmc_cs_get_memconf(cs, &old_base, &size);
527 if (base == old_base)
528 return 0;
529 gpmc_cs_disable_mem(cs);
530 ret = gpmc_cs_delete_mem(cs);
531 if (ret < 0)
532 return ret;
533 ret = gpmc_cs_insert_mem(cs, base, size);
534 if (ret < 0)
535 return ret;
536 ret = gpmc_cs_enable_mem(cs, base, size);
537 if (ret < 0)
538 return ret;
539
540 return 0;
541}
542
513int gpmc_cs_request(int cs, unsigned long size, unsigned long *base) 543int gpmc_cs_request(int cs, unsigned long size, unsigned long *base)
514{ 544{
515 struct resource *res = &gpmc_cs_mem[cs]; 545 struct resource *res = &gpmc_cs_mem[cs];
@@ -535,7 +565,12 @@ int gpmc_cs_request(int cs, unsigned long size, unsigned long *base)
535 if (r < 0) 565 if (r < 0)
536 goto out; 566 goto out;
537 567
538 gpmc_cs_enable_mem(cs, res->start, resource_size(res)); 568 r = gpmc_cs_enable_mem(cs, res->start, resource_size(res));
569 if (r < 0) {
570 release_resource(res);
571 goto out;
572 }
573
539 *base = res->start; 574 *base = res->start;
540 gpmc_cs_set_reserved(cs, 1); 575 gpmc_cs_set_reserved(cs, 1);
541out: 576out:
@@ -561,16 +596,14 @@ void gpmc_cs_free(int cs)
561EXPORT_SYMBOL(gpmc_cs_free); 596EXPORT_SYMBOL(gpmc_cs_free);
562 597
563/** 598/**
564 * gpmc_cs_configure - write request to configure gpmc 599 * gpmc_configure - write request to configure gpmc
565 * @cs: chip select number
566 * @cmd: command type 600 * @cmd: command type
567 * @wval: value to write 601 * @wval: value to write
568 * @return status of the operation 602 * @return status of the operation
569 */ 603 */
570int gpmc_cs_configure(int cs, int cmd, int wval) 604int gpmc_configure(int cmd, int wval)
571{ 605{
572 int err = 0; 606 u32 regval;
573 u32 regval = 0;
574 607
575 switch (cmd) { 608 switch (cmd) {
576 case GPMC_ENABLE_IRQ: 609 case GPMC_ENABLE_IRQ:
@@ -590,43 +623,14 @@ int gpmc_cs_configure(int cs, int cmd, int wval)
590 gpmc_write_reg(GPMC_CONFIG, regval); 623 gpmc_write_reg(GPMC_CONFIG, regval);
591 break; 624 break;
592 625
593 case GPMC_CONFIG_RDY_BSY:
594 regval = gpmc_cs_read_reg(cs, GPMC_CS_CONFIG1);
595 if (wval)
596 regval |= WR_RD_PIN_MONITORING;
597 else
598 regval &= ~WR_RD_PIN_MONITORING;
599 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG1, regval);
600 break;
601
602 case GPMC_CONFIG_DEV_SIZE:
603 regval = gpmc_cs_read_reg(cs, GPMC_CS_CONFIG1);
604
605 /* clear 2 target bits */
606 regval &= ~GPMC_CONFIG1_DEVICESIZE(3);
607
608 /* set the proper value */
609 regval |= GPMC_CONFIG1_DEVICESIZE(wval);
610
611 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG1, regval);
612 break;
613
614 case GPMC_CONFIG_DEV_TYPE:
615 regval = gpmc_cs_read_reg(cs, GPMC_CS_CONFIG1);
616 regval |= GPMC_CONFIG1_DEVICETYPE(wval);
617 if (wval == GPMC_DEVICETYPE_NOR)
618 regval |= GPMC_CONFIG1_MUXADDDATA;
619 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG1, regval);
620 break;
621
622 default: 626 default:
623 printk(KERN_ERR "gpmc_configure_cs: Not supported\n"); 627 pr_err("%s: command not supported\n", __func__);
624 err = -EINVAL; 628 return -EINVAL;
625 } 629 }
626 630
627 return err; 631 return 0;
628} 632}
629EXPORT_SYMBOL(gpmc_cs_configure); 633EXPORT_SYMBOL(gpmc_configure);
630 634
631void gpmc_update_nand_reg(struct gpmc_nand_regs *reg, int cs) 635void gpmc_update_nand_reg(struct gpmc_nand_regs *reg, int cs)
632{ 636{
@@ -716,7 +720,7 @@ static int gpmc_setup_irq(void)
716 return -EINVAL; 720 return -EINVAL;
717 721
718 gpmc_irq_start = irq_alloc_descs(-1, 0, GPMC_NR_IRQ, 0); 722 gpmc_irq_start = irq_alloc_descs(-1, 0, GPMC_NR_IRQ, 0);
719 if (IS_ERR_VALUE(gpmc_irq_start)) { 723 if (gpmc_irq_start < 0) {
720 pr_err("irq_alloc_descs failed\n"); 724 pr_err("irq_alloc_descs failed\n");
721 return gpmc_irq_start; 725 return gpmc_irq_start;
722 } 726 }
@@ -781,16 +785,16 @@ static void gpmc_mem_exit(void)
781 785
782} 786}
783 787
784static int gpmc_mem_init(void) 788static void gpmc_mem_init(void)
785{ 789{
786 int cs, rc; 790 int cs;
787 unsigned long boot_rom_space = 0;
788 791
789 /* never allocate the first page, to facilitate bug detection; 792 /*
790 * even if we didn't boot from ROM. 793 * The first 1MB of GPMC address space is typically mapped to
794 * the internal ROM. Never allocate the first page, to
795 * facilitate bug detection; even if we didn't boot from ROM.
791 */ 796 */
792 boot_rom_space = BOOT_ROM_SPACE; 797 gpmc_mem_root.start = SZ_1M;
793 gpmc_mem_root.start = GPMC_MEM_START + boot_rom_space;
794 gpmc_mem_root.end = GPMC_MEM_END; 798 gpmc_mem_root.end = GPMC_MEM_END;
795 799
796 /* Reserve all regions that has been set up by bootloader */ 800 /* Reserve all regions that has been set up by bootloader */
@@ -800,16 +804,12 @@ static int gpmc_mem_init(void)
800 if (!gpmc_cs_mem_enabled(cs)) 804 if (!gpmc_cs_mem_enabled(cs))
801 continue; 805 continue;
802 gpmc_cs_get_memconf(cs, &base, &size); 806 gpmc_cs_get_memconf(cs, &base, &size);
803 rc = gpmc_cs_insert_mem(cs, base, size); 807 if (gpmc_cs_insert_mem(cs, base, size)) {
804 if (IS_ERR_VALUE(rc)) { 808 pr_warn("%s: disabling cs %d mapped at 0x%x-0x%x\n",
805 while (--cs >= 0) 809 __func__, cs, base, base + size);
806 if (gpmc_cs_mem_enabled(cs)) 810 gpmc_cs_disable_mem(cs);
807 gpmc_cs_delete_mem(cs);
808 return rc;
809 } 811 }
810 } 812 }
811
812 return 0;
813} 813}
814 814
815static u32 gpmc_round_ps_to_sync_clk(u32 time_ps, u32 sync_clk) 815static u32 gpmc_round_ps_to_sync_clk(u32 time_ps, u32 sync_clk)
@@ -825,9 +825,9 @@ static u32 gpmc_round_ps_to_sync_clk(u32 time_ps, u32 sync_clk)
825 825
826/* XXX: can the cycles be avoided ? */ 826/* XXX: can the cycles be avoided ? */
827static int gpmc_calc_sync_read_timings(struct gpmc_timings *gpmc_t, 827static int gpmc_calc_sync_read_timings(struct gpmc_timings *gpmc_t,
828 struct gpmc_device_timings *dev_t) 828 struct gpmc_device_timings *dev_t,
829 bool mux)
829{ 830{
830 bool mux = dev_t->mux;
831 u32 temp; 831 u32 temp;
832 832
833 /* adv_rd_off */ 833 /* adv_rd_off */
@@ -880,9 +880,9 @@ static int gpmc_calc_sync_read_timings(struct gpmc_timings *gpmc_t,
880} 880}
881 881
882static int gpmc_calc_sync_write_timings(struct gpmc_timings *gpmc_t, 882static int gpmc_calc_sync_write_timings(struct gpmc_timings *gpmc_t,
883 struct gpmc_device_timings *dev_t) 883 struct gpmc_device_timings *dev_t,
884 bool mux)
884{ 885{
885 bool mux = dev_t->mux;
886 u32 temp; 886 u32 temp;
887 887
888 /* adv_wr_off */ 888 /* adv_wr_off */
@@ -942,9 +942,9 @@ static int gpmc_calc_sync_write_timings(struct gpmc_timings *gpmc_t,
942} 942}
943 943
944static int gpmc_calc_async_read_timings(struct gpmc_timings *gpmc_t, 944static int gpmc_calc_async_read_timings(struct gpmc_timings *gpmc_t,
945 struct gpmc_device_timings *dev_t) 945 struct gpmc_device_timings *dev_t,
946 bool mux)
946{ 947{
947 bool mux = dev_t->mux;
948 u32 temp; 948 u32 temp;
949 949
950 /* adv_rd_off */ 950 /* adv_rd_off */
@@ -982,9 +982,9 @@ static int gpmc_calc_async_read_timings(struct gpmc_timings *gpmc_t,
982} 982}
983 983
984static int gpmc_calc_async_write_timings(struct gpmc_timings *gpmc_t, 984static int gpmc_calc_async_write_timings(struct gpmc_timings *gpmc_t,
985 struct gpmc_device_timings *dev_t) 985 struct gpmc_device_timings *dev_t,
986 bool mux)
986{ 987{
987 bool mux = dev_t->mux;
988 u32 temp; 988 u32 temp;
989 989
990 /* adv_wr_off */ 990 /* adv_wr_off */
@@ -1054,7 +1054,8 @@ static int gpmc_calc_sync_common_timings(struct gpmc_timings *gpmc_t,
1054} 1054}
1055 1055
1056static int gpmc_calc_common_timings(struct gpmc_timings *gpmc_t, 1056static int gpmc_calc_common_timings(struct gpmc_timings *gpmc_t,
1057 struct gpmc_device_timings *dev_t) 1057 struct gpmc_device_timings *dev_t,
1058 bool sync)
1058{ 1059{
1059 u32 temp; 1060 u32 temp;
1060 1061
@@ -1068,7 +1069,7 @@ static int gpmc_calc_common_timings(struct gpmc_timings *gpmc_t,
1068 gpmc_t->cs_on + dev_t->t_ce_avd); 1069 gpmc_t->cs_on + dev_t->t_ce_avd);
1069 gpmc_t->adv_on = gpmc_round_ps_to_ticks(temp); 1070 gpmc_t->adv_on = gpmc_round_ps_to_ticks(temp);
1070 1071
1071 if (dev_t->sync_write || dev_t->sync_read) 1072 if (sync)
1072 gpmc_calc_sync_common_timings(gpmc_t, dev_t); 1073 gpmc_calc_sync_common_timings(gpmc_t, dev_t);
1073 1074
1074 return 0; 1075 return 0;
@@ -1103,21 +1104,29 @@ static void gpmc_convert_ps_to_ns(struct gpmc_timings *t)
1103} 1104}
1104 1105
1105int gpmc_calc_timings(struct gpmc_timings *gpmc_t, 1106int gpmc_calc_timings(struct gpmc_timings *gpmc_t,
1106 struct gpmc_device_timings *dev_t) 1107 struct gpmc_settings *gpmc_s,
1108 struct gpmc_device_timings *dev_t)
1107{ 1109{
1110 bool mux = false, sync = false;
1111
1112 if (gpmc_s) {
1113 mux = gpmc_s->mux_add_data ? true : false;
1114 sync = (gpmc_s->sync_read || gpmc_s->sync_write);
1115 }
1116
1108 memset(gpmc_t, 0, sizeof(*gpmc_t)); 1117 memset(gpmc_t, 0, sizeof(*gpmc_t));
1109 1118
1110 gpmc_calc_common_timings(gpmc_t, dev_t); 1119 gpmc_calc_common_timings(gpmc_t, dev_t, sync);
1111 1120
1112 if (dev_t->sync_read) 1121 if (gpmc_s && gpmc_s->sync_read)
1113 gpmc_calc_sync_read_timings(gpmc_t, dev_t); 1122 gpmc_calc_sync_read_timings(gpmc_t, dev_t, mux);
1114 else 1123 else
1115 gpmc_calc_async_read_timings(gpmc_t, dev_t); 1124 gpmc_calc_async_read_timings(gpmc_t, dev_t, mux);
1116 1125
1117 if (dev_t->sync_write) 1126 if (gpmc_s && gpmc_s->sync_write)
1118 gpmc_calc_sync_write_timings(gpmc_t, dev_t); 1127 gpmc_calc_sync_write_timings(gpmc_t, dev_t, mux);
1119 else 1128 else
1120 gpmc_calc_async_write_timings(gpmc_t, dev_t); 1129 gpmc_calc_async_write_timings(gpmc_t, dev_t, mux);
1121 1130
1122 /* TODO: remove, see function definition */ 1131 /* TODO: remove, see function definition */
1123 gpmc_convert_ps_to_ns(gpmc_t); 1132 gpmc_convert_ps_to_ns(gpmc_t);
@@ -1125,6 +1134,90 @@ int gpmc_calc_timings(struct gpmc_timings *gpmc_t,
1125 return 0; 1134 return 0;
1126} 1135}
1127 1136
1137/**
1138 * gpmc_cs_program_settings - programs non-timing related settings
1139 * @cs: GPMC chip-select to program
1140 * @p: pointer to GPMC settings structure
1141 *
1142 * Programs non-timing related settings for a GPMC chip-select, such as
1143 * bus-width, burst configuration, etc. Function should be called once
1144 * for each chip-select that is being used and must be called before
1145 * calling gpmc_cs_set_timings() as timing parameters in the CONFIG1
1146 * register will be initialised to zero by this function. Returns 0 on
1147 * success and appropriate negative error code on failure.
1148 */
1149int gpmc_cs_program_settings(int cs, struct gpmc_settings *p)
1150{
1151 u32 config1;
1152
1153 if ((!p->device_width) || (p->device_width > GPMC_DEVWIDTH_16BIT)) {
1154 pr_err("%s: invalid width %d!", __func__, p->device_width);
1155 return -EINVAL;
1156 }
1157
1158 /* Address-data multiplexing not supported for NAND devices */
1159 if (p->device_nand && p->mux_add_data) {
1160 pr_err("%s: invalid configuration!\n", __func__);
1161 return -EINVAL;
1162 }
1163
1164 if ((p->mux_add_data > GPMC_MUX_AD) ||
1165 ((p->mux_add_data == GPMC_MUX_AAD) &&
1166 !(gpmc_capability & GPMC_HAS_MUX_AAD))) {
1167 pr_err("%s: invalid multiplex configuration!\n", __func__);
1168 return -EINVAL;
1169 }
1170
1171 /* Page/burst mode supports lengths of 4, 8 and 16 bytes */
1172 if (p->burst_read || p->burst_write) {
1173 switch (p->burst_len) {
1174 case GPMC_BURST_4:
1175 case GPMC_BURST_8:
1176 case GPMC_BURST_16:
1177 break;
1178 default:
1179 pr_err("%s: invalid page/burst-length (%d)\n",
1180 __func__, p->burst_len);
1181 return -EINVAL;
1182 }
1183 }
1184
1185 if ((p->wait_on_read || p->wait_on_write) &&
1186 (p->wait_pin > gpmc_nr_waitpins)) {
1187 pr_err("%s: invalid wait-pin (%d)\n", __func__, p->wait_pin);
1188 return -EINVAL;
1189 }
1190
1191 config1 = GPMC_CONFIG1_DEVICESIZE((p->device_width - 1));
1192
1193 if (p->sync_read)
1194 config1 |= GPMC_CONFIG1_READTYPE_SYNC;
1195 if (p->sync_write)
1196 config1 |= GPMC_CONFIG1_WRITETYPE_SYNC;
1197 if (p->wait_on_read)
1198 config1 |= GPMC_CONFIG1_WAIT_READ_MON;
1199 if (p->wait_on_write)
1200 config1 |= GPMC_CONFIG1_WAIT_WRITE_MON;
1201 if (p->wait_on_read || p->wait_on_write)
1202 config1 |= GPMC_CONFIG1_WAIT_PIN_SEL(p->wait_pin);
1203 if (p->device_nand)
1204 config1 |= GPMC_CONFIG1_DEVICETYPE(GPMC_DEVICETYPE_NAND);
1205 if (p->mux_add_data)
1206 config1 |= GPMC_CONFIG1_MUXTYPE(p->mux_add_data);
1207 if (p->burst_read)
1208 config1 |= GPMC_CONFIG1_READMULTIPLE_SUPP;
1209 if (p->burst_write)
1210 config1 |= GPMC_CONFIG1_WRITEMULTIPLE_SUPP;
1211 if (p->burst_read || p->burst_write) {
1212 config1 |= GPMC_CONFIG1_PAGE_LEN(p->burst_len >> 3);
1213 config1 |= p->burst_wrap ? GPMC_CONFIG1_WRAPBURST_SUPP : 0;
1214 }
1215
1216 gpmc_cs_write_reg(cs, GPMC_CS_CONFIG1, config1);
1217
1218 return 0;
1219}
1220
1128#ifdef CONFIG_OF 1221#ifdef CONFIG_OF
1129static struct of_device_id gpmc_dt_ids[] = { 1222static struct of_device_id gpmc_dt_ids[] = {
1130 { .compatible = "ti,omap2420-gpmc" }, 1223 { .compatible = "ti,omap2420-gpmc" },
@@ -1136,70 +1229,110 @@ static struct of_device_id gpmc_dt_ids[] = {
1136}; 1229};
1137MODULE_DEVICE_TABLE(of, gpmc_dt_ids); 1230MODULE_DEVICE_TABLE(of, gpmc_dt_ids);
1138 1231
1232/**
1233 * gpmc_read_settings_dt - read gpmc settings from device-tree
1234 * @np: pointer to device-tree node for a gpmc child device
1235 * @p: pointer to gpmc settings structure
1236 *
1237 * Reads the GPMC settings for a GPMC child device from device-tree and
1238 * stores them in the GPMC settings structure passed. The GPMC settings
1239 * structure is initialised to zero by this function and so any
1240 * previously stored settings will be cleared.
1241 */
1242void gpmc_read_settings_dt(struct device_node *np, struct gpmc_settings *p)
1243{
1244 memset(p, 0, sizeof(struct gpmc_settings));
1245
1246 p->sync_read = of_property_read_bool(np, "gpmc,sync-read");
1247 p->sync_write = of_property_read_bool(np, "gpmc,sync-write");
1248 p->device_nand = of_property_read_bool(np, "gpmc,device-nand");
1249 of_property_read_u32(np, "gpmc,device-width", &p->device_width);
1250 of_property_read_u32(np, "gpmc,mux-add-data", &p->mux_add_data);
1251
1252 if (!of_property_read_u32(np, "gpmc,burst-length", &p->burst_len)) {
1253 p->burst_wrap = of_property_read_bool(np, "gpmc,burst-wrap");
1254 p->burst_read = of_property_read_bool(np, "gpmc,burst-read");
1255 p->burst_write = of_property_read_bool(np, "gpmc,burst-write");
1256 if (!p->burst_read && !p->burst_write)
1257 pr_warn("%s: page/burst-length set but not used!\n",
1258 __func__);
1259 }
1260
1261 if (!of_property_read_u32(np, "gpmc,wait-pin", &p->wait_pin)) {
1262 p->wait_on_read = of_property_read_bool(np,
1263 "gpmc,wait-on-read");
1264 p->wait_on_write = of_property_read_bool(np,
1265 "gpmc,wait-on-write");
1266 if (!p->wait_on_read && !p->wait_on_write)
1267 pr_warn("%s: read/write wait monitoring not enabled!\n",
1268 __func__);
1269 }
1270}
1271
1139static void __maybe_unused gpmc_read_timings_dt(struct device_node *np, 1272static void __maybe_unused gpmc_read_timings_dt(struct device_node *np,
1140 struct gpmc_timings *gpmc_t) 1273 struct gpmc_timings *gpmc_t)
1141{ 1274{
1142 u32 val; 1275 struct gpmc_bool_timings *p;
1276
1277 if (!np || !gpmc_t)
1278 return;
1143 1279
1144 memset(gpmc_t, 0, sizeof(*gpmc_t)); 1280 memset(gpmc_t, 0, sizeof(*gpmc_t));
1145 1281
1146 /* minimum clock period for syncronous mode */ 1282 /* minimum clock period for syncronous mode */
1147 if (!of_property_read_u32(np, "gpmc,sync-clk", &val)) 1283 of_property_read_u32(np, "gpmc,sync-clk-ps", &gpmc_t->sync_clk);
1148 gpmc_t->sync_clk = val;
1149 1284
1150 /* chip select timtings */ 1285 /* chip select timtings */
1151 if (!of_property_read_u32(np, "gpmc,cs-on", &val)) 1286 of_property_read_u32(np, "gpmc,cs-on-ns", &gpmc_t->cs_on);
1152 gpmc_t->cs_on = val; 1287 of_property_read_u32(np, "gpmc,cs-rd-off-ns", &gpmc_t->cs_rd_off);
1153 1288 of_property_read_u32(np, "gpmc,cs-wr-off-ns", &gpmc_t->cs_wr_off);
1154 if (!of_property_read_u32(np, "gpmc,cs-rd-off", &val))
1155 gpmc_t->cs_rd_off = val;
1156
1157 if (!of_property_read_u32(np, "gpmc,cs-wr-off", &val))
1158 gpmc_t->cs_wr_off = val;
1159 1289
1160 /* ADV signal timings */ 1290 /* ADV signal timings */
1161 if (!of_property_read_u32(np, "gpmc,adv-on", &val)) 1291 of_property_read_u32(np, "gpmc,adv-on-ns", &gpmc_t->adv_on);
1162 gpmc_t->adv_on = val; 1292 of_property_read_u32(np, "gpmc,adv-rd-off-ns", &gpmc_t->adv_rd_off);
1163 1293 of_property_read_u32(np, "gpmc,adv-wr-off-ns", &gpmc_t->adv_wr_off);
1164 if (!of_property_read_u32(np, "gpmc,adv-rd-off", &val))
1165 gpmc_t->adv_rd_off = val;
1166
1167 if (!of_property_read_u32(np, "gpmc,adv-wr-off", &val))
1168 gpmc_t->adv_wr_off = val;
1169 1294
1170 /* WE signal timings */ 1295 /* WE signal timings */
1171 if (!of_property_read_u32(np, "gpmc,we-on", &val)) 1296 of_property_read_u32(np, "gpmc,we-on-ns", &gpmc_t->we_on);
1172 gpmc_t->we_on = val; 1297 of_property_read_u32(np, "gpmc,we-off-ns", &gpmc_t->we_off);
1173
1174 if (!of_property_read_u32(np, "gpmc,we-off", &val))
1175 gpmc_t->we_off = val;
1176 1298
1177 /* OE signal timings */ 1299 /* OE signal timings */
1178 if (!of_property_read_u32(np, "gpmc,oe-on", &val)) 1300 of_property_read_u32(np, "gpmc,oe-on-ns", &gpmc_t->oe_on);
1179 gpmc_t->oe_on = val; 1301 of_property_read_u32(np, "gpmc,oe-off-ns", &gpmc_t->oe_off);
1180
1181 if (!of_property_read_u32(np, "gpmc,oe-off", &val))
1182 gpmc_t->oe_off = val;
1183 1302
1184 /* access and cycle timings */ 1303 /* access and cycle timings */
1185 if (!of_property_read_u32(np, "gpmc,page-burst-access", &val)) 1304 of_property_read_u32(np, "gpmc,page-burst-access-ns",
1186 gpmc_t->page_burst_access = val; 1305 &gpmc_t->page_burst_access);
1187 1306 of_property_read_u32(np, "gpmc,access-ns", &gpmc_t->access);
1188 if (!of_property_read_u32(np, "gpmc,access", &val)) 1307 of_property_read_u32(np, "gpmc,rd-cycle-ns", &gpmc_t->rd_cycle);
1189 gpmc_t->access = val; 1308 of_property_read_u32(np, "gpmc,wr-cycle-ns", &gpmc_t->wr_cycle);
1190 1309 of_property_read_u32(np, "gpmc,bus-turnaround-ns",
1191 if (!of_property_read_u32(np, "gpmc,rd-cycle", &val)) 1310 &gpmc_t->bus_turnaround);
1192 gpmc_t->rd_cycle = val; 1311 of_property_read_u32(np, "gpmc,cycle2cycle-delay-ns",
1193 1312 &gpmc_t->cycle2cycle_delay);
1194 if (!of_property_read_u32(np, "gpmc,wr-cycle", &val)) 1313 of_property_read_u32(np, "gpmc,wait-monitoring-ns",
1195 gpmc_t->wr_cycle = val; 1314 &gpmc_t->wait_monitoring);
1196 1315 of_property_read_u32(np, "gpmc,clk-activation-ns",
1197 /* only for OMAP3430 */ 1316 &gpmc_t->clk_activation);
1198 if (!of_property_read_u32(np, "gpmc,wr-access", &val)) 1317
1199 gpmc_t->wr_access = val; 1318 /* only applicable to OMAP3+ */
1200 1319 of_property_read_u32(np, "gpmc,wr-access-ns", &gpmc_t->wr_access);
1201 if (!of_property_read_u32(np, "gpmc,wr-data-mux-bus", &val)) 1320 of_property_read_u32(np, "gpmc,wr-data-mux-bus-ns",
1202 gpmc_t->wr_data_mux_bus = val; 1321 &gpmc_t->wr_data_mux_bus);
1322
1323 /* bool timing parameters */
1324 p = &gpmc_t->bool_timings;
1325
1326 p->cycle2cyclediffcsen =
1327 of_property_read_bool(np, "gpmc,cycle2cycle-diffcsen");
1328 p->cycle2cyclesamecsen =
1329 of_property_read_bool(np, "gpmc,cycle2cycle-samecsen");
1330 p->we_extra_delay = of_property_read_bool(np, "gpmc,we-extra-delay");
1331 p->oe_extra_delay = of_property_read_bool(np, "gpmc,oe-extra-delay");
1332 p->adv_extra_delay = of_property_read_bool(np, "gpmc,adv-extra-delay");
1333 p->cs_extra_delay = of_property_read_bool(np, "gpmc,cs-extra-delay");
1334 p->time_para_granularity =
1335 of_property_read_bool(np, "gpmc,time-para-granularity");
1203} 1336}
1204 1337
1205#ifdef CONFIG_MTD_NAND 1338#ifdef CONFIG_MTD_NAND
@@ -1295,6 +1428,81 @@ static int gpmc_probe_onenand_child(struct platform_device *pdev,
1295} 1428}
1296#endif 1429#endif
1297 1430
1431/**
1432 * gpmc_probe_generic_child - configures the gpmc for a child device
1433 * @pdev: pointer to gpmc platform device
1434 * @child: pointer to device-tree node for child device
1435 *
1436 * Allocates and configures a GPMC chip-select for a child device.
1437 * Returns 0 on success and appropriate negative error code on failure.
1438 */
1439static int gpmc_probe_generic_child(struct platform_device *pdev,
1440 struct device_node *child)
1441{
1442 struct gpmc_settings gpmc_s;
1443 struct gpmc_timings gpmc_t;
1444 struct resource res;
1445 unsigned long base;
1446 int ret, cs;
1447
1448 if (of_property_read_u32(child, "reg", &cs) < 0) {
1449 dev_err(&pdev->dev, "%s has no 'reg' property\n",
1450 child->full_name);
1451 return -ENODEV;
1452 }
1453
1454 if (of_address_to_resource(child, 0, &res) < 0) {
1455 dev_err(&pdev->dev, "%s has malformed 'reg' property\n",
1456 child->full_name);
1457 return -ENODEV;
1458 }
1459
1460 ret = gpmc_cs_request(cs, resource_size(&res), &base);
1461 if (ret < 0) {
1462 dev_err(&pdev->dev, "cannot request GPMC CS %d\n", cs);
1463 return ret;
1464 }
1465
1466 /*
1467 * FIXME: gpmc_cs_request() will map the CS to an arbitary
1468 * location in the gpmc address space. When booting with
1469 * device-tree we want the NOR flash to be mapped to the
1470 * location specified in the device-tree blob. So remap the
1471 * CS to this location. Once DT migration is complete should
1472 * just make gpmc_cs_request() map a specific address.
1473 */
1474 ret = gpmc_cs_remap(cs, res.start);
1475 if (ret < 0) {
1476 dev_err(&pdev->dev, "cannot remap GPMC CS %d to 0x%x\n",
1477 cs, res.start);
1478 goto err;
1479 }
1480
1481 gpmc_read_settings_dt(child, &gpmc_s);
1482
1483 ret = of_property_read_u32(child, "bank-width", &gpmc_s.device_width);
1484 if (ret < 0)
1485 goto err;
1486
1487 ret = gpmc_cs_program_settings(cs, &gpmc_s);
1488 if (ret < 0)
1489 goto err;
1490
1491 gpmc_read_timings_dt(child, &gpmc_t);
1492 gpmc_cs_set_timings(cs, &gpmc_t);
1493
1494 if (of_platform_device_create(child, NULL, &pdev->dev))
1495 return 0;
1496
1497 dev_err(&pdev->dev, "failed to create gpmc child %s\n", child->name);
1498 ret = -ENODEV;
1499
1500err:
1501 gpmc_cs_free(cs);
1502
1503 return ret;
1504}
1505
1298static int gpmc_probe_dt(struct platform_device *pdev) 1506static int gpmc_probe_dt(struct platform_device *pdev)
1299{ 1507{
1300 int ret; 1508 int ret;
@@ -1305,6 +1513,13 @@ static int gpmc_probe_dt(struct platform_device *pdev)
1305 if (!of_id) 1513 if (!of_id)
1306 return 0; 1514 return 0;
1307 1515
1516 ret = of_property_read_u32(pdev->dev.of_node, "gpmc,num-waitpins",
1517 &gpmc_nr_waitpins);
1518 if (ret < 0) {
1519 pr_err("%s: number of wait pins not found!\n", __func__);
1520 return ret;
1521 }
1522
1308 for_each_node_by_name(child, "nand") { 1523 for_each_node_by_name(child, "nand") {
1309 ret = gpmc_probe_nand_child(pdev, child); 1524 ret = gpmc_probe_nand_child(pdev, child);
1310 if (ret < 0) { 1525 if (ret < 0) {
@@ -1320,6 +1535,23 @@ static int gpmc_probe_dt(struct platform_device *pdev)
1320 return ret; 1535 return ret;
1321 } 1536 }
1322 } 1537 }
1538
1539 for_each_node_by_name(child, "nor") {
1540 ret = gpmc_probe_generic_child(pdev, child);
1541 if (ret < 0) {
1542 of_node_put(child);
1543 return ret;
1544 }
1545 }
1546
1547 for_each_node_by_name(child, "ethernet") {
1548 ret = gpmc_probe_generic_child(pdev, child);
1549 if (ret < 0) {
1550 of_node_put(child);
1551 return ret;
1552 }
1553 }
1554
1323 return 0; 1555 return 0;
1324} 1556}
1325#else 1557#else
@@ -1364,25 +1596,37 @@ static int gpmc_probe(struct platform_device *pdev)
1364 gpmc_dev = &pdev->dev; 1596 gpmc_dev = &pdev->dev;
1365 1597
1366 l = gpmc_read_reg(GPMC_REVISION); 1598 l = gpmc_read_reg(GPMC_REVISION);
1599
1600 /*
1601 * FIXME: Once device-tree migration is complete the below flags
1602 * should be populated based upon the device-tree compatible
1603 * string. For now just use the IP revision. OMAP3+ devices have
1604 * the wr_access and wr_data_mux_bus register fields. OMAP4+
1605 * devices support the addr-addr-data multiplex protocol.
1606 *
1607 * GPMC IP revisions:
1608 * - OMAP24xx = 2.0
1609 * - OMAP3xxx = 5.0
1610 * - OMAP44xx/54xx/AM335x = 6.0
1611 */
1367 if (GPMC_REVISION_MAJOR(l) > 0x4) 1612 if (GPMC_REVISION_MAJOR(l) > 0x4)
1368 gpmc_capability = GPMC_HAS_WR_ACCESS | GPMC_HAS_WR_DATA_MUX_BUS; 1613 gpmc_capability = GPMC_HAS_WR_ACCESS | GPMC_HAS_WR_DATA_MUX_BUS;
1614 if (GPMC_REVISION_MAJOR(l) > 0x5)
1615 gpmc_capability |= GPMC_HAS_MUX_AAD;
1369 dev_info(gpmc_dev, "GPMC revision %d.%d\n", GPMC_REVISION_MAJOR(l), 1616 dev_info(gpmc_dev, "GPMC revision %d.%d\n", GPMC_REVISION_MAJOR(l),
1370 GPMC_REVISION_MINOR(l)); 1617 GPMC_REVISION_MINOR(l));
1371 1618
1372 rc = gpmc_mem_init(); 1619 gpmc_mem_init();
1373 if (IS_ERR_VALUE(rc)) {
1374 clk_disable_unprepare(gpmc_l3_clk);
1375 clk_put(gpmc_l3_clk);
1376 dev_err(gpmc_dev, "failed to reserve memory\n");
1377 return rc;
1378 }
1379 1620
1380 if (IS_ERR_VALUE(gpmc_setup_irq())) 1621 if (gpmc_setup_irq() < 0)
1381 dev_warn(gpmc_dev, "gpmc_setup_irq failed\n"); 1622 dev_warn(gpmc_dev, "gpmc_setup_irq failed\n");
1382 1623
1383 /* Now the GPMC is initialised, unreserve the chip-selects */ 1624 /* Now the GPMC is initialised, unreserve the chip-selects */
1384 gpmc_cs_map = 0; 1625 gpmc_cs_map = 0;
1385 1626
1627 if (!pdev->dev.of_node)
1628 gpmc_nr_waitpins = GPMC_NR_WAITPINS;
1629
1386 rc = gpmc_probe_dt(pdev); 1630 rc = gpmc_probe_dt(pdev);
1387 if (rc < 0) { 1631 if (rc < 0) {
1388 clk_disable_unprepare(gpmc_l3_clk); 1632 clk_disable_unprepare(gpmc_l3_clk);
diff --git a/arch/arm/mach-omap2/gpmc.h b/arch/arm/mach-omap2/gpmc.h
index fe0a844d5007..707f6d58edd5 100644
--- a/arch/arm/mach-omap2/gpmc.h
+++ b/arch/arm/mach-omap2/gpmc.h
@@ -58,7 +58,7 @@
58#define GPMC_CONFIG1_DEVICESIZE_16 GPMC_CONFIG1_DEVICESIZE(1) 58#define GPMC_CONFIG1_DEVICESIZE_16 GPMC_CONFIG1_DEVICESIZE(1)
59#define GPMC_CONFIG1_DEVICETYPE(val) ((val & 3) << 10) 59#define GPMC_CONFIG1_DEVICETYPE(val) ((val & 3) << 10)
60#define GPMC_CONFIG1_DEVICETYPE_NOR GPMC_CONFIG1_DEVICETYPE(0) 60#define GPMC_CONFIG1_DEVICETYPE_NOR GPMC_CONFIG1_DEVICETYPE(0)
61#define GPMC_CONFIG1_MUXADDDATA (1 << 9) 61#define GPMC_CONFIG1_MUXTYPE(val) ((val & 3) << 8)
62#define GPMC_CONFIG1_TIME_PARA_GRAN (1 << 4) 62#define GPMC_CONFIG1_TIME_PARA_GRAN (1 << 4)
63#define GPMC_CONFIG1_FCLK_DIV(val) (val & 3) 63#define GPMC_CONFIG1_FCLK_DIV(val) (val & 3)
64#define GPMC_CONFIG1_FCLK_DIV2 (GPMC_CONFIG1_FCLK_DIV(1)) 64#define GPMC_CONFIG1_FCLK_DIV2 (GPMC_CONFIG1_FCLK_DIV(1))
@@ -73,6 +73,13 @@
73#define GPMC_IRQ_FIFOEVENTENABLE 0x01 73#define GPMC_IRQ_FIFOEVENTENABLE 0x01
74#define GPMC_IRQ_COUNT_EVENT 0x02 74#define GPMC_IRQ_COUNT_EVENT 0x02
75 75
76#define GPMC_BURST_4 4 /* 4 word burst */
77#define GPMC_BURST_8 8 /* 8 word burst */
78#define GPMC_BURST_16 16 /* 16 word burst */
79#define GPMC_DEVWIDTH_8BIT 1 /* 8-bit device width */
80#define GPMC_DEVWIDTH_16BIT 2 /* 16-bit device width */
81#define GPMC_MUX_AAD 1 /* Addr-Addr-Data multiplex */
82#define GPMC_MUX_AD 2 /* Addr-Data multiplex */
76 83
77/* bool type time settings */ 84/* bool type time settings */
78struct gpmc_bool_timings { 85struct gpmc_bool_timings {
@@ -178,10 +185,6 @@ struct gpmc_device_timings {
178 u8 cyc_wpl; /* write deassertion time in cycles */ 185 u8 cyc_wpl; /* write deassertion time in cycles */
179 u32 cyc_iaa; /* initial access time in cycles */ 186 u32 cyc_iaa; /* initial access time in cycles */
180 187
181 bool mux; /* address & data muxed */
182 bool sync_write;/* synchronous write */
183 bool sync_read; /* synchronous read */
184
185 /* extra delays */ 188 /* extra delays */
186 bool ce_xdelay; 189 bool ce_xdelay;
187 bool avd_xdelay; 190 bool avd_xdelay;
@@ -189,28 +192,40 @@ struct gpmc_device_timings {
189 bool we_xdelay; 192 bool we_xdelay;
190}; 193};
191 194
195struct gpmc_settings {
196 bool burst_wrap; /* enables wrap bursting */
197 bool burst_read; /* enables read page/burst mode */
198 bool burst_write; /* enables write page/burst mode */
199 bool device_nand; /* device is NAND */
200 bool sync_read; /* enables synchronous reads */
201 bool sync_write; /* enables synchronous writes */
202 bool wait_on_read; /* monitor wait on reads */
203 bool wait_on_write; /* monitor wait on writes */
204 u32 burst_len; /* page/burst length */
205 u32 device_width; /* device bus width (8 or 16 bit) */
206 u32 mux_add_data; /* multiplex address & data */
207 u32 wait_pin; /* wait-pin to be used */
208};
209
192extern int gpmc_calc_timings(struct gpmc_timings *gpmc_t, 210extern int gpmc_calc_timings(struct gpmc_timings *gpmc_t,
193 struct gpmc_device_timings *dev_t); 211 struct gpmc_settings *gpmc_s,
212 struct gpmc_device_timings *dev_t);
194 213
195extern void gpmc_update_nand_reg(struct gpmc_nand_regs *reg, int cs); 214extern void gpmc_update_nand_reg(struct gpmc_nand_regs *reg, int cs);
196extern int gpmc_get_client_irq(unsigned irq_config); 215extern int gpmc_get_client_irq(unsigned irq_config);
197 216
198extern unsigned int gpmc_ns_to_ticks(unsigned int time_ns);
199extern unsigned int gpmc_ps_to_ticks(unsigned int time_ps);
200extern unsigned int gpmc_ticks_to_ns(unsigned int ticks); 217extern unsigned int gpmc_ticks_to_ns(unsigned int ticks);
201extern unsigned int gpmc_round_ns_to_ticks(unsigned int time_ns);
202extern unsigned long gpmc_get_fclk_period(void);
203 218
204extern void gpmc_cs_write_reg(int cs, int idx, u32 val); 219extern void gpmc_cs_write_reg(int cs, int idx, u32 val);
205extern u32 gpmc_cs_read_reg(int cs, int idx);
206extern int gpmc_calc_divider(unsigned int sync_clk); 220extern int gpmc_calc_divider(unsigned int sync_clk);
207extern int gpmc_cs_set_timings(int cs, const struct gpmc_timings *t); 221extern int gpmc_cs_set_timings(int cs, const struct gpmc_timings *t);
222extern int gpmc_cs_program_settings(int cs, struct gpmc_settings *p);
208extern int gpmc_cs_request(int cs, unsigned long size, unsigned long *base); 223extern int gpmc_cs_request(int cs, unsigned long size, unsigned long *base);
209extern void gpmc_cs_free(int cs); 224extern void gpmc_cs_free(int cs);
210extern int gpmc_cs_set_reserved(int cs, int reserved);
211extern int gpmc_cs_reserved(int cs);
212extern void omap3_gpmc_save_context(void); 225extern void omap3_gpmc_save_context(void);
213extern void omap3_gpmc_restore_context(void); 226extern void omap3_gpmc_restore_context(void);
214extern int gpmc_cs_configure(int cs, int cmd, int wval); 227extern int gpmc_configure(int cmd, int wval);
228extern void gpmc_read_settings_dt(struct device_node *np,
229 struct gpmc_settings *p);
215 230
216#endif 231#endif
diff --git a/arch/arm/mach-omap2/omap_device.c b/arch/arm/mach-omap2/omap_device.c
index 381be7ac0c17..eeea4fa28fbc 100644
--- a/arch/arm/mach-omap2/omap_device.c
+++ b/arch/arm/mach-omap2/omap_device.c
@@ -131,7 +131,7 @@ static int omap_device_build_from_dt(struct platform_device *pdev)
131 int oh_cnt, i, ret = 0; 131 int oh_cnt, i, ret = 0;
132 132
133 oh_cnt = of_property_count_strings(node, "ti,hwmods"); 133 oh_cnt = of_property_count_strings(node, "ti,hwmods");
134 if (!oh_cnt || IS_ERR_VALUE(oh_cnt)) { 134 if (oh_cnt <= 0) {
135 dev_dbg(&pdev->dev, "No 'hwmods' to build omap_device\n"); 135 dev_dbg(&pdev->dev, "No 'hwmods' to build omap_device\n");
136 return -ENODEV; 136 return -ENODEV;
137 } 137 }
@@ -815,20 +815,17 @@ struct device *omap_device_get_by_hwmod_name(const char *oh_name)
815 } 815 }
816 816
817 oh = omap_hwmod_lookup(oh_name); 817 oh = omap_hwmod_lookup(oh_name);
818 if (IS_ERR_OR_NULL(oh)) { 818 if (!oh) {
819 WARN(1, "%s: no hwmod for %s\n", __func__, 819 WARN(1, "%s: no hwmod for %s\n", __func__,
820 oh_name); 820 oh_name);
821 return ERR_PTR(oh ? PTR_ERR(oh) : -ENODEV); 821 return ERR_PTR(-ENODEV);
822 } 822 }
823 if (IS_ERR_OR_NULL(oh->od)) { 823 if (!oh->od) {
824 WARN(1, "%s: no omap_device for %s\n", __func__, 824 WARN(1, "%s: no omap_device for %s\n", __func__,
825 oh_name); 825 oh_name);
826 return ERR_PTR(oh->od ? PTR_ERR(oh->od) : -ENODEV); 826 return ERR_PTR(-ENODEV);
827 } 827 }
828 828
829 if (IS_ERR_OR_NULL(oh->od->pdev))
830 return ERR_PTR(oh->od->pdev ? PTR_ERR(oh->od->pdev) : -ENODEV);
831
832 return &oh->od->pdev->dev; 829 return &oh->od->pdev->dev;
833} 830}
834 831
diff --git a/arch/arm/mach-omap2/omap_hwmod.c b/arch/arm/mach-omap2/omap_hwmod.c
index 5f33c2da6999..3f50f680372e 100644
--- a/arch/arm/mach-omap2/omap_hwmod.c
+++ b/arch/arm/mach-omap2/omap_hwmod.c
@@ -1662,7 +1662,7 @@ static int _deassert_hardreset(struct omap_hwmod *oh, const char *name)
1662 return -ENOSYS; 1662 return -ENOSYS;
1663 1663
1664 ret = _lookup_hardreset(oh, name, &ohri); 1664 ret = _lookup_hardreset(oh, name, &ohri);
1665 if (IS_ERR_VALUE(ret)) 1665 if (ret < 0)
1666 return ret; 1666 return ret;
1667 1667
1668 if (oh->clkdm) { 1668 if (oh->clkdm) {
@@ -2412,7 +2412,7 @@ static int __init _init(struct omap_hwmod *oh, void *data)
2412 _init_mpu_rt_base(oh, NULL); 2412 _init_mpu_rt_base(oh, NULL);
2413 2413
2414 r = _init_clocks(oh, NULL); 2414 r = _init_clocks(oh, NULL);
2415 if (IS_ERR_VALUE(r)) { 2415 if (r < 0) {
2416 WARN(1, "omap_hwmod: %s: couldn't init clocks\n", oh->name); 2416 WARN(1, "omap_hwmod: %s: couldn't init clocks\n", oh->name);
2417 return -EINVAL; 2417 return -EINVAL;
2418 } 2418 }
diff --git a/arch/arm/mach-omap2/pm-debug.c b/arch/arm/mach-omap2/pm-debug.c
index 1edd000a8143..0b339861d751 100644
--- a/arch/arm/mach-omap2/pm-debug.c
+++ b/arch/arm/mach-omap2/pm-debug.c
@@ -217,7 +217,7 @@ static int __init pwrdms_setup(struct powerdomain *pwrdm, void *dir)
217 return 0; 217 return 0;
218 218
219 d = debugfs_create_dir(pwrdm->name, (struct dentry *)dir); 219 d = debugfs_create_dir(pwrdm->name, (struct dentry *)dir);
220 if (!(IS_ERR_OR_NULL(d))) 220 if (d)
221 (void) debugfs_create_file("suspend", S_IRUGO|S_IWUSR, d, 221 (void) debugfs_create_file("suspend", S_IRUGO|S_IWUSR, d,
222 (void *)pwrdm, &pwrdm_suspend_fops); 222 (void *)pwrdm, &pwrdm_suspend_fops);
223 223
@@ -261,8 +261,8 @@ static int __init pm_dbg_init(void)
261 return 0; 261 return 0;
262 262
263 d = debugfs_create_dir("pm_debug", NULL); 263 d = debugfs_create_dir("pm_debug", NULL);
264 if (IS_ERR_OR_NULL(d)) 264 if (!d)
265 return PTR_ERR(d); 265 return -EINVAL;
266 266
267 (void) debugfs_create_file("count", S_IRUGO, 267 (void) debugfs_create_file("count", S_IRUGO,
268 d, (void *)DEBUG_FILE_COUNTERS, &debug_fops); 268 d, (void *)DEBUG_FILE_COUNTERS, &debug_fops);
diff --git a/arch/arm/mach-omap2/powerdomain.c b/arch/arm/mach-omap2/powerdomain.c
index 89cad4a605dd..86babd740d41 100644
--- a/arch/arm/mach-omap2/powerdomain.c
+++ b/arch/arm/mach-omap2/powerdomain.c
@@ -1180,7 +1180,7 @@ bool pwrdm_can_ever_lose_context(struct powerdomain *pwrdm)
1180{ 1180{
1181 int i; 1181 int i;
1182 1182
1183 if (IS_ERR_OR_NULL(pwrdm)) { 1183 if (!pwrdm) {
1184 pr_debug("powerdomain: %s: invalid powerdomain pointer\n", 1184 pr_debug("powerdomain: %s: invalid powerdomain pointer\n",
1185 __func__); 1185 __func__);
1186 return 1; 1186 return 1;
diff --git a/arch/arm/mach-omap2/timer.c b/arch/arm/mach-omap2/timer.c
index d00d89c93f1c..fdf1c039062c 100644
--- a/arch/arm/mach-omap2/timer.c
+++ b/arch/arm/mach-omap2/timer.c
@@ -46,7 +46,6 @@
46#include <asm/smp_twd.h> 46#include <asm/smp_twd.h>
47#include <asm/sched_clock.h> 47#include <asm/sched_clock.h>
48 48
49#include <asm/arch_timer.h>
50#include "omap_hwmod.h" 49#include "omap_hwmod.h"
51#include "omap_device.h" 50#include "omap_device.h"
52#include <plat/counter-32k.h> 51#include <plat/counter-32k.h>
@@ -57,16 +56,6 @@
57#include "common.h" 56#include "common.h"
58#include "powerdomain.h" 57#include "powerdomain.h"
59 58
60/* Parent clocks, eventually these will come from the clock framework */
61
62#define OMAP2_MPU_SOURCE "sys_ck"
63#define OMAP3_MPU_SOURCE OMAP2_MPU_SOURCE
64#define OMAP4_MPU_SOURCE "sys_clkin_ck"
65#define OMAP5_MPU_SOURCE "sys_clkin"
66#define OMAP2_32K_SOURCE "func_32k_ck"
67#define OMAP3_32K_SOURCE "omap_32k_fck"
68#define OMAP4_32K_SOURCE "sys_32k_ck"
69
70#define REALTIME_COUNTER_BASE 0x48243200 59#define REALTIME_COUNTER_BASE 0x48243200
71#define INCREMENTER_NUMERATOR_OFFSET 0x10 60#define INCREMENTER_NUMERATOR_OFFSET 0x10
72#define INCREMENTER_DENUMERATOR_RELOAD_OFFSET 0x14 61#define INCREMENTER_DENUMERATOR_RELOAD_OFFSET 0x14
@@ -130,7 +119,6 @@ static void omap2_gp_timer_set_mode(enum clock_event_mode mode,
130} 119}
131 120
132static struct clock_event_device clockevent_gpt = { 121static struct clock_event_device clockevent_gpt = {
133 .name = "gp_timer",
134 .features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT, 122 .features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT,
135 .rating = 300, 123 .rating = 300,
136 .set_next_event = omap2_gp_timer_set_next_event, 124 .set_next_event = omap2_gp_timer_set_next_event,
@@ -171,6 +159,12 @@ static struct device_node * __init omap_get_timer_dt(struct of_device_id *match,
171 if (property && !of_get_property(np, property, NULL)) 159 if (property && !of_get_property(np, property, NULL))
172 continue; 160 continue;
173 161
162 if (!property && (of_get_property(np, "ti,timer-alwon", NULL) ||
163 of_get_property(np, "ti,timer-dsp", NULL) ||
164 of_get_property(np, "ti,timer-pwm", NULL) ||
165 of_get_property(np, "ti,timer-secure", NULL)))
166 continue;
167
174 of_add_property(np, &device_disabled); 168 of_add_property(np, &device_disabled);
175 return np; 169 return np;
176 } 170 }
@@ -215,16 +209,17 @@ static u32 __init omap_dm_timer_get_errata(void)
215} 209}
216 210
217static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer, 211static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
218 int gptimer_id, 212 const char *fck_source,
219 const char *fck_source, 213 const char *property,
220 const char *property, 214 const char **timer_name,
221 int posted) 215 int posted)
222{ 216{
223 char name[10]; /* 10 = sizeof("gptXX_Xck0") */ 217 char name[10]; /* 10 = sizeof("gptXX_Xck0") */
224 const char *oh_name; 218 const char *oh_name;
225 struct device_node *np; 219 struct device_node *np;
226 struct omap_hwmod *oh; 220 struct omap_hwmod *oh;
227 struct resource irq, mem; 221 struct resource irq, mem;
222 struct clk *src;
228 int r = 0; 223 int r = 0;
229 224
230 if (of_have_populated_dt()) { 225 if (of_have_populated_dt()) {
@@ -244,10 +239,10 @@ static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
244 239
245 of_node_put(np); 240 of_node_put(np);
246 } else { 241 } else {
247 if (omap_dm_timer_reserve_systimer(gptimer_id)) 242 if (omap_dm_timer_reserve_systimer(timer->id))
248 return -ENODEV; 243 return -ENODEV;
249 244
250 sprintf(name, "timer%d", gptimer_id); 245 sprintf(name, "timer%d", timer->id);
251 oh_name = name; 246 oh_name = name;
252 } 247 }
253 248
@@ -255,6 +250,8 @@ static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
255 if (!oh) 250 if (!oh)
256 return -ENODEV; 251 return -ENODEV;
257 252
253 *timer_name = oh->name;
254
258 if (!of_have_populated_dt()) { 255 if (!of_have_populated_dt()) {
259 r = omap_hwmod_get_resource_byname(oh, IORESOURCE_IRQ, NULL, 256 r = omap_hwmod_get_resource_byname(oh, IORESOURCE_IRQ, NULL,
260 &irq); 257 &irq);
@@ -277,24 +274,24 @@ static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
277 /* After the dmtimer is using hwmod these clocks won't be needed */ 274 /* After the dmtimer is using hwmod these clocks won't be needed */
278 timer->fclk = clk_get(NULL, omap_hwmod_get_main_clk(oh)); 275 timer->fclk = clk_get(NULL, omap_hwmod_get_main_clk(oh));
279 if (IS_ERR(timer->fclk)) 276 if (IS_ERR(timer->fclk))
280 return -ENODEV; 277 return PTR_ERR(timer->fclk);
281 278
282 /* FIXME: Need to remove hard-coded test on timer ID */ 279 src = clk_get(NULL, fck_source);
283 if (gptimer_id != 12) { 280 if (IS_ERR(src))
284 struct clk *src; 281 return PTR_ERR(src);
285 282
286 src = clk_get(NULL, fck_source); 283 if (clk_get_parent(timer->fclk) != src) {
287 if (IS_ERR(src)) { 284 r = clk_set_parent(timer->fclk, src);
288 r = -EINVAL; 285 if (r < 0) {
289 } else { 286 pr_warn("%s: %s cannot set source\n", __func__,
290 r = clk_set_parent(timer->fclk, src); 287 oh->name);
291 if (IS_ERR_VALUE(r))
292 pr_warn("%s: %s cannot set source\n",
293 __func__, oh->name);
294 clk_put(src); 288 clk_put(src);
289 return r;
295 } 290 }
296 } 291 }
297 292
293 clk_put(src);
294
298 omap_hwmod_setup_one(oh_name); 295 omap_hwmod_setup_one(oh_name);
299 omap_hwmod_enable(oh); 296 omap_hwmod_enable(oh);
300 __omap_dm_timer_init_regs(timer); 297 __omap_dm_timer_init_regs(timer);
@@ -318,6 +315,7 @@ static void __init omap2_gp_clockevent_init(int gptimer_id,
318{ 315{
319 int res; 316 int res;
320 317
318 clkev.id = gptimer_id;
321 clkev.errata = omap_dm_timer_get_errata(); 319 clkev.errata = omap_dm_timer_get_errata();
322 320
323 /* 321 /*
@@ -327,8 +325,8 @@ static void __init omap2_gp_clockevent_init(int gptimer_id,
327 */ 325 */
328 __omap_dm_timer_override_errata(&clkev, OMAP_TIMER_ERRATA_I103_I767); 326 __omap_dm_timer_override_errata(&clkev, OMAP_TIMER_ERRATA_I103_I767);
329 327
330 res = omap_dm_timer_init_one(&clkev, gptimer_id, fck_source, property, 328 res = omap_dm_timer_init_one(&clkev, fck_source, property,
331 OMAP_TIMER_POSTED); 329 &clockevent_gpt.name, OMAP_TIMER_POSTED);
332 BUG_ON(res); 330 BUG_ON(res);
333 331
334 omap2_gp_timer_irq.dev_id = &clkev; 332 omap2_gp_timer_irq.dev_id = &clkev;
@@ -342,8 +340,8 @@ static void __init omap2_gp_clockevent_init(int gptimer_id,
342 3, /* Timer internal resynch latency */ 340 3, /* Timer internal resynch latency */
343 0xffffffff); 341 0xffffffff);
344 342
345 pr_info("OMAP clockevent source: GPTIMER%d at %lu Hz\n", 343 pr_info("OMAP clockevent source: %s at %lu Hz\n", clockevent_gpt.name,
346 gptimer_id, clkev.rate); 344 clkev.rate);
347} 345}
348 346
349/* Clocksource code */ 347/* Clocksource code */
@@ -360,7 +358,6 @@ static cycle_t clocksource_read_cycles(struct clocksource *cs)
360} 358}
361 359
362static struct clocksource clocksource_gpt = { 360static struct clocksource clocksource_gpt = {
363 .name = "gp_timer",
364 .rating = 300, 361 .rating = 300,
365 .read = clocksource_read_cycles, 362 .read = clocksource_read_cycles,
366 .mask = CLOCKSOURCE_MASK(32), 363 .mask = CLOCKSOURCE_MASK(32),
@@ -443,13 +440,16 @@ static int __init __maybe_unused omap2_sync32k_clocksource_init(void)
443} 440}
444 441
445static void __init omap2_gptimer_clocksource_init(int gptimer_id, 442static void __init omap2_gptimer_clocksource_init(int gptimer_id,
446 const char *fck_source) 443 const char *fck_source,
444 const char *property)
447{ 445{
448 int res; 446 int res;
449 447
448 clksrc.id = gptimer_id;
450 clksrc.errata = omap_dm_timer_get_errata(); 449 clksrc.errata = omap_dm_timer_get_errata();
451 450
452 res = omap_dm_timer_init_one(&clksrc, gptimer_id, fck_source, NULL, 451 res = omap_dm_timer_init_one(&clksrc, fck_source, property,
452 &clocksource_gpt.name,
453 OMAP_TIMER_NONPOSTED); 453 OMAP_TIMER_NONPOSTED);
454 BUG_ON(res); 454 BUG_ON(res);
455 455
@@ -462,8 +462,8 @@ static void __init omap2_gptimer_clocksource_init(int gptimer_id,
462 pr_err("Could not register clocksource %s\n", 462 pr_err("Could not register clocksource %s\n",
463 clocksource_gpt.name); 463 clocksource_gpt.name);
464 else 464 else
465 pr_info("OMAP clocksource: GPTIMER%d at %lu Hz\n", 465 pr_info("OMAP clocksource: %s at %lu Hz\n",
466 gptimer_id, clksrc.rate); 466 clocksource_gpt.name, clksrc.rate);
467} 467}
468 468
469#ifdef CONFIG_SOC_HAS_REALTIME_COUNTER 469#ifdef CONFIG_SOC_HAS_REALTIME_COUNTER
@@ -488,7 +488,7 @@ static void __init realtime_counter_init(void)
488 pr_err("%s: ioremap failed\n", __func__); 488 pr_err("%s: ioremap failed\n", __func__);
489 return; 489 return;
490 } 490 }
491 sys_clk = clk_get(NULL, OMAP5_MPU_SOURCE); 491 sys_clk = clk_get(NULL, "sys_clkin");
492 if (IS_ERR(sys_clk)) { 492 if (IS_ERR(sys_clk)) {
493 pr_err("%s: failed to get system clock handle\n", __func__); 493 pr_err("%s: failed to get system clock handle\n", __func__);
494 iounmap(base); 494 iounmap(base);
@@ -545,18 +545,19 @@ static inline void __init realtime_counter_init(void)
545#endif 545#endif
546 546
547#define OMAP_SYS_GP_TIMER_INIT(name, clkev_nr, clkev_src, clkev_prop, \ 547#define OMAP_SYS_GP_TIMER_INIT(name, clkev_nr, clkev_src, clkev_prop, \
548 clksrc_nr, clksrc_src) \ 548 clksrc_nr, clksrc_src, clksrc_prop) \
549void __init omap##name##_gptimer_timer_init(void) \ 549void __init omap##name##_gptimer_timer_init(void) \
550{ \ 550{ \
551 if (omap_clk_init) \ 551 if (omap_clk_init) \
552 omap_clk_init(); \ 552 omap_clk_init(); \
553 omap_dmtimer_init(); \ 553 omap_dmtimer_init(); \
554 omap2_gp_clockevent_init((clkev_nr), clkev_src, clkev_prop); \ 554 omap2_gp_clockevent_init((clkev_nr), clkev_src, clkev_prop); \
555 omap2_gptimer_clocksource_init((clksrc_nr), clksrc_src); \ 555 omap2_gptimer_clocksource_init((clksrc_nr), clksrc_src, \
556 clksrc_prop); \
556} 557}
557 558
558#define OMAP_SYS_32K_TIMER_INIT(name, clkev_nr, clkev_src, clkev_prop, \ 559#define OMAP_SYS_32K_TIMER_INIT(name, clkev_nr, clkev_src, clkev_prop, \
559 clksrc_nr, clksrc_src) \ 560 clksrc_nr, clksrc_src, clksrc_prop) \
560void __init omap##name##_sync32k_timer_init(void) \ 561void __init omap##name##_sync32k_timer_init(void) \
561{ \ 562{ \
562 if (omap_clk_init) \ 563 if (omap_clk_init) \
@@ -565,33 +566,35 @@ void __init omap##name##_sync32k_timer_init(void) \
565 omap2_gp_clockevent_init((clkev_nr), clkev_src, clkev_prop); \ 566 omap2_gp_clockevent_init((clkev_nr), clkev_src, clkev_prop); \
566 /* Enable the use of clocksource="gp_timer" kernel parameter */ \ 567 /* Enable the use of clocksource="gp_timer" kernel parameter */ \
567 if (use_gptimer_clksrc) \ 568 if (use_gptimer_clksrc) \
568 omap2_gptimer_clocksource_init((clksrc_nr), clksrc_src);\ 569 omap2_gptimer_clocksource_init((clksrc_nr), clksrc_src, \
570 clksrc_prop); \
569 else \ 571 else \
570 omap2_sync32k_clocksource_init(); \ 572 omap2_sync32k_clocksource_init(); \
571} 573}
572 574
573#ifdef CONFIG_ARCH_OMAP2 575#ifdef CONFIG_ARCH_OMAP2
574OMAP_SYS_32K_TIMER_INIT(2, 1, OMAP2_32K_SOURCE, "ti,timer-alwon", 576OMAP_SYS_32K_TIMER_INIT(2, 1, "timer_32k_ck", "ti,timer-alwon",
575 2, OMAP2_MPU_SOURCE); 577 2, "timer_sys_ck", NULL);
576#endif /* CONFIG_ARCH_OMAP2 */ 578#endif /* CONFIG_ARCH_OMAP2 */
577 579
578#ifdef CONFIG_ARCH_OMAP3 580#ifdef CONFIG_ARCH_OMAP3
579OMAP_SYS_32K_TIMER_INIT(3, 1, OMAP3_32K_SOURCE, "ti,timer-alwon", 581OMAP_SYS_32K_TIMER_INIT(3, 1, "timer_32k_ck", "ti,timer-alwon",
580 2, OMAP3_MPU_SOURCE); 582 2, "timer_sys_ck", NULL);
581OMAP_SYS_32K_TIMER_INIT(3_secure, 12, OMAP3_32K_SOURCE, "ti,timer-secure", 583OMAP_SYS_32K_TIMER_INIT(3_secure, 12, "secure_32k_fck", "ti,timer-secure",
582 2, OMAP3_MPU_SOURCE); 584 2, "timer_sys_ck", NULL);
583OMAP_SYS_GP_TIMER_INIT(3_gp, 1, OMAP3_MPU_SOURCE, "ti,timer-alwon",
584 2, OMAP3_MPU_SOURCE);
585#endif /* CONFIG_ARCH_OMAP3 */ 585#endif /* CONFIG_ARCH_OMAP3 */
586 586
587#ifdef CONFIG_SOC_AM33XX 587#if defined(CONFIG_ARCH_OMAP3) || defined(CONFIG_SOC_AM33XX)
588OMAP_SYS_GP_TIMER_INIT(3_am33xx, 1, OMAP4_MPU_SOURCE, "ti,timer-alwon", 588OMAP_SYS_GP_TIMER_INIT(3, 2, "timer_sys_ck", NULL,
589 2, OMAP4_MPU_SOURCE); 589 1, "timer_sys_ck", "ti,timer-alwon");
590#endif /* CONFIG_SOC_AM33XX */ 590#endif
591
592#if defined(CONFIG_ARCH_OMAP4) || defined(CONFIG_SOC_OMAP5)
593static OMAP_SYS_32K_TIMER_INIT(4, 1, "timer_32k_ck", "ti,timer-alwon",
594 2, "sys_clkin_ck", NULL);
595#endif
591 596
592#ifdef CONFIG_ARCH_OMAP4 597#ifdef CONFIG_ARCH_OMAP4
593OMAP_SYS_32K_TIMER_INIT(4, 1, OMAP4_32K_SOURCE, "ti,timer-alwon",
594 2, OMAP4_MPU_SOURCE);
595#ifdef CONFIG_LOCAL_TIMERS 598#ifdef CONFIG_LOCAL_TIMERS
596static DEFINE_TWD_LOCAL_TIMER(twd_local_timer, OMAP44XX_LOCAL_TWD_BASE, 29); 599static DEFINE_TWD_LOCAL_TIMER(twd_local_timer, OMAP44XX_LOCAL_TWD_BASE, 29);
597void __init omap4_local_timer_init(void) 600void __init omap4_local_timer_init(void)
@@ -602,7 +605,7 @@ void __init omap4_local_timer_init(void)
602 int err; 605 int err;
603 606
604 if (of_have_populated_dt()) { 607 if (of_have_populated_dt()) {
605 twd_local_timer_of_register(); 608 clocksource_of_init();
606 return; 609 return;
607 } 610 }
608 611
@@ -620,18 +623,12 @@ void __init omap4_local_timer_init(void)
620#endif /* CONFIG_ARCH_OMAP4 */ 623#endif /* CONFIG_ARCH_OMAP4 */
621 624
622#ifdef CONFIG_SOC_OMAP5 625#ifdef CONFIG_SOC_OMAP5
623OMAP_SYS_32K_TIMER_INIT(5, 1, OMAP4_32K_SOURCE, "ti,timer-alwon",
624 2, OMAP5_MPU_SOURCE);
625void __init omap5_realtime_timer_init(void) 626void __init omap5_realtime_timer_init(void)
626{ 627{
627 int err; 628 omap4_sync32k_timer_init();
628
629 omap5_sync32k_timer_init();
630 realtime_counter_init(); 629 realtime_counter_init();
631 630
632 err = arch_timer_of_register(); 631 clocksource_of_init();
633 if (err)
634 pr_err("%s: arch_timer_register failed %d\n", __func__, err);
635} 632}
636#endif /* CONFIG_SOC_OMAP5 */ 633#endif /* CONFIG_SOC_OMAP5 */
637 634
diff --git a/arch/arm/mach-omap2/usb-host.c b/arch/arm/mach-omap2/usb-host.c
index 5706bdccf45e..aa27d7f5cbb7 100644
--- a/arch/arm/mach-omap2/usb-host.c
+++ b/arch/arm/mach-omap2/usb-host.c
@@ -22,8 +22,12 @@
22#include <linux/platform_device.h> 22#include <linux/platform_device.h>
23#include <linux/slab.h> 23#include <linux/slab.h>
24#include <linux/dma-mapping.h> 24#include <linux/dma-mapping.h>
25 25#include <linux/regulator/machine.h>
26#include <asm/io.h> 26#include <linux/regulator/fixed.h>
27#include <linux/string.h>
28#include <linux/io.h>
29#include <linux/gpio.h>
30#include <linux/usb/phy.h>
27 31
28#include "soc.h" 32#include "soc.h"
29#include "omap_device.h" 33#include "omap_device.h"
@@ -526,3 +530,155 @@ void __init usbhs_init(struct usbhs_omap_platform_data *pdata)
526} 530}
527 531
528#endif 532#endif
533
534/* Template for PHY regulators */
535static struct fixed_voltage_config hsusb_reg_config = {
536 /* .supply_name filled later */
537 .microvolts = 3300000,
538 .gpio = -1, /* updated later */
539 .startup_delay = 70000, /* 70msec */
540 .enable_high = 1, /* updated later */
541 .enabled_at_boot = 0, /* keep in RESET */
542 /* .init_data filled later */
543};
544
545static const char *nop_name = "nop_usb_xceiv"; /* NOP PHY driver */
546static const char *reg_name = "reg-fixed-voltage"; /* Regulator driver */
547
548/**
549 * usbhs_add_regulator - Add a gpio based fixed voltage regulator device
550 * @name: name for the regulator
551 * @dev_id: device id of the device this regulator supplies power to
552 * @dev_supply: supply name that the device expects
553 * @gpio: GPIO number
554 * @polarity: 1 - Active high, 0 - Active low
555 */
556static int usbhs_add_regulator(char *name, char *dev_id, char *dev_supply,
557 int gpio, int polarity)
558{
559 struct regulator_consumer_supply *supplies;
560 struct regulator_init_data *reg_data;
561 struct fixed_voltage_config *config;
562 struct platform_device *pdev;
563 int ret;
564
565 supplies = kzalloc(sizeof(*supplies), GFP_KERNEL);
566 if (!supplies)
567 return -ENOMEM;
568
569 supplies->supply = dev_supply;
570 supplies->dev_name = dev_id;
571
572 reg_data = kzalloc(sizeof(*reg_data), GFP_KERNEL);
573 if (!reg_data)
574 return -ENOMEM;
575
576 reg_data->constraints.valid_ops_mask = REGULATOR_CHANGE_STATUS;
577 reg_data->consumer_supplies = supplies;
578 reg_data->num_consumer_supplies = 1;
579
580 config = kmemdup(&hsusb_reg_config, sizeof(hsusb_reg_config),
581 GFP_KERNEL);
582 if (!config)
583 return -ENOMEM;
584
585 config->supply_name = name;
586 config->gpio = gpio;
587 config->enable_high = polarity;
588 config->init_data = reg_data;
589
590 /* create a regulator device */
591 pdev = kzalloc(sizeof(*pdev), GFP_KERNEL);
592 if (!pdev)
593 return -ENOMEM;
594
595 pdev->id = PLATFORM_DEVID_AUTO;
596 pdev->name = reg_name;
597 pdev->dev.platform_data = config;
598
599 ret = platform_device_register(pdev);
600 if (ret)
601 pr_err("%s: Failed registering regulator %s for %s\n",
602 __func__, name, dev_id);
603
604 return ret;
605}
606
607int usbhs_init_phys(struct usbhs_phy_data *phy, int num_phys)
608{
609 char *rail_name;
610 int i, len;
611 struct platform_device *pdev;
612 char *phy_id;
613
614 /* the phy_id will be something like "nop_usb_xceiv.1" */
615 len = strlen(nop_name) + 3; /* 3 -> ".1" and NULL terminator */
616
617 for (i = 0; i < num_phys; i++) {
618
619 if (!phy->port) {
620 pr_err("%s: Invalid port 0. Must start from 1\n",
621 __func__);
622 continue;
623 }
624
625 /* do we need a NOP PHY device ? */
626 if (!gpio_is_valid(phy->reset_gpio) &&
627 !gpio_is_valid(phy->vcc_gpio))
628 continue;
629
630 /* create a NOP PHY device */
631 pdev = kzalloc(sizeof(*pdev), GFP_KERNEL);
632 if (!pdev)
633 return -ENOMEM;
634
635 pdev->id = phy->port;
636 pdev->name = nop_name;
637 pdev->dev.platform_data = phy->platform_data;
638
639 phy_id = kmalloc(len, GFP_KERNEL);
640 if (!phy_id)
641 return -ENOMEM;
642
643 scnprintf(phy_id, len, "nop_usb_xceiv.%d\n",
644 pdev->id);
645
646 if (platform_device_register(pdev)) {
647 pr_err("%s: Failed to register device %s\n",
648 __func__, phy_id);
649 continue;
650 }
651
652 usb_bind_phy("ehci-omap.0", phy->port - 1, phy_id);
653
654 /* Do we need RESET regulator ? */
655 if (gpio_is_valid(phy->reset_gpio)) {
656
657 rail_name = kmalloc(13, GFP_KERNEL);
658 if (!rail_name)
659 return -ENOMEM;
660
661 scnprintf(rail_name, 13, "hsusb%d_reset", phy->port);
662
663 usbhs_add_regulator(rail_name, phy_id, "reset",
664 phy->reset_gpio, 1);
665 }
666
667 /* Do we need VCC regulator ? */
668 if (gpio_is_valid(phy->vcc_gpio)) {
669
670 rail_name = kmalloc(13, GFP_KERNEL);
671 if (!rail_name)
672 return -ENOMEM;
673
674 scnprintf(rail_name, 13, "hsusb%d_vcc", phy->port);
675
676 usbhs_add_regulator(rail_name, phy_id, "vcc",
677 phy->vcc_gpio, phy->vcc_polarity);
678 }
679
680 phy++;
681 }
682
683 return 0;
684}
diff --git a/arch/arm/mach-omap2/usb-tusb6010.c b/arch/arm/mach-omap2/usb-tusb6010.c
index c5a3c6f9504e..e832bc7b8e2d 100644
--- a/arch/arm/mach-omap2/usb-tusb6010.c
+++ b/arch/arm/mach-omap2/usb-tusb6010.c
@@ -8,6 +8,7 @@
8 * published by the Free Software Foundation. 8 * published by the Free Software Foundation.
9 */ 9 */
10 10
11#include <linux/err.h>
11#include <linux/string.h> 12#include <linux/string.h>
12#include <linux/types.h> 13#include <linux/types.h>
13#include <linux/errno.h> 14#include <linux/errno.h>
@@ -26,6 +27,24 @@
26static u8 async_cs, sync_cs; 27static u8 async_cs, sync_cs;
27static unsigned refclk_psec; 28static unsigned refclk_psec;
28 29
30static struct gpmc_settings tusb_async = {
31 .wait_on_read = true,
32 .wait_on_write = true,
33 .device_width = GPMC_DEVWIDTH_16BIT,
34 .mux_add_data = GPMC_MUX_AD,
35};
36
37static struct gpmc_settings tusb_sync = {
38 .burst_read = true,
39 .burst_write = true,
40 .sync_read = true,
41 .sync_write = true,
42 .wait_on_read = true,
43 .wait_on_write = true,
44 .burst_len = GPMC_BURST_16,
45 .device_width = GPMC_DEVWIDTH_16BIT,
46 .mux_add_data = GPMC_MUX_AD,
47};
29 48
30/* NOTE: timings are from tusb 6010 datasheet Rev 1.8, 12-Sept 2006 */ 49/* NOTE: timings are from tusb 6010 datasheet Rev 1.8, 12-Sept 2006 */
31 50
@@ -37,8 +56,6 @@ static int tusb_set_async_mode(unsigned sysclk_ps)
37 56
38 memset(&dev_t, 0, sizeof(dev_t)); 57 memset(&dev_t, 0, sizeof(dev_t));
39 58
40 dev_t.mux = true;
41
42 dev_t.t_ceasu = 8 * 1000; 59 dev_t.t_ceasu = 8 * 1000;
43 dev_t.t_avdasu = t_acsnh_advnh - 7000; 60 dev_t.t_avdasu = t_acsnh_advnh - 7000;
44 dev_t.t_ce_avd = 1000; 61 dev_t.t_ce_avd = 1000;
@@ -52,7 +69,7 @@ static int tusb_set_async_mode(unsigned sysclk_ps)
52 dev_t.t_wpl = 300; 69 dev_t.t_wpl = 300;
53 dev_t.cyc_aavdh_we = 1; 70 dev_t.cyc_aavdh_we = 1;
54 71
55 gpmc_calc_timings(&t, &dev_t); 72 gpmc_calc_timings(&t, &tusb_async, &dev_t);
56 73
57 return gpmc_cs_set_timings(async_cs, &t); 74 return gpmc_cs_set_timings(async_cs, &t);
58} 75}
@@ -65,10 +82,6 @@ static int tusb_set_sync_mode(unsigned sysclk_ps)
65 82
66 memset(&dev_t, 0, sizeof(dev_t)); 83 memset(&dev_t, 0, sizeof(dev_t));
67 84
68 dev_t.mux = true;
69 dev_t.sync_read = true;
70 dev_t.sync_write = true;
71
72 dev_t.clk = 11100; 85 dev_t.clk = 11100;
73 dev_t.t_bacc = 1000; 86 dev_t.t_bacc = 1000;
74 dev_t.t_ces = 1000; 87 dev_t.t_ces = 1000;
@@ -84,7 +97,7 @@ static int tusb_set_sync_mode(unsigned sysclk_ps)
84 dev_t.cyc_wpl = 6; 97 dev_t.cyc_wpl = 6;
85 dev_t.t_ce_rdyz = 7000; 98 dev_t.t_ce_rdyz = 7000;
86 99
87 gpmc_calc_timings(&t, &dev_t); 100 gpmc_calc_timings(&t, &tusb_sync, &dev_t);
88 101
89 return gpmc_cs_set_timings(sync_cs, &t); 102 return gpmc_cs_set_timings(sync_cs, &t);
90} 103}
@@ -165,18 +178,12 @@ tusb6010_setup_interface(struct musb_hdrc_platform_data *data,
165 return status; 178 return status;
166 } 179 }
167 tusb_resources[0].end = tusb_resources[0].start + 0x9ff; 180 tusb_resources[0].end = tusb_resources[0].start + 0x9ff;
181 tusb_async.wait_pin = waitpin;
168 async_cs = async; 182 async_cs = async;
169 gpmc_cs_write_reg(async, GPMC_CS_CONFIG1,
170 GPMC_CONFIG1_PAGE_LEN(2)
171 | GPMC_CONFIG1_WAIT_READ_MON
172 | GPMC_CONFIG1_WAIT_WRITE_MON
173 | GPMC_CONFIG1_WAIT_PIN_SEL(waitpin)
174 | GPMC_CONFIG1_READTYPE_ASYNC
175 | GPMC_CONFIG1_WRITETYPE_ASYNC
176 | GPMC_CONFIG1_DEVICESIZE_16
177 | GPMC_CONFIG1_DEVICETYPE_NOR
178 | GPMC_CONFIG1_MUXADDDATA);
179 183
184 status = gpmc_cs_program_settings(async_cs, &tusb_async);
185 if (status < 0)
186 return status;
180 187
181 /* SYNC region, primarily for DMA */ 188 /* SYNC region, primarily for DMA */
182 status = gpmc_cs_request(sync, SZ_16M, (unsigned long *) 189 status = gpmc_cs_request(sync, SZ_16M, (unsigned long *)
@@ -186,21 +193,12 @@ tusb6010_setup_interface(struct musb_hdrc_platform_data *data,
186 return status; 193 return status;
187 } 194 }
188 tusb_resources[1].end = tusb_resources[1].start + 0x9ff; 195 tusb_resources[1].end = tusb_resources[1].start + 0x9ff;
196 tusb_sync.wait_pin = waitpin;
189 sync_cs = sync; 197 sync_cs = sync;
190 gpmc_cs_write_reg(sync, GPMC_CS_CONFIG1, 198
191 GPMC_CONFIG1_READMULTIPLE_SUPP 199 status = gpmc_cs_program_settings(sync_cs, &tusb_sync);
192 | GPMC_CONFIG1_READTYPE_SYNC 200 if (status < 0)
193 | GPMC_CONFIG1_WRITEMULTIPLE_SUPP 201 return status;
194 | GPMC_CONFIG1_WRITETYPE_SYNC
195 | GPMC_CONFIG1_PAGE_LEN(2)
196 | GPMC_CONFIG1_WAIT_READ_MON
197 | GPMC_CONFIG1_WAIT_WRITE_MON
198 | GPMC_CONFIG1_WAIT_PIN_SEL(waitpin)
199 | GPMC_CONFIG1_DEVICESIZE_16
200 | GPMC_CONFIG1_DEVICETYPE_NOR
201 | GPMC_CONFIG1_MUXADDDATA
202 /* fclk divider gets set later */
203 );
204 202
205 /* IRQ */ 203 /* IRQ */
206 status = gpio_request_one(irq, GPIOF_IN, "TUSB6010 irq"); 204 status = gpio_request_one(irq, GPIOF_IN, "TUSB6010 irq");
diff --git a/arch/arm/mach-omap2/usb.h b/arch/arm/mach-omap2/usb.h
index 3319f5cf47a3..e7261ebcf7b0 100644
--- a/arch/arm/mach-omap2/usb.h
+++ b/arch/arm/mach-omap2/usb.h
@@ -53,8 +53,17 @@
53#define USBPHY_OTGSESSEND_EN (1 << 20) 53#define USBPHY_OTGSESSEND_EN (1 << 20)
54#define USBPHY_DATA_POLARITY (1 << 23) 54#define USBPHY_DATA_POLARITY (1 << 23)
55 55
56struct usbhs_phy_data {
57 int port; /* 1 indexed port number */
58 int reset_gpio;
59 int vcc_gpio;
60 bool vcc_polarity; /* 1 active high, 0 active low */
61 void *platform_data;
62};
63
56extern void usb_musb_init(struct omap_musb_board_data *board_data); 64extern void usb_musb_init(struct omap_musb_board_data *board_data);
57extern void usbhs_init(struct usbhs_omap_platform_data *pdata); 65extern void usbhs_init(struct usbhs_omap_platform_data *pdata);
66extern int usbhs_init_phys(struct usbhs_phy_data *phy, int num_phys);
58 67
59extern void am35x_musb_reset(void); 68extern void am35x_musb_reset(void);
60extern void am35x_musb_phy_power(u8 on); 69extern void am35x_musb_phy_power(u8 on);
diff --git a/arch/arm/mach-s3c24xx/Kconfig b/arch/arm/mach-s3c24xx/Kconfig
index 37f513d1588e..0a8663c5f2ba 100644
--- a/arch/arm/mach-s3c24xx/Kconfig
+++ b/arch/arm/mach-s3c24xx/Kconfig
@@ -30,6 +30,7 @@ config CPU_S3C2410
30 select S3C2410_CLOCK 30 select S3C2410_CLOCK
31 select S3C2410_CPUFREQ if CPU_FREQ_S3C24XX 31 select S3C2410_CPUFREQ if CPU_FREQ_S3C24XX
32 select S3C2410_PM if PM 32 select S3C2410_PM if PM
33 select SAMSUNG_HRT
33 help 34 help
34 Support for S3C2410 and S3C2410A family from the S3C24XX line 35 Support for S3C2410 and S3C2410A family from the S3C24XX line
35 of Samsung Mobile CPUs. 36 of Samsung Mobile CPUs.
@@ -41,6 +42,7 @@ config CPU_S3C2412
41 select CPU_LLSERIAL_S3C2440 42 select CPU_LLSERIAL_S3C2440
42 select S3C2412_DMA if S3C24XX_DMA 43 select S3C2412_DMA if S3C24XX_DMA
43 select S3C2412_PM if PM 44 select S3C2412_PM if PM
45 select SAMSUNG_HRT
44 help 46 help
45 Support for the S3C2412 and S3C2413 SoCs from the S3C24XX line 47 Support for the S3C2412 and S3C2413 SoCs from the S3C24XX line
46 48
@@ -53,6 +55,7 @@ config CPU_S3C2416
53 select S3C2443_COMMON 55 select S3C2443_COMMON
54 select S3C2443_DMA if S3C24XX_DMA 56 select S3C2443_DMA if S3C24XX_DMA
55 select SAMSUNG_CLKSRC 57 select SAMSUNG_CLKSRC
58 select SAMSUNG_HRT
56 help 59 help
57 Support for the S3C2416 SoC from the S3C24XX line 60 Support for the S3C2416 SoC from the S3C24XX line
58 61
@@ -63,6 +66,7 @@ config CPU_S3C2440
63 select S3C2410_CLOCK 66 select S3C2410_CLOCK
64 select S3C2410_PM if PM 67 select S3C2410_PM if PM
65 select S3C2440_DMA if S3C24XX_DMA 68 select S3C2440_DMA if S3C24XX_DMA
69 select SAMSUNG_HRT
66 help 70 help
67 Support for S3C2440 Samsung Mobile CPU based systems. 71 Support for S3C2440 Samsung Mobile CPU based systems.
68 72
@@ -72,6 +76,7 @@ config CPU_S3C2442
72 select CPU_LLSERIAL_S3C2440 76 select CPU_LLSERIAL_S3C2440
73 select S3C2410_CLOCK 77 select S3C2410_CLOCK
74 select S3C2410_PM if PM 78 select S3C2410_PM if PM
79 select SAMSUNG_HRT
75 help 80 help
76 Support for S3C2442 Samsung Mobile CPU based systems. 81 Support for S3C2442 Samsung Mobile CPU based systems.
77 82
@@ -87,6 +92,7 @@ config CPU_S3C2443
87 select S3C2443_COMMON 92 select S3C2443_COMMON
88 select S3C2443_DMA if S3C24XX_DMA 93 select S3C2443_DMA if S3C24XX_DMA
89 select SAMSUNG_CLKSRC 94 select SAMSUNG_CLKSRC
95 select SAMSUNG_HRT
90 help 96 help
91 Support for the S3C2443 SoC from the S3C24XX line 97 Support for the S3C2443 SoC from the S3C24XX line
92 98
@@ -401,6 +407,7 @@ config S3C2412_DMA
401config S3C2412_PM 407config S3C2412_PM
402 bool 408 bool
403 select S3C2412_PM_SLEEP 409 select S3C2412_PM_SLEEP
410 select SAMSUNG_WAKEMASK
404 help 411 help
405 Internal config node to apply S3C2412 power management 412 Internal config node to apply S3C2412 power management
406 413
diff --git a/arch/arm/mach-s3c24xx/Makefile b/arch/arm/mach-s3c24xx/Makefile
index af53d27d5c36..6f46ecfc8396 100644
--- a/arch/arm/mach-s3c24xx/Makefile
+++ b/arch/arm/mach-s3c24xx/Makefile
@@ -14,7 +14,7 @@ obj- :=
14 14
15# core 15# core
16 16
17obj-y += common.o irq.o 17obj-y += common.o
18 18
19obj-$(CONFIG_CPU_S3C2410) += s3c2410.o 19obj-$(CONFIG_CPU_S3C2410) += s3c2410.o
20obj-$(CONFIG_S3C2410_CPUFREQ) += cpufreq-s3c2410.o 20obj-$(CONFIG_S3C2410_CPUFREQ) += cpufreq-s3c2410.o
@@ -22,7 +22,7 @@ obj-$(CONFIG_S3C2410_DMA) += dma-s3c2410.o
22obj-$(CONFIG_S3C2410_PLL) += pll-s3c2410.o 22obj-$(CONFIG_S3C2410_PLL) += pll-s3c2410.o
23obj-$(CONFIG_S3C2410_PM) += pm-s3c2410.o sleep-s3c2410.o 23obj-$(CONFIG_S3C2410_PM) += pm-s3c2410.o sleep-s3c2410.o
24 24
25obj-$(CONFIG_CPU_S3C2412) += s3c2412.o irq-s3c2412.o clock-s3c2412.o 25obj-$(CONFIG_CPU_S3C2412) += s3c2412.o clock-s3c2412.o
26obj-$(CONFIG_S3C2412_CPUFREQ) += cpufreq-s3c2412.o 26obj-$(CONFIG_S3C2412_CPUFREQ) += cpufreq-s3c2412.o
27obj-$(CONFIG_S3C2412_DMA) += dma-s3c2412.o 27obj-$(CONFIG_S3C2412_DMA) += dma-s3c2412.o
28obj-$(CONFIG_S3C2412_PM) += pm-s3c2412.o 28obj-$(CONFIG_S3C2412_PM) += pm-s3c2412.o
@@ -31,9 +31,9 @@ obj-$(CONFIG_S3C2412_PM_SLEEP) += sleep-s3c2412.o
31obj-$(CONFIG_CPU_S3C2416) += s3c2416.o clock-s3c2416.o 31obj-$(CONFIG_CPU_S3C2416) += s3c2416.o clock-s3c2416.o
32obj-$(CONFIG_S3C2416_PM) += pm-s3c2416.o 32obj-$(CONFIG_S3C2416_PM) += pm-s3c2416.o
33 33
34obj-$(CONFIG_CPU_S3C2440) += s3c2440.o irq-s3c2440.o clock-s3c2440.o 34obj-$(CONFIG_CPU_S3C2440) += s3c2440.o clock-s3c2440.o
35obj-$(CONFIG_CPU_S3C2442) += s3c2442.o 35obj-$(CONFIG_CPU_S3C2442) += s3c2442.o
36obj-$(CONFIG_CPU_S3C244X) += s3c244x.o irq-s3c244x.o clock-s3c244x.o 36obj-$(CONFIG_CPU_S3C244X) += s3c244x.o clock-s3c244x.o
37obj-$(CONFIG_S3C2440_CPUFREQ) += cpufreq-s3c2440.o 37obj-$(CONFIG_S3C2440_CPUFREQ) += cpufreq-s3c2440.o
38obj-$(CONFIG_S3C2440_DMA) += dma-s3c2440.o 38obj-$(CONFIG_S3C2440_DMA) += dma-s3c2440.o
39obj-$(CONFIG_S3C2440_PLL_12000000) += pll-s3c2440-12000000.o 39obj-$(CONFIG_S3C2440_PLL_12000000) += pll-s3c2440-12000000.o
diff --git a/arch/arm/mach-s3c24xx/bast-irq.c b/arch/arm/mach-s3c24xx/bast-irq.c
index c0daa9590b4c..cb1b791954de 100644
--- a/arch/arm/mach-s3c24xx/bast-irq.c
+++ b/arch/arm/mach-s3c24xx/bast-irq.c
@@ -34,8 +34,6 @@
34#include <mach/hardware.h> 34#include <mach/hardware.h>
35#include <mach/regs-irq.h> 35#include <mach/regs-irq.h>
36 36
37#include <plat/irq.h>
38
39#include "bast.h" 37#include "bast.h"
40 38
41#define irqdbf(x...) 39#define irqdbf(x...)
diff --git a/arch/arm/mach-s3c24xx/clock-s3c2410.c b/arch/arm/mach-s3c24xx/clock-s3c2410.c
index 641266f3d152..34fffdf6fc1d 100644
--- a/arch/arm/mach-s3c24xx/clock-s3c2410.c
+++ b/arch/arm/mach-s3c24xx/clock-s3c2410.c
@@ -40,7 +40,6 @@
40#include <mach/regs-clock.h> 40#include <mach/regs-clock.h>
41#include <mach/regs-gpio.h> 41#include <mach/regs-gpio.h>
42 42
43#include <plat/s3c2410.h>
44#include <plat/clock.h> 43#include <plat/clock.h>
45#include <plat/cpu.h> 44#include <plat/cpu.h>
46 45
diff --git a/arch/arm/mach-s3c24xx/clock-s3c2412.c b/arch/arm/mach-s3c24xx/clock-s3c2412.c
index d10b695a9066..2cc017da88fe 100644
--- a/arch/arm/mach-s3c24xx/clock-s3c2412.c
+++ b/arch/arm/mach-s3c24xx/clock-s3c2412.c
@@ -41,7 +41,6 @@
41#include <mach/regs-clock.h> 41#include <mach/regs-clock.h>
42#include <mach/regs-gpio.h> 42#include <mach/regs-gpio.h>
43 43
44#include <plat/s3c2412.h>
45#include <plat/clock.h> 44#include <plat/clock.h>
46#include <plat/cpu.h> 45#include <plat/cpu.h>
47 46
diff --git a/arch/arm/mach-s3c24xx/clock-s3c2416.c b/arch/arm/mach-s3c24xx/clock-s3c2416.c
index 14a81c2317a4..036056cea57c 100644
--- a/arch/arm/mach-s3c24xx/clock-s3c2416.c
+++ b/arch/arm/mach-s3c24xx/clock-s3c2416.c
@@ -14,7 +14,6 @@
14#include <linux/init.h> 14#include <linux/init.h>
15#include <linux/clk.h> 15#include <linux/clk.h>
16 16
17#include <plat/s3c2416.h>
18#include <plat/clock.h> 17#include <plat/clock.h>
19#include <plat/clock-clksrc.h> 18#include <plat/clock-clksrc.h>
20#include <plat/cpu.h> 19#include <plat/cpu.h>
diff --git a/arch/arm/mach-s3c24xx/clock-s3c2443.c b/arch/arm/mach-s3c24xx/clock-s3c2443.c
index bdaba59b42dc..0a53051b0787 100644
--- a/arch/arm/mach-s3c24xx/clock-s3c2443.c
+++ b/arch/arm/mach-s3c24xx/clock-s3c2443.c
@@ -41,7 +41,6 @@
41 41
42#include <plat/cpu-freq.h> 42#include <plat/cpu-freq.h>
43 43
44#include <plat/s3c2443.h>
45#include <plat/clock.h> 44#include <plat/clock.h>
46#include <plat/clock-clksrc.h> 45#include <plat/clock-clksrc.h>
47#include <plat/cpu.h> 46#include <plat/cpu.h>
diff --git a/arch/arm/mach-s3c24xx/common-smdk.c b/arch/arm/mach-s3c24xx/common-smdk.c
index 3b2cf6db3634..404444dd3840 100644
--- a/arch/arm/mach-s3c24xx/common-smdk.c
+++ b/arch/arm/mach-s3c24xx/common-smdk.c
@@ -41,11 +41,12 @@
41 41
42#include <linux/platform_data/mtd-nand-s3c2410.h> 42#include <linux/platform_data/mtd-nand-s3c2410.h>
43 43
44#include <plat/common-smdk.h>
45#include <plat/gpio-cfg.h> 44#include <plat/gpio-cfg.h>
46#include <plat/devs.h> 45#include <plat/devs.h>
47#include <plat/pm.h> 46#include <plat/pm.h>
48 47
48#include "common-smdk.h"
49
49/* LED devices */ 50/* LED devices */
50 51
51static struct s3c24xx_led_platdata smdk_pdata_led4 = { 52static struct s3c24xx_led_platdata smdk_pdata_led4 = {
diff --git a/arch/arm/plat-samsung/include/plat/common-smdk.h b/arch/arm/mach-s3c24xx/common-smdk.h
index ba028f1ed30b..98f733e1cb42 100644
--- a/arch/arm/plat-samsung/include/plat/common-smdk.h
+++ b/arch/arm/mach-s3c24xx/common-smdk.h
@@ -1,5 +1,4 @@
1/* linux/arch/arm/plat-samsung/include/plat/common-smdk.h 1/*
2 *
3 * Copyright (c) 2006 Simtec Electronics 2 * Copyright (c) 2006 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk> 3 * Ben Dooks <ben@simtec.co.uk>
5 * 4 *
diff --git a/arch/arm/mach-s3c24xx/common.c b/arch/arm/mach-s3c24xx/common.c
index 6bcf87f65f9e..d97533d21ac4 100644
--- a/arch/arm/mach-s3c24xx/common.c
+++ b/arch/arm/mach-s3c24xx/common.c
@@ -47,14 +47,11 @@
47#include <plat/cpu.h> 47#include <plat/cpu.h>
48#include <plat/devs.h> 48#include <plat/devs.h>
49#include <plat/clock.h> 49#include <plat/clock.h>
50#include <plat/s3c2410.h>
51#include <plat/s3c2412.h>
52#include <plat/s3c2416.h>
53#include <plat/s3c244x.h>
54#include <plat/s3c2443.h>
55#include <plat/cpu-freq.h> 50#include <plat/cpu-freq.h>
56#include <plat/pll.h> 51#include <plat/pll.h>
57 52
53#include "common.h"
54
58/* table of supported CPUs */ 55/* table of supported CPUs */
59 56
60static const char name_s3c2410[] = "S3C2410"; 57static const char name_s3c2410[] = "S3C2410";
diff --git a/arch/arm/mach-s3c24xx/common.h b/arch/arm/mach-s3c24xx/common.h
index ed6276fcaa3b..307c3714be55 100644
--- a/arch/arm/mach-s3c24xx/common.h
+++ b/arch/arm/mach-s3c24xx/common.h
@@ -12,8 +12,98 @@
12#ifndef __ARCH_ARM_MACH_S3C24XX_COMMON_H 12#ifndef __ARCH_ARM_MACH_S3C24XX_COMMON_H
13#define __ARCH_ARM_MACH_S3C24XX_COMMON_H __FILE__ 13#define __ARCH_ARM_MACH_S3C24XX_COMMON_H __FILE__
14 14
15void s3c2410_restart(char mode, const char *cmd); 15struct s3c2410_uartcfg;
16void s3c244x_restart(char mode, const char *cmd); 16
17#ifdef CONFIG_CPU_S3C2410
18extern int s3c2410_init(void);
19extern int s3c2410a_init(void);
20extern void s3c2410_map_io(void);
21extern void s3c2410_init_uarts(struct s3c2410_uartcfg *cfg, int no);
22extern void s3c2410_init_clocks(int xtal);
23extern void s3c2410_restart(char mode, const char *cmd);
24extern void s3c2410_init_irq(void);
25#else
26#define s3c2410_init_clocks NULL
27#define s3c2410_init_uarts NULL
28#define s3c2410_map_io NULL
29#define s3c2410_init NULL
30#define s3c2410a_init NULL
31#endif
32
33#ifdef CONFIG_CPU_S3C2412
34extern int s3c2412_init(void);
35extern void s3c2412_map_io(void);
36extern void s3c2412_init_uarts(struct s3c2410_uartcfg *cfg, int no);
37extern void s3c2412_init_clocks(int xtal);
38extern int s3c2412_baseclk_add(void);
39extern void s3c2412_restart(char mode, const char *cmd);
40extern void s3c2412_init_irq(void);
41#else
42#define s3c2412_init_clocks NULL
43#define s3c2412_init_uarts NULL
44#define s3c2412_map_io NULL
45#define s3c2412_init NULL
46#endif
47
48#ifdef CONFIG_CPU_S3C2416
49extern int s3c2416_init(void);
50extern void s3c2416_map_io(void);
51extern void s3c2416_init_uarts(struct s3c2410_uartcfg *cfg, int no);
52extern void s3c2416_init_clocks(int xtal);
53extern int s3c2416_baseclk_add(void);
54extern void s3c2416_restart(char mode, const char *cmd);
55extern void s3c2416_init_irq(void);
56
57extern struct syscore_ops s3c2416_irq_syscore_ops;
58#else
59#define s3c2416_init_clocks NULL
60#define s3c2416_init_uarts NULL
61#define s3c2416_map_io NULL
62#define s3c2416_init NULL
63#endif
64
65#if defined(CONFIG_CPU_S3C2440) || defined(CONFIG_CPU_S3C2442)
66extern void s3c244x_map_io(void);
67extern void s3c244x_init_uarts(struct s3c2410_uartcfg *cfg, int no);
68extern void s3c244x_init_clocks(int xtal);
69extern void s3c244x_restart(char mode, const char *cmd);
70#else
71#define s3c244x_init_clocks NULL
72#define s3c244x_init_uarts NULL
73#endif
74
75#ifdef CONFIG_CPU_S3C2440
76extern int s3c2440_init(void);
77extern void s3c2440_map_io(void);
78extern void s3c2440_init_irq(void);
79#else
80#define s3c2440_init NULL
81#define s3c2440_map_io NULL
82#endif
83
84#ifdef CONFIG_CPU_S3C2442
85extern int s3c2442_init(void);
86extern void s3c2442_map_io(void);
87extern void s3c2442_init_irq(void);
88#else
89#define s3c2442_init NULL
90#define s3c2442_map_io NULL
91#endif
92
93#ifdef CONFIG_CPU_S3C2443
94extern int s3c2443_init(void);
95extern void s3c2443_map_io(void);
96extern void s3c2443_init_uarts(struct s3c2410_uartcfg *cfg, int no);
97extern void s3c2443_init_clocks(int xtal);
98extern int s3c2443_baseclk_add(void);
99extern void s3c2443_restart(char mode, const char *cmd);
100extern void s3c2443_init_irq(void);
101#else
102#define s3c2443_init_clocks NULL
103#define s3c2443_init_uarts NULL
104#define s3c2443_map_io NULL
105#define s3c2443_init NULL
106#endif
17 107
18extern struct syscore_ops s3c24xx_irq_syscore_ops; 108extern struct syscore_ops s3c24xx_irq_syscore_ops;
19 109
diff --git a/arch/arm/mach-s3c24xx/dma-s3c2410.c b/arch/arm/mach-s3c24xx/dma-s3c2410.c
index 25d085adc93c..a6c94b820954 100644
--- a/arch/arm/mach-s3c24xx/dma-s3c2410.c
+++ b/arch/arm/mach-s3c24xx/dma-s3c2410.c
@@ -28,7 +28,6 @@
28#include <plat/regs-ac97.h> 28#include <plat/regs-ac97.h>
29#include <plat/regs-dma.h> 29#include <plat/regs-dma.h>
30#include <mach/regs-lcd.h> 30#include <mach/regs-lcd.h>
31#include <mach/regs-sdi.h>
32#include <plat/regs-iis.h> 31#include <plat/regs-iis.h>
33#include <plat/regs-spi.h> 32#include <plat/regs-spi.h>
34 33
diff --git a/arch/arm/mach-s3c24xx/dma-s3c2412.c b/arch/arm/mach-s3c24xx/dma-s3c2412.c
index d2408ba372cb..c0e8c3f5057e 100644
--- a/arch/arm/mach-s3c24xx/dma-s3c2412.c
+++ b/arch/arm/mach-s3c24xx/dma-s3c2412.c
@@ -28,7 +28,6 @@
28#include <plat/regs-ac97.h> 28#include <plat/regs-ac97.h>
29#include <plat/regs-dma.h> 29#include <plat/regs-dma.h>
30#include <mach/regs-lcd.h> 30#include <mach/regs-lcd.h>
31#include <mach/regs-sdi.h>
32#include <plat/regs-iis.h> 31#include <plat/regs-iis.h>
33#include <plat/regs-spi.h> 32#include <plat/regs-spi.h>
34 33
diff --git a/arch/arm/mach-s3c24xx/dma-s3c2440.c b/arch/arm/mach-s3c24xx/dma-s3c2440.c
index 0b86e74d104f..1c08eccd9425 100644
--- a/arch/arm/mach-s3c24xx/dma-s3c2440.c
+++ b/arch/arm/mach-s3c24xx/dma-s3c2440.c
@@ -28,7 +28,6 @@
28#include <plat/regs-ac97.h> 28#include <plat/regs-ac97.h>
29#include <plat/regs-dma.h> 29#include <plat/regs-dma.h>
30#include <mach/regs-lcd.h> 30#include <mach/regs-lcd.h>
31#include <mach/regs-sdi.h>
32#include <plat/regs-iis.h> 31#include <plat/regs-iis.h>
33#include <plat/regs-spi.h> 32#include <plat/regs-spi.h>
34 33
diff --git a/arch/arm/mach-s3c24xx/dma-s3c2443.c b/arch/arm/mach-s3c24xx/dma-s3c2443.c
index 05536254a3f8..000e4c69fce9 100644
--- a/arch/arm/mach-s3c24xx/dma-s3c2443.c
+++ b/arch/arm/mach-s3c24xx/dma-s3c2443.c
@@ -28,7 +28,6 @@
28#include <plat/regs-ac97.h> 28#include <plat/regs-ac97.h>
29#include <plat/regs-dma.h> 29#include <plat/regs-dma.h>
30#include <mach/regs-lcd.h> 30#include <mach/regs-lcd.h>
31#include <mach/regs-sdi.h>
32#include <plat/regs-iis.h> 31#include <plat/regs-iis.h>
33#include <plat/regs-spi.h> 32#include <plat/regs-spi.h>
34 33
diff --git a/arch/arm/mach-s3c24xx/include/mach/entry-macro.S b/arch/arm/mach-s3c24xx/include/mach/entry-macro.S
deleted file mode 100644
index 6a21beeba1da..000000000000
--- a/arch/arm/mach-s3c24xx/include/mach/entry-macro.S
+++ /dev/null
@@ -1,70 +0,0 @@
1/*
2 * arch/arm/mach-s3c2410/include/mach/entry-macro.S
3 *
4 * Low-level IRQ helper macros for S3C2410-based platforms
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9*/
10
11/* We have a problem that the INTOFFSET register does not always
12 * show one interrupt. Occasionally we get two interrupts through
13 * the prioritiser, and this causes the INTOFFSET register to show
14 * what looks like the logical-or of the two interrupt numbers.
15 *
16 * Thanks to Klaus, Shannon, et al for helping to debug this problem
17*/
18
19#define INTPND (0x10)
20#define INTOFFSET (0x14)
21
22#include <mach/hardware.h>
23#include <asm/irq.h>
24
25 .macro get_irqnr_preamble, base, tmp
26 .endm
27
28 .macro get_irqnr_and_base, irqnr, irqstat, base, tmp
29
30 mov \base, #S3C24XX_VA_IRQ
31
32 @@ try the interrupt offset register, since it is there
33
34 ldr \irqstat, [\base, #INTPND ]
35 teq \irqstat, #0
36 beq 1002f
37 ldr \irqnr, [\base, #INTOFFSET ]
38 mov \tmp, #1
39 tst \irqstat, \tmp, lsl \irqnr
40 bne 1001f
41
42 @@ the number specified is not a valid irq, so try
43 @@ and work it out for ourselves
44
45 mov \irqnr, #0 @@ start here
46
47 @@ work out which irq (if any) we got
48
49 movs \tmp, \irqstat, lsl#16
50 addeq \irqnr, \irqnr, #16
51 moveq \irqstat, \irqstat, lsr#16
52 tst \irqstat, #0xff
53 addeq \irqnr, \irqnr, #8
54 moveq \irqstat, \irqstat, lsr#8
55 tst \irqstat, #0xf
56 addeq \irqnr, \irqnr, #4
57 moveq \irqstat, \irqstat, lsr#4
58 tst \irqstat, #0x3
59 addeq \irqnr, \irqnr, #2
60 moveq \irqstat, \irqstat, lsr#2
61 tst \irqstat, #0x1
62 addeq \irqnr, \irqnr, #1
63
64 @@ we have the value
651001:
66 adds \irqnr, \irqnr, #IRQ_EINT0
671002:
68 @@ exit here, Z flag unset if IRQ
69
70 .endm
diff --git a/arch/arm/mach-s3c24xx/include/mach/irqs.h b/arch/arm/mach-s3c24xx/include/mach/irqs.h
index b7a9f4d469e8..43cada8019b4 100644
--- a/arch/arm/mach-s3c24xx/include/mach/irqs.h
+++ b/arch/arm/mach-s3c24xx/include/mach/irqs.h
@@ -59,49 +59,53 @@
59#define IRQ_ADCPARENT S3C2410_IRQ(31) 59#define IRQ_ADCPARENT S3C2410_IRQ(31)
60 60
61/* interrupts generated from the external interrupts sources */ 61/* interrupts generated from the external interrupts sources */
62#define IRQ_EINT4 S3C2410_IRQ(32) /* 48 */ 62#define IRQ_EINT0_2412 S3C2410_IRQ(32)
63#define IRQ_EINT5 S3C2410_IRQ(33) 63#define IRQ_EINT1_2412 S3C2410_IRQ(33)
64#define IRQ_EINT6 S3C2410_IRQ(34) 64#define IRQ_EINT2_2412 S3C2410_IRQ(34)
65#define IRQ_EINT7 S3C2410_IRQ(35) 65#define IRQ_EINT3_2412 S3C2410_IRQ(35)
66#define IRQ_EINT8 S3C2410_IRQ(36) 66#define IRQ_EINT4 S3C2410_IRQ(36) /* 52 */
67#define IRQ_EINT9 S3C2410_IRQ(37) 67#define IRQ_EINT5 S3C2410_IRQ(37)
68#define IRQ_EINT10 S3C2410_IRQ(38) 68#define IRQ_EINT6 S3C2410_IRQ(38)
69#define IRQ_EINT11 S3C2410_IRQ(39) 69#define IRQ_EINT7 S3C2410_IRQ(39)
70#define IRQ_EINT12 S3C2410_IRQ(40) 70#define IRQ_EINT8 S3C2410_IRQ(40)
71#define IRQ_EINT13 S3C2410_IRQ(41) 71#define IRQ_EINT9 S3C2410_IRQ(41)
72#define IRQ_EINT14 S3C2410_IRQ(42) 72#define IRQ_EINT10 S3C2410_IRQ(42)
73#define IRQ_EINT15 S3C2410_IRQ(43) 73#define IRQ_EINT11 S3C2410_IRQ(43)
74#define IRQ_EINT16 S3C2410_IRQ(44) 74#define IRQ_EINT12 S3C2410_IRQ(44)
75#define IRQ_EINT17 S3C2410_IRQ(45) 75#define IRQ_EINT13 S3C2410_IRQ(45)
76#define IRQ_EINT18 S3C2410_IRQ(46) 76#define IRQ_EINT14 S3C2410_IRQ(46)
77#define IRQ_EINT19 S3C2410_IRQ(47) 77#define IRQ_EINT15 S3C2410_IRQ(47)
78#define IRQ_EINT20 S3C2410_IRQ(48) /* 64 */ 78#define IRQ_EINT16 S3C2410_IRQ(48)
79#define IRQ_EINT21 S3C2410_IRQ(49) 79#define IRQ_EINT17 S3C2410_IRQ(49)
80#define IRQ_EINT22 S3C2410_IRQ(50) 80#define IRQ_EINT18 S3C2410_IRQ(50)
81#define IRQ_EINT23 S3C2410_IRQ(51) 81#define IRQ_EINT19 S3C2410_IRQ(51)
82#define IRQ_EINT20 S3C2410_IRQ(52) /* 68 */
83#define IRQ_EINT21 S3C2410_IRQ(53)
84#define IRQ_EINT22 S3C2410_IRQ(54)
85#define IRQ_EINT23 S3C2410_IRQ(55)
82 86
83#define IRQ_EINT_BIT(x) ((x) - IRQ_EINT4 + 4) 87#define IRQ_EINT_BIT(x) ((x) - IRQ_EINT4 + 4)
84#define IRQ_EINT(x) (((x) >= 4) ? (IRQ_EINT4 + (x) - 4) : (IRQ_EINT0 + (x))) 88#define IRQ_EINT(x) (((x) >= 4) ? (IRQ_EINT4 + (x) - 4) : (IRQ_EINT0 + (x)))
85 89
86#define IRQ_LCD_FIFO S3C2410_IRQ(52) 90#define IRQ_LCD_FIFO S3C2410_IRQ(56)
87#define IRQ_LCD_FRAME S3C2410_IRQ(53) 91#define IRQ_LCD_FRAME S3C2410_IRQ(57)
88 92
89/* IRQs for the interal UARTs, and ADC 93/* IRQs for the interal UARTs, and ADC
90 * these need to be ordered in number of appearance in the 94 * these need to be ordered in number of appearance in the
91 * SUBSRC mask register 95 * SUBSRC mask register
92*/ 96*/
93 97
94#define S3C2410_IRQSUB(x) S3C2410_IRQ((x)+54) 98#define S3C2410_IRQSUB(x) S3C2410_IRQ((x)+58)
95 99
96#define IRQ_S3CUART_RX0 S3C2410_IRQSUB(0) /* 70 */ 100#define IRQ_S3CUART_RX0 S3C2410_IRQSUB(0) /* 74 */
97#define IRQ_S3CUART_TX0 S3C2410_IRQSUB(1) 101#define IRQ_S3CUART_TX0 S3C2410_IRQSUB(1)
98#define IRQ_S3CUART_ERR0 S3C2410_IRQSUB(2) 102#define IRQ_S3CUART_ERR0 S3C2410_IRQSUB(2)
99 103
100#define IRQ_S3CUART_RX1 S3C2410_IRQSUB(3) /* 73 */ 104#define IRQ_S3CUART_RX1 S3C2410_IRQSUB(3) /* 77 */
101#define IRQ_S3CUART_TX1 S3C2410_IRQSUB(4) 105#define IRQ_S3CUART_TX1 S3C2410_IRQSUB(4)
102#define IRQ_S3CUART_ERR1 S3C2410_IRQSUB(5) 106#define IRQ_S3CUART_ERR1 S3C2410_IRQSUB(5)
103 107
104#define IRQ_S3CUART_RX2 S3C2410_IRQSUB(6) /* 76 */ 108#define IRQ_S3CUART_RX2 S3C2410_IRQSUB(6) /* 80 */
105#define IRQ_S3CUART_TX2 S3C2410_IRQSUB(7) 109#define IRQ_S3CUART_TX2 S3C2410_IRQSUB(7)
106#define IRQ_S3CUART_ERR2 S3C2410_IRQSUB(8) 110#define IRQ_S3CUART_ERR2 S3C2410_IRQSUB(8)
107 111
@@ -136,7 +140,7 @@
136 140
137/* second interrupt-register of s3c2416/s3c2450 */ 141/* second interrupt-register of s3c2416/s3c2450 */
138 142
139#define S3C2416_IRQ(x) S3C2410_IRQ((x) + 54 + 29) 143#define S3C2416_IRQ(x) S3C2410_IRQ((x) + 58 + 29)
140#define IRQ_S3C2416_2D S3C2416_IRQ(0) 144#define IRQ_S3C2416_2D S3C2416_IRQ(0)
141#define IRQ_S3C2416_IIC1 S3C2416_IRQ(1) 145#define IRQ_S3C2416_IIC1 S3C2416_IRQ(1)
142#define IRQ_S3C2416_RESERVED2 S3C2416_IRQ(2) 146#define IRQ_S3C2416_RESERVED2 S3C2416_IRQ(2)
diff --git a/arch/arm/mach-s3c24xx/include/mach/regs-sdi.h b/arch/arm/mach-s3c24xx/include/mach/regs-sdi.h
deleted file mode 100644
index cbf2d8884e30..000000000000
--- a/arch/arm/mach-s3c24xx/include/mach/regs-sdi.h
+++ /dev/null
@@ -1,127 +0,0 @@
1/* arch/arm/mach-s3c2410/include/mach/regs-sdi.h
2 *
3 * Copyright (c) 2004 Simtec Electronics <linux@simtec.co.uk>
4 * http://www.simtec.co.uk/products/SWLINUX/
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 as
8 * published by the Free Software Foundation.
9 *
10 * S3C2410 MMC/SDIO register definitions
11*/
12
13#ifndef __ASM_ARM_REGS_SDI
14#define __ASM_ARM_REGS_SDI "regs-sdi.h"
15
16#define S3C2410_SDICON (0x00)
17#define S3C2410_SDIPRE (0x04)
18#define S3C2410_SDICMDARG (0x08)
19#define S3C2410_SDICMDCON (0x0C)
20#define S3C2410_SDICMDSTAT (0x10)
21#define S3C2410_SDIRSP0 (0x14)
22#define S3C2410_SDIRSP1 (0x18)
23#define S3C2410_SDIRSP2 (0x1C)
24#define S3C2410_SDIRSP3 (0x20)
25#define S3C2410_SDITIMER (0x24)
26#define S3C2410_SDIBSIZE (0x28)
27#define S3C2410_SDIDCON (0x2C)
28#define S3C2410_SDIDCNT (0x30)
29#define S3C2410_SDIDSTA (0x34)
30#define S3C2410_SDIFSTA (0x38)
31
32#define S3C2410_SDIDATA (0x3C)
33#define S3C2410_SDIIMSK (0x40)
34
35#define S3C2440_SDIDATA (0x40)
36#define S3C2440_SDIIMSK (0x3C)
37
38#define S3C2440_SDICON_SDRESET (1<<8)
39#define S3C2440_SDICON_MMCCLOCK (1<<5)
40#define S3C2410_SDICON_BYTEORDER (1<<4)
41#define S3C2410_SDICON_SDIOIRQ (1<<3)
42#define S3C2410_SDICON_RWAITEN (1<<2)
43#define S3C2410_SDICON_FIFORESET (1<<1)
44#define S3C2410_SDICON_CLOCKTYPE (1<<0)
45
46#define S3C2410_SDICMDCON_ABORT (1<<12)
47#define S3C2410_SDICMDCON_WITHDATA (1<<11)
48#define S3C2410_SDICMDCON_LONGRSP (1<<10)
49#define S3C2410_SDICMDCON_WAITRSP (1<<9)
50#define S3C2410_SDICMDCON_CMDSTART (1<<8)
51#define S3C2410_SDICMDCON_SENDERHOST (1<<6)
52#define S3C2410_SDICMDCON_INDEX (0x3f)
53
54#define S3C2410_SDICMDSTAT_CRCFAIL (1<<12)
55#define S3C2410_SDICMDSTAT_CMDSENT (1<<11)
56#define S3C2410_SDICMDSTAT_CMDTIMEOUT (1<<10)
57#define S3C2410_SDICMDSTAT_RSPFIN (1<<9)
58#define S3C2410_SDICMDSTAT_XFERING (1<<8)
59#define S3C2410_SDICMDSTAT_INDEX (0xff)
60
61#define S3C2440_SDIDCON_DS_BYTE (0<<22)
62#define S3C2440_SDIDCON_DS_HALFWORD (1<<22)
63#define S3C2440_SDIDCON_DS_WORD (2<<22)
64#define S3C2410_SDIDCON_IRQPERIOD (1<<21)
65#define S3C2410_SDIDCON_TXAFTERRESP (1<<20)
66#define S3C2410_SDIDCON_RXAFTERCMD (1<<19)
67#define S3C2410_SDIDCON_BUSYAFTERCMD (1<<18)
68#define S3C2410_SDIDCON_BLOCKMODE (1<<17)
69#define S3C2410_SDIDCON_WIDEBUS (1<<16)
70#define S3C2410_SDIDCON_DMAEN (1<<15)
71#define S3C2410_SDIDCON_STOP (1<<14)
72#define S3C2440_SDIDCON_DATSTART (1<<14)
73#define S3C2410_SDIDCON_DATMODE (3<<12)
74#define S3C2410_SDIDCON_BLKNUM (0x7ff)
75
76/* constants for S3C2410_SDIDCON_DATMODE */
77#define S3C2410_SDIDCON_XFER_READY (0<<12)
78#define S3C2410_SDIDCON_XFER_CHKSTART (1<<12)
79#define S3C2410_SDIDCON_XFER_RXSTART (2<<12)
80#define S3C2410_SDIDCON_XFER_TXSTART (3<<12)
81
82#define S3C2410_SDIDCON_BLKNUM_MASK (0xFFF)
83#define S3C2410_SDIDCNT_BLKNUM_SHIFT (12)
84
85#define S3C2410_SDIDSTA_RDYWAITREQ (1<<10)
86#define S3C2410_SDIDSTA_SDIOIRQDETECT (1<<9)
87#define S3C2410_SDIDSTA_FIFOFAIL (1<<8) /* reserved on 2440 */
88#define S3C2410_SDIDSTA_CRCFAIL (1<<7)
89#define S3C2410_SDIDSTA_RXCRCFAIL (1<<6)
90#define S3C2410_SDIDSTA_DATATIMEOUT (1<<5)
91#define S3C2410_SDIDSTA_XFERFINISH (1<<4)
92#define S3C2410_SDIDSTA_BUSYFINISH (1<<3)
93#define S3C2410_SDIDSTA_SBITERR (1<<2) /* reserved on 2410a/2440 */
94#define S3C2410_SDIDSTA_TXDATAON (1<<1)
95#define S3C2410_SDIDSTA_RXDATAON (1<<0)
96
97#define S3C2440_SDIFSTA_FIFORESET (1<<16)
98#define S3C2440_SDIFSTA_FIFOFAIL (3<<14) /* 3 is correct (2 bits) */
99#define S3C2410_SDIFSTA_TFDET (1<<13)
100#define S3C2410_SDIFSTA_RFDET (1<<12)
101#define S3C2410_SDIFSTA_TFHALF (1<<11)
102#define S3C2410_SDIFSTA_TFEMPTY (1<<10)
103#define S3C2410_SDIFSTA_RFLAST (1<<9)
104#define S3C2410_SDIFSTA_RFFULL (1<<8)
105#define S3C2410_SDIFSTA_RFHALF (1<<7)
106#define S3C2410_SDIFSTA_COUNTMASK (0x7f)
107
108#define S3C2410_SDIIMSK_RESPONSECRC (1<<17)
109#define S3C2410_SDIIMSK_CMDSENT (1<<16)
110#define S3C2410_SDIIMSK_CMDTIMEOUT (1<<15)
111#define S3C2410_SDIIMSK_RESPONSEND (1<<14)
112#define S3C2410_SDIIMSK_READWAIT (1<<13)
113#define S3C2410_SDIIMSK_SDIOIRQ (1<<12)
114#define S3C2410_SDIIMSK_FIFOFAIL (1<<11)
115#define S3C2410_SDIIMSK_CRCSTATUS (1<<10)
116#define S3C2410_SDIIMSK_DATACRC (1<<9)
117#define S3C2410_SDIIMSK_DATATIMEOUT (1<<8)
118#define S3C2410_SDIIMSK_DATAFINISH (1<<7)
119#define S3C2410_SDIIMSK_BUSYFINISH (1<<6)
120#define S3C2410_SDIIMSK_SBITERR (1<<5) /* reserved 2440/2410a */
121#define S3C2410_SDIIMSK_TXFIFOHALF (1<<4)
122#define S3C2410_SDIIMSK_TXFIFOEMPTY (1<<3)
123#define S3C2410_SDIIMSK_RXFIFOLAST (1<<2)
124#define S3C2410_SDIIMSK_RXFIFOFULL (1<<1)
125#define S3C2410_SDIIMSK_RXFIFOHALF (1<<0)
126
127#endif /* __ASM_ARM_REGS_SDI */
diff --git a/arch/arm/mach-s3c24xx/irq-pm.c b/arch/arm/mach-s3c24xx/irq-pm.c
index e1199599873e..b91341ef2b2e 100644
--- a/arch/arm/mach-s3c24xx/irq-pm.c
+++ b/arch/arm/mach-s3c24xx/irq-pm.c
@@ -16,10 +16,15 @@
16#include <linux/interrupt.h> 16#include <linux/interrupt.h>
17#include <linux/irq.h> 17#include <linux/irq.h>
18#include <linux/syscore_ops.h> 18#include <linux/syscore_ops.h>
19#include <linux/io.h>
19 20
20#include <plat/cpu.h> 21#include <plat/cpu.h>
21#include <plat/pm.h> 22#include <plat/pm.h>
22#include <plat/irq.h> 23#include <plat/map-base.h>
24#include <plat/map-s3c.h>
25
26#include <mach/regs-irq.h>
27#include <mach/regs-gpio.h>
23 28
24#include <asm/irq.h> 29#include <asm/irq.h>
25 30
diff --git a/arch/arm/mach-s3c24xx/irq-s3c2412.c b/arch/arm/mach-s3c24xx/irq-s3c2412.c
deleted file mode 100644
index 67d763178d3f..000000000000
--- a/arch/arm/mach-s3c24xx/irq-s3c2412.c
+++ /dev/null
@@ -1,215 +0,0 @@
1/* linux/arch/arm/mach-s3c2412/irq.c
2 *
3 * Copyright (c) 2006 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 *
20*/
21
22#include <linux/init.h>
23#include <linux/module.h>
24#include <linux/interrupt.h>
25#include <linux/ioport.h>
26#include <linux/device.h>
27#include <linux/io.h>
28
29#include <mach/hardware.h>
30#include <asm/irq.h>
31
32#include <asm/mach/irq.h>
33
34#include <mach/regs-irq.h>
35#include <mach/regs-gpio.h>
36
37#include <plat/cpu.h>
38#include <plat/irq.h>
39#include <plat/pm.h>
40
41#include "s3c2412-power.h"
42
43#define INTMSK(start, end) ((1 << ((end) + 1 - (start))) - 1)
44#define INTMSK_SUB(start, end) (INTMSK(start, end) << ((start - S3C2410_IRQSUB(0))))
45
46/* the s3c2412 changes the behaviour of IRQ_EINT0 through IRQ_EINT3 by
47 * having them turn up in both the INT* and the EINT* registers. Whilst
48 * both show the status, they both now need to be acked when the IRQs
49 * go off.
50*/
51
52static void
53s3c2412_irq_mask(struct irq_data *data)
54{
55 unsigned long bitval = 1UL << (data->irq - IRQ_EINT0);
56 unsigned long mask;
57
58 mask = __raw_readl(S3C2410_INTMSK);
59 __raw_writel(mask | bitval, S3C2410_INTMSK);
60
61 mask = __raw_readl(S3C2412_EINTMASK);
62 __raw_writel(mask | bitval, S3C2412_EINTMASK);
63}
64
65static inline void
66s3c2412_irq_ack(struct irq_data *data)
67{
68 unsigned long bitval = 1UL << (data->irq - IRQ_EINT0);
69
70 __raw_writel(bitval, S3C2412_EINTPEND);
71 __raw_writel(bitval, S3C2410_SRCPND);
72 __raw_writel(bitval, S3C2410_INTPND);
73}
74
75static inline void
76s3c2412_irq_maskack(struct irq_data *data)
77{
78 unsigned long bitval = 1UL << (data->irq - IRQ_EINT0);
79 unsigned long mask;
80
81 mask = __raw_readl(S3C2410_INTMSK);
82 __raw_writel(mask|bitval, S3C2410_INTMSK);
83
84 mask = __raw_readl(S3C2412_EINTMASK);
85 __raw_writel(mask | bitval, S3C2412_EINTMASK);
86
87 __raw_writel(bitval, S3C2412_EINTPEND);
88 __raw_writel(bitval, S3C2410_SRCPND);
89 __raw_writel(bitval, S3C2410_INTPND);
90}
91
92static void
93s3c2412_irq_unmask(struct irq_data *data)
94{
95 unsigned long bitval = 1UL << (data->irq - IRQ_EINT0);
96 unsigned long mask;
97
98 mask = __raw_readl(S3C2412_EINTMASK);
99 __raw_writel(mask & ~bitval, S3C2412_EINTMASK);
100
101 mask = __raw_readl(S3C2410_INTMSK);
102 __raw_writel(mask & ~bitval, S3C2410_INTMSK);
103}
104
105static struct irq_chip s3c2412_irq_eint0t4 = {
106 .irq_ack = s3c2412_irq_ack,
107 .irq_mask = s3c2412_irq_mask,
108 .irq_unmask = s3c2412_irq_unmask,
109 .irq_set_wake = s3c_irq_wake,
110 .irq_set_type = s3c_irqext_type,
111};
112
113#define INTBIT(x) (1 << ((x) - S3C2410_IRQSUB(0)))
114
115/* CF and SDI sub interrupts */
116
117static void s3c2412_irq_demux_cfsdi(unsigned int irq, struct irq_desc *desc)
118{
119 unsigned int subsrc, submsk;
120
121 subsrc = __raw_readl(S3C2410_SUBSRCPND);
122 submsk = __raw_readl(S3C2410_INTSUBMSK);
123
124 subsrc &= ~submsk;
125
126 if (subsrc & INTBIT(IRQ_S3C2412_SDI))
127 generic_handle_irq(IRQ_S3C2412_SDI);
128
129 if (subsrc & INTBIT(IRQ_S3C2412_CF))
130 generic_handle_irq(IRQ_S3C2412_CF);
131}
132
133#define INTMSK_CFSDI (1UL << (IRQ_S3C2412_CFSDI - IRQ_EINT0))
134#define SUBMSK_CFSDI INTMSK_SUB(IRQ_S3C2412_SDI, IRQ_S3C2412_CF)
135
136static void s3c2412_irq_cfsdi_mask(struct irq_data *data)
137{
138 s3c_irqsub_mask(data->irq, INTMSK_CFSDI, SUBMSK_CFSDI);
139}
140
141static void s3c2412_irq_cfsdi_unmask(struct irq_data *data)
142{
143 s3c_irqsub_unmask(data->irq, INTMSK_CFSDI);
144}
145
146static void s3c2412_irq_cfsdi_ack(struct irq_data *data)
147{
148 s3c_irqsub_maskack(data->irq, INTMSK_CFSDI, SUBMSK_CFSDI);
149}
150
151static struct irq_chip s3c2412_irq_cfsdi = {
152 .name = "s3c2412-cfsdi",
153 .irq_ack = s3c2412_irq_cfsdi_ack,
154 .irq_mask = s3c2412_irq_cfsdi_mask,
155 .irq_unmask = s3c2412_irq_cfsdi_unmask,
156};
157
158static int s3c2412_irq_rtc_wake(struct irq_data *data, unsigned int state)
159{
160 unsigned long pwrcfg;
161
162 pwrcfg = __raw_readl(S3C2412_PWRCFG);
163 if (state)
164 pwrcfg &= ~S3C2412_PWRCFG_RTC_MASKIRQ;
165 else
166 pwrcfg |= S3C2412_PWRCFG_RTC_MASKIRQ;
167 __raw_writel(pwrcfg, S3C2412_PWRCFG);
168
169 return s3c_irq_chip.irq_set_wake(data, state);
170}
171
172static struct irq_chip s3c2412_irq_rtc_chip;
173
174static int s3c2412_irq_add(struct device *dev, struct subsys_interface *sif)
175{
176 unsigned int irqno;
177
178 for (irqno = IRQ_EINT0; irqno <= IRQ_EINT3; irqno++) {
179 irq_set_chip_and_handler(irqno, &s3c2412_irq_eint0t4,
180 handle_edge_irq);
181 set_irq_flags(irqno, IRQF_VALID);
182 }
183
184 /* add demux support for CF/SDI */
185
186 irq_set_chained_handler(IRQ_S3C2412_CFSDI, s3c2412_irq_demux_cfsdi);
187
188 for (irqno = IRQ_S3C2412_SDI; irqno <= IRQ_S3C2412_CF; irqno++) {
189 irq_set_chip_and_handler(irqno, &s3c2412_irq_cfsdi,
190 handle_level_irq);
191 set_irq_flags(irqno, IRQF_VALID);
192 }
193
194 /* change RTC IRQ's set wake method */
195
196 s3c2412_irq_rtc_chip = s3c_irq_chip;
197 s3c2412_irq_rtc_chip.irq_set_wake = s3c2412_irq_rtc_wake;
198
199 irq_set_chip(IRQ_RTC, &s3c2412_irq_rtc_chip);
200
201 return 0;
202}
203
204static struct subsys_interface s3c2412_irq_interface = {
205 .name = "s3c2412_irq",
206 .subsys = &s3c2412_subsys,
207 .add_dev = s3c2412_irq_add,
208};
209
210static int s3c2412_irq_init(void)
211{
212 return subsys_interface_register(&s3c2412_irq_interface);
213}
214
215arch_initcall(s3c2412_irq_init);
diff --git a/arch/arm/mach-s3c24xx/irq-s3c2440.c b/arch/arm/mach-s3c24xx/irq-s3c2440.c
deleted file mode 100644
index 4a18cde439cc..000000000000
--- a/arch/arm/mach-s3c24xx/irq-s3c2440.c
+++ /dev/null
@@ -1,128 +0,0 @@
1/* linux/arch/arm/mach-s3c2440/irq.c
2 *
3 * Copyright (c) 2003-2004 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 *
20*/
21
22#include <linux/init.h>
23#include <linux/module.h>
24#include <linux/interrupt.h>
25#include <linux/ioport.h>
26#include <linux/device.h>
27#include <linux/io.h>
28
29#include <mach/hardware.h>
30#include <asm/irq.h>
31
32#include <asm/mach/irq.h>
33
34#include <mach/regs-irq.h>
35#include <mach/regs-gpio.h>
36
37#include <plat/cpu.h>
38#include <plat/pm.h>
39#include <plat/irq.h>
40
41/* WDT/AC97 */
42
43static void s3c_irq_demux_wdtac97(unsigned int irq,
44 struct irq_desc *desc)
45{
46 unsigned int subsrc, submsk;
47
48 /* read the current pending interrupts, and the mask
49 * for what it is available */
50
51 subsrc = __raw_readl(S3C2410_SUBSRCPND);
52 submsk = __raw_readl(S3C2410_INTSUBMSK);
53
54 subsrc &= ~submsk;
55 subsrc >>= 13;
56 subsrc &= 3;
57
58 if (subsrc != 0) {
59 if (subsrc & 1) {
60 generic_handle_irq(IRQ_S3C2440_WDT);
61 }
62 if (subsrc & 2) {
63 generic_handle_irq(IRQ_S3C2440_AC97);
64 }
65 }
66}
67
68
69#define INTMSK_WDT (1UL << (IRQ_WDT - IRQ_EINT0))
70
71static void
72s3c_irq_wdtac97_mask(struct irq_data *data)
73{
74 s3c_irqsub_mask(data->irq, INTMSK_WDT, 3 << 13);
75}
76
77static void
78s3c_irq_wdtac97_unmask(struct irq_data *data)
79{
80 s3c_irqsub_unmask(data->irq, INTMSK_WDT);
81}
82
83static void
84s3c_irq_wdtac97_ack(struct irq_data *data)
85{
86 s3c_irqsub_maskack(data->irq, INTMSK_WDT, 3 << 13);
87}
88
89static struct irq_chip s3c_irq_wdtac97 = {
90 .irq_mask = s3c_irq_wdtac97_mask,
91 .irq_unmask = s3c_irq_wdtac97_unmask,
92 .irq_ack = s3c_irq_wdtac97_ack,
93};
94
95static int s3c2440_irq_add(struct device *dev, struct subsys_interface *sif)
96{
97 unsigned int irqno;
98
99 printk("S3C2440: IRQ Support\n");
100
101 /* add new chained handler for wdt, ac7 */
102
103 irq_set_chip_and_handler(IRQ_WDT, &s3c_irq_level_chip,
104 handle_level_irq);
105 irq_set_chained_handler(IRQ_WDT, s3c_irq_demux_wdtac97);
106
107 for (irqno = IRQ_S3C2440_WDT; irqno <= IRQ_S3C2440_AC97; irqno++) {
108 irq_set_chip_and_handler(irqno, &s3c_irq_wdtac97,
109 handle_level_irq);
110 set_irq_flags(irqno, IRQF_VALID);
111 }
112
113 return 0;
114}
115
116static struct subsys_interface s3c2440_irq_interface = {
117 .name = "s3c2440_irq",
118 .subsys = &s3c2440_subsys,
119 .add_dev = s3c2440_irq_add,
120};
121
122static int s3c2440_irq_init(void)
123{
124 return subsys_interface_register(&s3c2440_irq_interface);
125}
126
127arch_initcall(s3c2440_irq_init);
128
diff --git a/arch/arm/mach-s3c24xx/irq-s3c244x.c b/arch/arm/mach-s3c24xx/irq-s3c244x.c
deleted file mode 100644
index 5fe8e58d3afd..000000000000
--- a/arch/arm/mach-s3c24xx/irq-s3c244x.c
+++ /dev/null
@@ -1,142 +0,0 @@
1/* linux/arch/arm/plat-s3c24xx/s3c244x-irq.c
2 *
3 * Copyright (c) 2003-2004 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 *
20*/
21
22#include <linux/init.h>
23#include <linux/module.h>
24#include <linux/interrupt.h>
25#include <linux/ioport.h>
26#include <linux/device.h>
27#include <linux/io.h>
28
29#include <mach/hardware.h>
30#include <asm/irq.h>
31
32#include <asm/mach/irq.h>
33
34#include <mach/regs-irq.h>
35#include <mach/regs-gpio.h>
36
37#include <plat/cpu.h>
38#include <plat/pm.h>
39#include <plat/irq.h>
40
41/* camera irq */
42
43static void s3c_irq_demux_cam(unsigned int irq,
44 struct irq_desc *desc)
45{
46 unsigned int subsrc, submsk;
47
48 /* read the current pending interrupts, and the mask
49 * for what it is available */
50
51 subsrc = __raw_readl(S3C2410_SUBSRCPND);
52 submsk = __raw_readl(S3C2410_INTSUBMSK);
53
54 subsrc &= ~submsk;
55 subsrc >>= 11;
56 subsrc &= 3;
57
58 if (subsrc != 0) {
59 if (subsrc & 1) {
60 generic_handle_irq(IRQ_S3C2440_CAM_C);
61 }
62 if (subsrc & 2) {
63 generic_handle_irq(IRQ_S3C2440_CAM_P);
64 }
65 }
66}
67
68#define INTMSK_CAM (1UL << (IRQ_CAM - IRQ_EINT0))
69
70static void
71s3c_irq_cam_mask(struct irq_data *data)
72{
73 s3c_irqsub_mask(data->irq, INTMSK_CAM, 3 << 11);
74}
75
76static void
77s3c_irq_cam_unmask(struct irq_data *data)
78{
79 s3c_irqsub_unmask(data->irq, INTMSK_CAM);
80}
81
82static void
83s3c_irq_cam_ack(struct irq_data *data)
84{
85 s3c_irqsub_maskack(data->irq, INTMSK_CAM, 3 << 11);
86}
87
88static struct irq_chip s3c_irq_cam = {
89 .irq_mask = s3c_irq_cam_mask,
90 .irq_unmask = s3c_irq_cam_unmask,
91 .irq_ack = s3c_irq_cam_ack,
92};
93
94static int s3c244x_irq_add(struct device *dev, struct subsys_interface *sif)
95{
96 unsigned int irqno;
97
98 irq_set_chip_and_handler(IRQ_NFCON, &s3c_irq_level_chip,
99 handle_level_irq);
100 set_irq_flags(IRQ_NFCON, IRQF_VALID);
101
102 /* add chained handler for camera */
103
104 irq_set_chip_and_handler(IRQ_CAM, &s3c_irq_level_chip,
105 handle_level_irq);
106 irq_set_chained_handler(IRQ_CAM, s3c_irq_demux_cam);
107
108 for (irqno = IRQ_S3C2440_CAM_C; irqno <= IRQ_S3C2440_CAM_P; irqno++) {
109 irq_set_chip_and_handler(irqno, &s3c_irq_cam,
110 handle_level_irq);
111 set_irq_flags(irqno, IRQF_VALID);
112 }
113
114 return 0;
115}
116
117static struct subsys_interface s3c2440_irq_interface = {
118 .name = "s3c2440_irq",
119 .subsys = &s3c2440_subsys,
120 .add_dev = s3c244x_irq_add,
121};
122
123static int s3c2440_irq_init(void)
124{
125 return subsys_interface_register(&s3c2440_irq_interface);
126}
127
128arch_initcall(s3c2440_irq_init);
129
130static struct subsys_interface s3c2442_irq_interface = {
131 .name = "s3c2442_irq",
132 .subsys = &s3c2442_subsys,
133 .add_dev = s3c244x_irq_add,
134};
135
136
137static int s3c2442_irq_init(void)
138{
139 return subsys_interface_register(&s3c2442_irq_interface);
140}
141
142arch_initcall(s3c2442_irq_init);
diff --git a/arch/arm/mach-s3c24xx/irq.c b/arch/arm/mach-s3c24xx/irq.c
deleted file mode 100644
index cb9f5e011e73..000000000000
--- a/arch/arm/mach-s3c24xx/irq.c
+++ /dev/null
@@ -1,822 +0,0 @@
1/*
2 * S3C24XX IRQ handling
3 *
4 * Copyright (c) 2003-2004 Simtec Electronics
5 * Ben Dooks <ben@simtec.co.uk>
6 * Copyright (c) 2012 Heiko Stuebner <heiko@sntech.de>
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17*/
18
19#include <linux/init.h>
20#include <linux/slab.h>
21#include <linux/module.h>
22#include <linux/io.h>
23#include <linux/err.h>
24#include <linux/interrupt.h>
25#include <linux/ioport.h>
26#include <linux/device.h>
27#include <linux/irqdomain.h>
28
29#include <asm/mach/irq.h>
30
31#include <mach/regs-irq.h>
32#include <mach/regs-gpio.h>
33
34#include <plat/cpu.h>
35#include <plat/regs-irqtype.h>
36#include <plat/pm.h>
37#include <plat/irq.h>
38
39#define S3C_IRQTYPE_NONE 0
40#define S3C_IRQTYPE_EINT 1
41#define S3C_IRQTYPE_EDGE 2
42#define S3C_IRQTYPE_LEVEL 3
43
44struct s3c_irq_data {
45 unsigned int type;
46 unsigned long parent_irq;
47
48 /* data gets filled during init */
49 struct s3c_irq_intc *intc;
50 unsigned long sub_bits;
51 struct s3c_irq_intc *sub_intc;
52};
53
54/*
55 * Sructure holding the controller data
56 * @reg_pending register holding pending irqs
57 * @reg_intpnd special register intpnd in main intc
58 * @reg_mask mask register
59 * @domain irq_domain of the controller
60 * @parent parent controller for ext and sub irqs
61 * @irqs irq-data, always s3c_irq_data[32]
62 */
63struct s3c_irq_intc {
64 void __iomem *reg_pending;
65 void __iomem *reg_intpnd;
66 void __iomem *reg_mask;
67 struct irq_domain *domain;
68 struct s3c_irq_intc *parent;
69 struct s3c_irq_data *irqs;
70};
71
72static void s3c_irq_mask(struct irq_data *data)
73{
74 struct s3c_irq_intc *intc = data->domain->host_data;
75 struct s3c_irq_intc *parent_intc = intc->parent;
76 struct s3c_irq_data *irq_data = &intc->irqs[data->hwirq];
77 struct s3c_irq_data *parent_data;
78 unsigned long mask;
79 unsigned int irqno;
80
81 mask = __raw_readl(intc->reg_mask);
82 mask |= (1UL << data->hwirq);
83 __raw_writel(mask, intc->reg_mask);
84
85 if (parent_intc && irq_data->parent_irq) {
86 parent_data = &parent_intc->irqs[irq_data->parent_irq];
87
88 /* check to see if we need to mask the parent IRQ */
89 if ((mask & parent_data->sub_bits) == parent_data->sub_bits) {
90 irqno = irq_find_mapping(parent_intc->domain,
91 irq_data->parent_irq);
92 s3c_irq_mask(irq_get_irq_data(irqno));
93 }
94 }
95}
96
97static void s3c_irq_unmask(struct irq_data *data)
98{
99 struct s3c_irq_intc *intc = data->domain->host_data;
100 struct s3c_irq_intc *parent_intc = intc->parent;
101 struct s3c_irq_data *irq_data = &intc->irqs[data->hwirq];
102 unsigned long mask;
103 unsigned int irqno;
104
105 mask = __raw_readl(intc->reg_mask);
106 mask &= ~(1UL << data->hwirq);
107 __raw_writel(mask, intc->reg_mask);
108
109 if (parent_intc && irq_data->parent_irq) {
110 irqno = irq_find_mapping(parent_intc->domain,
111 irq_data->parent_irq);
112 s3c_irq_unmask(irq_get_irq_data(irqno));
113 }
114}
115
116static inline void s3c_irq_ack(struct irq_data *data)
117{
118 struct s3c_irq_intc *intc = data->domain->host_data;
119 unsigned long bitval = 1UL << data->hwirq;
120
121 __raw_writel(bitval, intc->reg_pending);
122 if (intc->reg_intpnd)
123 __raw_writel(bitval, intc->reg_intpnd);
124}
125
126static int s3c_irqext_type_set(void __iomem *gpcon_reg,
127 void __iomem *extint_reg,
128 unsigned long gpcon_offset,
129 unsigned long extint_offset,
130 unsigned int type)
131{
132 unsigned long newvalue = 0, value;
133
134 /* Set the GPIO to external interrupt mode */
135 value = __raw_readl(gpcon_reg);
136 value = (value & ~(3 << gpcon_offset)) | (0x02 << gpcon_offset);
137 __raw_writel(value, gpcon_reg);
138
139 /* Set the external interrupt to pointed trigger type */
140 switch (type)
141 {
142 case IRQ_TYPE_NONE:
143 pr_warn("No edge setting!\n");
144 break;
145
146 case IRQ_TYPE_EDGE_RISING:
147 newvalue = S3C2410_EXTINT_RISEEDGE;
148 break;
149
150 case IRQ_TYPE_EDGE_FALLING:
151 newvalue = S3C2410_EXTINT_FALLEDGE;
152 break;
153
154 case IRQ_TYPE_EDGE_BOTH:
155 newvalue = S3C2410_EXTINT_BOTHEDGE;
156 break;
157
158 case IRQ_TYPE_LEVEL_LOW:
159 newvalue = S3C2410_EXTINT_LOWLEV;
160 break;
161
162 case IRQ_TYPE_LEVEL_HIGH:
163 newvalue = S3C2410_EXTINT_HILEV;
164 break;
165
166 default:
167 pr_err("No such irq type %d", type);
168 return -EINVAL;
169 }
170
171 value = __raw_readl(extint_reg);
172 value = (value & ~(7 << extint_offset)) | (newvalue << extint_offset);
173 __raw_writel(value, extint_reg);
174
175 return 0;
176}
177
178/* FIXME: make static when it's out of plat-samsung/irq.h */
179int s3c_irqext_type(struct irq_data *data, unsigned int type)
180{
181 void __iomem *extint_reg;
182 void __iomem *gpcon_reg;
183 unsigned long gpcon_offset, extint_offset;
184
185 if ((data->hwirq >= 4) && (data->hwirq <= 7)) {
186 gpcon_reg = S3C2410_GPFCON;
187 extint_reg = S3C24XX_EXTINT0;
188 gpcon_offset = (data->hwirq) * 2;
189 extint_offset = (data->hwirq) * 4;
190 } else if ((data->hwirq >= 8) && (data->hwirq <= 15)) {
191 gpcon_reg = S3C2410_GPGCON;
192 extint_reg = S3C24XX_EXTINT1;
193 gpcon_offset = (data->hwirq - 8) * 2;
194 extint_offset = (data->hwirq - 8) * 4;
195 } else if ((data->hwirq >= 16) && (data->hwirq <= 23)) {
196 gpcon_reg = S3C2410_GPGCON;
197 extint_reg = S3C24XX_EXTINT2;
198 gpcon_offset = (data->hwirq - 8) * 2;
199 extint_offset = (data->hwirq - 16) * 4;
200 } else {
201 return -EINVAL;
202 }
203
204 return s3c_irqext_type_set(gpcon_reg, extint_reg, gpcon_offset,
205 extint_offset, type);
206}
207
208static int s3c_irqext0_type(struct irq_data *data, unsigned int type)
209{
210 void __iomem *extint_reg;
211 void __iomem *gpcon_reg;
212 unsigned long gpcon_offset, extint_offset;
213
214 if ((data->hwirq >= 0) && (data->hwirq <= 3)) {
215 gpcon_reg = S3C2410_GPFCON;
216 extint_reg = S3C24XX_EXTINT0;
217 gpcon_offset = (data->hwirq) * 2;
218 extint_offset = (data->hwirq) * 4;
219 } else {
220 return -EINVAL;
221 }
222
223 return s3c_irqext_type_set(gpcon_reg, extint_reg, gpcon_offset,
224 extint_offset, type);
225}
226
227struct irq_chip s3c_irq_chip = {
228 .name = "s3c",
229 .irq_ack = s3c_irq_ack,
230 .irq_mask = s3c_irq_mask,
231 .irq_unmask = s3c_irq_unmask,
232 .irq_set_wake = s3c_irq_wake
233};
234
235struct irq_chip s3c_irq_level_chip = {
236 .name = "s3c-level",
237 .irq_mask = s3c_irq_mask,
238 .irq_unmask = s3c_irq_unmask,
239 .irq_ack = s3c_irq_ack,
240};
241
242static struct irq_chip s3c_irqext_chip = {
243 .name = "s3c-ext",
244 .irq_mask = s3c_irq_mask,
245 .irq_unmask = s3c_irq_unmask,
246 .irq_ack = s3c_irq_ack,
247 .irq_set_type = s3c_irqext_type,
248 .irq_set_wake = s3c_irqext_wake
249};
250
251static struct irq_chip s3c_irq_eint0t4 = {
252 .name = "s3c-ext0",
253 .irq_ack = s3c_irq_ack,
254 .irq_mask = s3c_irq_mask,
255 .irq_unmask = s3c_irq_unmask,
256 .irq_set_wake = s3c_irq_wake,
257 .irq_set_type = s3c_irqext0_type,
258};
259
260static void s3c_irq_demux(unsigned int irq, struct irq_desc *desc)
261{
262 struct irq_chip *chip = irq_desc_get_chip(desc);
263 struct s3c_irq_intc *intc = desc->irq_data.domain->host_data;
264 struct s3c_irq_data *irq_data = &intc->irqs[desc->irq_data.hwirq];
265 struct s3c_irq_intc *sub_intc = irq_data->sub_intc;
266 unsigned long src;
267 unsigned long msk;
268 unsigned int n;
269
270 chained_irq_enter(chip, desc);
271
272 src = __raw_readl(sub_intc->reg_pending);
273 msk = __raw_readl(sub_intc->reg_mask);
274
275 src &= ~msk;
276 src &= irq_data->sub_bits;
277
278 while (src) {
279 n = __ffs(src);
280 src &= ~(1 << n);
281 generic_handle_irq(irq_find_mapping(sub_intc->domain, n));
282 }
283
284 chained_irq_exit(chip, desc);
285}
286
287#ifdef CONFIG_FIQ
288/**
289 * s3c24xx_set_fiq - set the FIQ routing
290 * @irq: IRQ number to route to FIQ on processor.
291 * @on: Whether to route @irq to the FIQ, or to remove the FIQ routing.
292 *
293 * Change the state of the IRQ to FIQ routing depending on @irq and @on. If
294 * @on is true, the @irq is checked to see if it can be routed and the
295 * interrupt controller updated to route the IRQ. If @on is false, the FIQ
296 * routing is cleared, regardless of which @irq is specified.
297 */
298int s3c24xx_set_fiq(unsigned int irq, bool on)
299{
300 u32 intmod;
301 unsigned offs;
302
303 if (on) {
304 offs = irq - FIQ_START;
305 if (offs > 31)
306 return -EINVAL;
307
308 intmod = 1 << offs;
309 } else {
310 intmod = 0;
311 }
312
313 __raw_writel(intmod, S3C2410_INTMOD);
314 return 0;
315}
316
317EXPORT_SYMBOL_GPL(s3c24xx_set_fiq);
318#endif
319
320static int s3c24xx_irq_map(struct irq_domain *h, unsigned int virq,
321 irq_hw_number_t hw)
322{
323 struct s3c_irq_intc *intc = h->host_data;
324 struct s3c_irq_data *irq_data = &intc->irqs[hw];
325 struct s3c_irq_intc *parent_intc;
326 struct s3c_irq_data *parent_irq_data;
327 unsigned int irqno;
328
329 if (!intc) {
330 pr_err("irq-s3c24xx: no controller found for hwirq %lu\n", hw);
331 return -EINVAL;
332 }
333
334 if (!irq_data) {
335 pr_err("irq-s3c24xx: no irq data found for hwirq %lu\n", hw);
336 return -EINVAL;
337 }
338
339 /* attach controller pointer to irq_data */
340 irq_data->intc = intc;
341
342 /* set handler and flags */
343 switch (irq_data->type) {
344 case S3C_IRQTYPE_NONE:
345 return 0;
346 case S3C_IRQTYPE_EINT:
347 if (irq_data->parent_irq)
348 irq_set_chip_and_handler(virq, &s3c_irqext_chip,
349 handle_edge_irq);
350 else
351 irq_set_chip_and_handler(virq, &s3c_irq_eint0t4,
352 handle_edge_irq);
353 break;
354 case S3C_IRQTYPE_EDGE:
355 if (irq_data->parent_irq ||
356 intc->reg_pending == S3C2416_SRCPND2)
357 irq_set_chip_and_handler(virq, &s3c_irq_level_chip,
358 handle_edge_irq);
359 else
360 irq_set_chip_and_handler(virq, &s3c_irq_chip,
361 handle_edge_irq);
362 break;
363 case S3C_IRQTYPE_LEVEL:
364 if (irq_data->parent_irq)
365 irq_set_chip_and_handler(virq, &s3c_irq_level_chip,
366 handle_level_irq);
367 else
368 irq_set_chip_and_handler(virq, &s3c_irq_chip,
369 handle_level_irq);
370 break;
371 default:
372 pr_err("irq-s3c24xx: unsupported irqtype %d\n", irq_data->type);
373 return -EINVAL;
374 }
375 set_irq_flags(virq, IRQF_VALID);
376
377 if (irq_data->parent_irq) {
378 parent_intc = intc->parent;
379 if (!parent_intc) {
380 pr_err("irq-s3c24xx: no parent controller found for hwirq %lu\n",
381 hw);
382 goto err;
383 }
384
385 parent_irq_data = &parent_intc->irqs[irq_data->parent_irq];
386 if (!irq_data) {
387 pr_err("irq-s3c24xx: no irq data found for hwirq %lu\n",
388 hw);
389 goto err;
390 }
391
392 parent_irq_data->sub_intc = intc;
393 parent_irq_data->sub_bits |= (1UL << hw);
394
395 /* attach the demuxer to the parent irq */
396 irqno = irq_find_mapping(parent_intc->domain,
397 irq_data->parent_irq);
398 if (!irqno) {
399 pr_err("irq-s3c24xx: could not find mapping for parent irq %lu\n",
400 irq_data->parent_irq);
401 goto err;
402 }
403 irq_set_chained_handler(irqno, s3c_irq_demux);
404 }
405
406 return 0;
407
408err:
409 set_irq_flags(virq, 0);
410
411 /* the only error can result from bad mapping data*/
412 return -EINVAL;
413}
414
415static struct irq_domain_ops s3c24xx_irq_ops = {
416 .map = s3c24xx_irq_map,
417 .xlate = irq_domain_xlate_twocell,
418};
419
420static void s3c24xx_clear_intc(struct s3c_irq_intc *intc)
421{
422 void __iomem *reg_source;
423 unsigned long pend;
424 unsigned long last;
425 int i;
426
427 /* if intpnd is set, read the next pending irq from there */
428 reg_source = intc->reg_intpnd ? intc->reg_intpnd : intc->reg_pending;
429
430 last = 0;
431 for (i = 0; i < 4; i++) {
432 pend = __raw_readl(reg_source);
433
434 if (pend == 0 || pend == last)
435 break;
436
437 __raw_writel(pend, intc->reg_pending);
438 if (intc->reg_intpnd)
439 __raw_writel(pend, intc->reg_intpnd);
440
441 pr_info("irq: clearing pending status %08x\n", (int)pend);
442 last = pend;
443 }
444}
445
446struct s3c_irq_intc *s3c24xx_init_intc(struct device_node *np,
447 struct s3c_irq_data *irq_data,
448 struct s3c_irq_intc *parent,
449 unsigned long address)
450{
451 struct s3c_irq_intc *intc;
452 void __iomem *base = (void *)0xf6000000; /* static mapping */
453 int irq_num;
454 int irq_start;
455 int irq_offset;
456 int ret;
457
458 intc = kzalloc(sizeof(struct s3c_irq_intc), GFP_KERNEL);
459 if (!intc)
460 return ERR_PTR(-ENOMEM);
461
462 intc->irqs = irq_data;
463
464 if (parent)
465 intc->parent = parent;
466
467 /* select the correct data for the controller.
468 * Need to hard code the irq num start and offset
469 * to preserve the static mapping for now
470 */
471 switch (address) {
472 case 0x4a000000:
473 pr_debug("irq: found main intc\n");
474 intc->reg_pending = base;
475 intc->reg_mask = base + 0x08;
476 intc->reg_intpnd = base + 0x10;
477 irq_num = 32;
478 irq_start = S3C2410_IRQ(0);
479 irq_offset = 0;
480 break;
481 case 0x4a000018:
482 pr_debug("irq: found subintc\n");
483 intc->reg_pending = base + 0x18;
484 intc->reg_mask = base + 0x1c;
485 irq_num = 29;
486 irq_start = S3C2410_IRQSUB(0);
487 irq_offset = 0;
488 break;
489 case 0x4a000040:
490 pr_debug("irq: found intc2\n");
491 intc->reg_pending = base + 0x40;
492 intc->reg_mask = base + 0x48;
493 intc->reg_intpnd = base + 0x50;
494 irq_num = 8;
495 irq_start = S3C2416_IRQ(0);
496 irq_offset = 0;
497 break;
498 case 0x560000a4:
499 pr_debug("irq: found eintc\n");
500 base = (void *)0xfd000000;
501
502 intc->reg_mask = base + 0xa4;
503 intc->reg_pending = base + 0x08;
504 irq_num = 20;
505 irq_start = S3C2410_IRQ(32);
506 irq_offset = 4;
507 break;
508 default:
509 pr_err("irq: unsupported controller address\n");
510 ret = -EINVAL;
511 goto err;
512 }
513
514 /* now that all the data is complete, init the irq-domain */
515 s3c24xx_clear_intc(intc);
516 intc->domain = irq_domain_add_legacy(np, irq_num, irq_start,
517 irq_offset, &s3c24xx_irq_ops,
518 intc);
519 if (!intc->domain) {
520 pr_err("irq: could not create irq-domain\n");
521 ret = -EINVAL;
522 goto err;
523 }
524
525 return intc;
526
527err:
528 kfree(intc);
529 return ERR_PTR(ret);
530}
531
532/* s3c24xx_init_irq
533 *
534 * Initialise S3C2410 IRQ system
535*/
536
537static struct s3c_irq_data init_base[32] = {
538 { .type = S3C_IRQTYPE_EINT, }, /* EINT0 */
539 { .type = S3C_IRQTYPE_EINT, }, /* EINT1 */
540 { .type = S3C_IRQTYPE_EINT, }, /* EINT2 */
541 { .type = S3C_IRQTYPE_EINT, }, /* EINT3 */
542 { .type = S3C_IRQTYPE_LEVEL, }, /* EINT4to7 */
543 { .type = S3C_IRQTYPE_LEVEL, }, /* EINT8to23 */
544 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
545 { .type = S3C_IRQTYPE_EDGE, }, /* nBATT_FLT */
546 { .type = S3C_IRQTYPE_EDGE, }, /* TICK */
547 { .type = S3C_IRQTYPE_EDGE, }, /* WDT */
548 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER0 */
549 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER1 */
550 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER2 */
551 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER3 */
552 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER4 */
553 { .type = S3C_IRQTYPE_LEVEL, }, /* UART2 */
554 { .type = S3C_IRQTYPE_EDGE, }, /* LCD */
555 { .type = S3C_IRQTYPE_EDGE, }, /* DMA0 */
556 { .type = S3C_IRQTYPE_EDGE, }, /* DMA1 */
557 { .type = S3C_IRQTYPE_EDGE, }, /* DMA2 */
558 { .type = S3C_IRQTYPE_EDGE, }, /* DMA3 */
559 { .type = S3C_IRQTYPE_EDGE, }, /* SDI */
560 { .type = S3C_IRQTYPE_EDGE, }, /* SPI0 */
561 { .type = S3C_IRQTYPE_LEVEL, }, /* UART1 */
562 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
563 { .type = S3C_IRQTYPE_EDGE, }, /* USBD */
564 { .type = S3C_IRQTYPE_EDGE, }, /* USBH */
565 { .type = S3C_IRQTYPE_EDGE, }, /* IIC */
566 { .type = S3C_IRQTYPE_LEVEL, }, /* UART0 */
567 { .type = S3C_IRQTYPE_EDGE, }, /* SPI1 */
568 { .type = S3C_IRQTYPE_EDGE, }, /* RTC */
569 { .type = S3C_IRQTYPE_LEVEL, }, /* ADCPARENT */
570};
571
572static struct s3c_irq_data init_eint[32] = {
573 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
574 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
575 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
576 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
577 { .type = S3C_IRQTYPE_EINT, .parent_irq = 4 }, /* EINT4 */
578 { .type = S3C_IRQTYPE_EINT, .parent_irq = 4 }, /* EINT5 */
579 { .type = S3C_IRQTYPE_EINT, .parent_irq = 4 }, /* EINT6 */
580 { .type = S3C_IRQTYPE_EINT, .parent_irq = 4 }, /* EINT7 */
581 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT8 */
582 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT9 */
583 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT10 */
584 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT11 */
585 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT12 */
586 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT13 */
587 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT14 */
588 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT15 */
589 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT16 */
590 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT17 */
591 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT18 */
592 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT19 */
593 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT20 */
594 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT21 */
595 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT22 */
596 { .type = S3C_IRQTYPE_EINT, .parent_irq = 5 }, /* EINT23 */
597};
598
599static struct s3c_irq_data init_subint[32] = {
600 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-RX */
601 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-TX */
602 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-ERR */
603 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-RX */
604 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-TX */
605 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-ERR */
606 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-RX */
607 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-TX */
608 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-ERR */
609 { .type = S3C_IRQTYPE_EDGE, .parent_irq = 31 }, /* TC */
610 { .type = S3C_IRQTYPE_EDGE, .parent_irq = 31 }, /* ADC */
611};
612
613void __init s3c24xx_init_irq(void)
614{
615 struct s3c_irq_intc *main_intc;
616
617#ifdef CONFIG_FIQ
618 init_FIQ(FIQ_START);
619#endif
620
621 main_intc = s3c24xx_init_intc(NULL, &init_base[0], NULL, 0x4a000000);
622 if (IS_ERR(main_intc)) {
623 pr_err("irq: could not create main interrupt controller\n");
624 return;
625 }
626
627 s3c24xx_init_intc(NULL, &init_subint[0], main_intc, 0x4a000018);
628 s3c24xx_init_intc(NULL, &init_eint[0], main_intc, 0x560000a4);
629}
630
631#ifdef CONFIG_CPU_S3C2416
632static struct s3c_irq_data init_s3c2416base[32] = {
633 { .type = S3C_IRQTYPE_EINT, }, /* EINT0 */
634 { .type = S3C_IRQTYPE_EINT, }, /* EINT1 */
635 { .type = S3C_IRQTYPE_EINT, }, /* EINT2 */
636 { .type = S3C_IRQTYPE_EINT, }, /* EINT3 */
637 { .type = S3C_IRQTYPE_LEVEL, }, /* EINT4to7 */
638 { .type = S3C_IRQTYPE_LEVEL, }, /* EINT8to23 */
639 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
640 { .type = S3C_IRQTYPE_EDGE, }, /* nBATT_FLT */
641 { .type = S3C_IRQTYPE_EDGE, }, /* TICK */
642 { .type = S3C_IRQTYPE_LEVEL, }, /* WDT/AC97 */
643 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER0 */
644 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER1 */
645 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER2 */
646 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER3 */
647 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER4 */
648 { .type = S3C_IRQTYPE_LEVEL, }, /* UART2 */
649 { .type = S3C_IRQTYPE_LEVEL, }, /* LCD */
650 { .type = S3C_IRQTYPE_LEVEL, }, /* DMA */
651 { .type = S3C_IRQTYPE_LEVEL, }, /* UART3 */
652 { .type = S3C_IRQTYPE_NONE, }, /* reserved */
653 { .type = S3C_IRQTYPE_EDGE, }, /* SDI1 */
654 { .type = S3C_IRQTYPE_EDGE, }, /* SDI0 */
655 { .type = S3C_IRQTYPE_EDGE, }, /* SPI0 */
656 { .type = S3C_IRQTYPE_LEVEL, }, /* UART1 */
657 { .type = S3C_IRQTYPE_EDGE, }, /* NAND */
658 { .type = S3C_IRQTYPE_EDGE, }, /* USBD */
659 { .type = S3C_IRQTYPE_EDGE, }, /* USBH */
660 { .type = S3C_IRQTYPE_EDGE, }, /* IIC */
661 { .type = S3C_IRQTYPE_LEVEL, }, /* UART0 */
662 { .type = S3C_IRQTYPE_NONE, },
663 { .type = S3C_IRQTYPE_EDGE, }, /* RTC */
664 { .type = S3C_IRQTYPE_LEVEL, }, /* ADCPARENT */
665};
666
667static struct s3c_irq_data init_s3c2416subint[32] = {
668 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-RX */
669 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-TX */
670 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-ERR */
671 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-RX */
672 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-TX */
673 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-ERR */
674 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-RX */
675 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-TX */
676 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-ERR */
677 { .type = S3C_IRQTYPE_EDGE, .parent_irq = 31 }, /* TC */
678 { .type = S3C_IRQTYPE_EDGE, .parent_irq = 31 }, /* ADC */
679 { .type = S3C_IRQTYPE_NONE }, /* reserved */
680 { .type = S3C_IRQTYPE_NONE }, /* reserved */
681 { .type = S3C_IRQTYPE_NONE }, /* reserved */
682 { .type = S3C_IRQTYPE_NONE }, /* reserved */
683 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 16 }, /* LCD2 */
684 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 16 }, /* LCD3 */
685 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 16 }, /* LCD4 */
686 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA0 */
687 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA1 */
688 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA2 */
689 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA3 */
690 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA4 */
691 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA5 */
692 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 18 }, /* UART3-RX */
693 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 18 }, /* UART3-TX */
694 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 18 }, /* UART3-ERR */
695 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 9 }, /* WDT */
696 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 9 }, /* AC97 */
697};
698
699static struct s3c_irq_data init_s3c2416_second[32] = {
700 { .type = S3C_IRQTYPE_EDGE }, /* 2D */
701 { .type = S3C_IRQTYPE_EDGE }, /* IIC1 */
702 { .type = S3C_IRQTYPE_NONE }, /* reserved */
703 { .type = S3C_IRQTYPE_NONE }, /* reserved */
704 { .type = S3C_IRQTYPE_EDGE }, /* PCM0 */
705 { .type = S3C_IRQTYPE_EDGE }, /* PCM1 */
706 { .type = S3C_IRQTYPE_EDGE }, /* I2S0 */
707 { .type = S3C_IRQTYPE_EDGE }, /* I2S1 */
708};
709
710void __init s3c2416_init_irq(void)
711{
712 struct s3c_irq_intc *main_intc;
713
714 pr_info("S3C2416: IRQ Support\n");
715
716#ifdef CONFIG_FIQ
717 init_FIQ(FIQ_START);
718#endif
719
720 main_intc = s3c24xx_init_intc(NULL, &init_s3c2416base[0], NULL, 0x4a000000);
721 if (IS_ERR(main_intc)) {
722 pr_err("irq: could not create main interrupt controller\n");
723 return;
724 }
725
726 s3c24xx_init_intc(NULL, &init_eint[0], main_intc, 0x560000a4);
727 s3c24xx_init_intc(NULL, &init_s3c2416subint[0], main_intc, 0x4a000018);
728
729 s3c24xx_init_intc(NULL, &init_s3c2416_second[0], NULL, 0x4a000040);
730}
731
732#endif
733
734#ifdef CONFIG_CPU_S3C2443
735static struct s3c_irq_data init_s3c2443base[32] = {
736 { .type = S3C_IRQTYPE_EINT, }, /* EINT0 */
737 { .type = S3C_IRQTYPE_EINT, }, /* EINT1 */
738 { .type = S3C_IRQTYPE_EINT, }, /* EINT2 */
739 { .type = S3C_IRQTYPE_EINT, }, /* EINT3 */
740 { .type = S3C_IRQTYPE_LEVEL, }, /* EINT4to7 */
741 { .type = S3C_IRQTYPE_LEVEL, }, /* EINT8to23 */
742 { .type = S3C_IRQTYPE_LEVEL, }, /* CAM */
743 { .type = S3C_IRQTYPE_EDGE, }, /* nBATT_FLT */
744 { .type = S3C_IRQTYPE_EDGE, }, /* TICK */
745 { .type = S3C_IRQTYPE_LEVEL, }, /* WDT/AC97 */
746 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER0 */
747 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER1 */
748 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER2 */
749 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER3 */
750 { .type = S3C_IRQTYPE_EDGE, }, /* TIMER4 */
751 { .type = S3C_IRQTYPE_LEVEL, }, /* UART2 */
752 { .type = S3C_IRQTYPE_LEVEL, }, /* LCD */
753 { .type = S3C_IRQTYPE_LEVEL, }, /* DMA */
754 { .type = S3C_IRQTYPE_LEVEL, }, /* UART3 */
755 { .type = S3C_IRQTYPE_EDGE, }, /* CFON */
756 { .type = S3C_IRQTYPE_EDGE, }, /* SDI1 */
757 { .type = S3C_IRQTYPE_EDGE, }, /* SDI0 */
758 { .type = S3C_IRQTYPE_EDGE, }, /* SPI0 */
759 { .type = S3C_IRQTYPE_LEVEL, }, /* UART1 */
760 { .type = S3C_IRQTYPE_EDGE, }, /* NAND */
761 { .type = S3C_IRQTYPE_EDGE, }, /* USBD */
762 { .type = S3C_IRQTYPE_EDGE, }, /* USBH */
763 { .type = S3C_IRQTYPE_EDGE, }, /* IIC */
764 { .type = S3C_IRQTYPE_LEVEL, }, /* UART0 */
765 { .type = S3C_IRQTYPE_EDGE, }, /* SPI1 */
766 { .type = S3C_IRQTYPE_EDGE, }, /* RTC */
767 { .type = S3C_IRQTYPE_LEVEL, }, /* ADCPARENT */
768};
769
770
771static struct s3c_irq_data init_s3c2443subint[32] = {
772 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-RX */
773 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-TX */
774 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 28 }, /* UART0-ERR */
775 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-RX */
776 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-TX */
777 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 23 }, /* UART1-ERR */
778 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-RX */
779 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-TX */
780 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 15 }, /* UART2-ERR */
781 { .type = S3C_IRQTYPE_EDGE, .parent_irq = 31 }, /* TC */
782 { .type = S3C_IRQTYPE_EDGE, .parent_irq = 31 }, /* ADC */
783 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 6 }, /* CAM_C */
784 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 6 }, /* CAM_P */
785 { .type = S3C_IRQTYPE_NONE }, /* reserved */
786 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 16 }, /* LCD1 */
787 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 16 }, /* LCD2 */
788 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 16 }, /* LCD3 */
789 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 16 }, /* LCD4 */
790 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA0 */
791 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA1 */
792 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA2 */
793 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA3 */
794 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA4 */
795 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 17 }, /* DMA5 */
796 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 18 }, /* UART3-RX */
797 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 18 }, /* UART3-TX */
798 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 18 }, /* UART3-ERR */
799 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 9 }, /* WDT */
800 { .type = S3C_IRQTYPE_LEVEL, .parent_irq = 9 }, /* AC97 */
801};
802
803void __init s3c2443_init_irq(void)
804{
805 struct s3c_irq_intc *main_intc;
806
807 pr_info("S3C2443: IRQ Support\n");
808
809#ifdef CONFIG_FIQ
810 init_FIQ(FIQ_START);
811#endif
812
813 main_intc = s3c24xx_init_intc(NULL, &init_s3c2443base[0], NULL, 0x4a000000);
814 if (IS_ERR(main_intc)) {
815 pr_err("irq: could not create main interrupt controller\n");
816 return;
817 }
818
819 s3c24xx_init_intc(NULL, &init_eint[0], main_intc, 0x560000a4);
820 s3c24xx_init_intc(NULL, &init_s3c2443subint[0], main_intc, 0x4a000018);
821}
822#endif
diff --git a/arch/arm/mach-s3c24xx/mach-amlm5900.c b/arch/arm/mach-s3c24xx/mach-amlm5900.c
index 0e0279e79150..e27b5c91b3db 100644
--- a/arch/arm/mach-s3c24xx/mach-amlm5900.c
+++ b/arch/arm/mach-s3c24xx/mach-amlm5900.c
@@ -63,6 +63,8 @@
63#include <linux/mtd/map.h> 63#include <linux/mtd/map.h>
64#include <linux/mtd/physmap.h> 64#include <linux/mtd/physmap.h>
65 65
66#include <plat/samsung-time.h>
67
66#include "common.h" 68#include "common.h"
67 69
68static struct resource amlm5900_nor_resource = 70static struct resource amlm5900_nor_resource =
@@ -160,6 +162,7 @@ static void __init amlm5900_map_io(void)
160 s3c24xx_init_io(amlm5900_iodesc, ARRAY_SIZE(amlm5900_iodesc)); 162 s3c24xx_init_io(amlm5900_iodesc, ARRAY_SIZE(amlm5900_iodesc));
161 s3c24xx_init_clocks(0); 163 s3c24xx_init_clocks(0);
162 s3c24xx_init_uarts(amlm5900_uartcfgs, ARRAY_SIZE(amlm5900_uartcfgs)); 164 s3c24xx_init_uarts(amlm5900_uartcfgs, ARRAY_SIZE(amlm5900_uartcfgs));
165 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
163} 166}
164 167
165#ifdef CONFIG_FB_S3C2410 168#ifdef CONFIG_FB_S3C2410
@@ -235,8 +238,8 @@ static void __init amlm5900_init(void)
235MACHINE_START(AML_M5900, "AML_M5900") 238MACHINE_START(AML_M5900, "AML_M5900")
236 .atag_offset = 0x100, 239 .atag_offset = 0x100,
237 .map_io = amlm5900_map_io, 240 .map_io = amlm5900_map_io,
238 .init_irq = s3c24xx_init_irq, 241 .init_irq = s3c2410_init_irq,
239 .init_machine = amlm5900_init, 242 .init_machine = amlm5900_init,
240 .init_time = s3c24xx_timer_init, 243 .init_time = samsung_timer_init,
241 .restart = s3c2410_restart, 244 .restart = s3c2410_restart,
242MACHINE_END 245MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-anubis.c b/arch/arm/mach-s3c24xx/mach-anubis.c
index bb595f15ce36..c1fb6c37867f 100644
--- a/arch/arm/mach-s3c24xx/mach-anubis.c
+++ b/arch/arm/mach-s3c24xx/mach-anubis.c
@@ -49,6 +49,7 @@
49#include <plat/devs.h> 49#include <plat/devs.h>
50#include <plat/cpu.h> 50#include <plat/cpu.h>
51#include <linux/platform_data/asoc-s3c24xx_simtec.h> 51#include <linux/platform_data/asoc-s3c24xx_simtec.h>
52#include <plat/samsung-time.h>
52 53
53#include "anubis.h" 54#include "anubis.h"
54#include "common.h" 55#include "common.h"
@@ -410,6 +411,7 @@ static void __init anubis_map_io(void)
410 s3c24xx_init_io(anubis_iodesc, ARRAY_SIZE(anubis_iodesc)); 411 s3c24xx_init_io(anubis_iodesc, ARRAY_SIZE(anubis_iodesc));
411 s3c24xx_init_clocks(0); 412 s3c24xx_init_clocks(0);
412 s3c24xx_init_uarts(anubis_uartcfgs, ARRAY_SIZE(anubis_uartcfgs)); 413 s3c24xx_init_uarts(anubis_uartcfgs, ARRAY_SIZE(anubis_uartcfgs));
414 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
413 415
414 /* check for the newer revision boards with large page nand */ 416 /* check for the newer revision boards with large page nand */
415 417
@@ -443,7 +445,7 @@ MACHINE_START(ANUBIS, "Simtec-Anubis")
443 .atag_offset = 0x100, 445 .atag_offset = 0x100,
444 .map_io = anubis_map_io, 446 .map_io = anubis_map_io,
445 .init_machine = anubis_init, 447 .init_machine = anubis_init,
446 .init_irq = s3c24xx_init_irq, 448 .init_irq = s3c2440_init_irq,
447 .init_time = s3c24xx_timer_init, 449 .init_time = samsung_timer_init,
448 .restart = s3c244x_restart, 450 .restart = s3c244x_restart,
449MACHINE_END 451MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-at2440evb.c b/arch/arm/mach-s3c24xx/mach-at2440evb.c
index b4bc60c78ebb..6dfeeb7ef469 100644
--- a/arch/arm/mach-s3c24xx/mach-at2440evb.c
+++ b/arch/arm/mach-s3c24xx/mach-at2440evb.c
@@ -48,6 +48,7 @@
48#include <plat/devs.h> 48#include <plat/devs.h>
49#include <plat/cpu.h> 49#include <plat/cpu.h>
50#include <linux/platform_data/mmc-s3cmci.h> 50#include <linux/platform_data/mmc-s3cmci.h>
51#include <plat/samsung-time.h>
51 52
52#include "common.h" 53#include "common.h"
53 54
@@ -192,6 +193,7 @@ static void __init at2440evb_map_io(void)
192 s3c24xx_init_io(at2440evb_iodesc, ARRAY_SIZE(at2440evb_iodesc)); 193 s3c24xx_init_io(at2440evb_iodesc, ARRAY_SIZE(at2440evb_iodesc));
193 s3c24xx_init_clocks(16934400); 194 s3c24xx_init_clocks(16934400);
194 s3c24xx_init_uarts(at2440evb_uartcfgs, ARRAY_SIZE(at2440evb_uartcfgs)); 195 s3c24xx_init_uarts(at2440evb_uartcfgs, ARRAY_SIZE(at2440evb_uartcfgs));
196 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
195} 197}
196 198
197static void __init at2440evb_init(void) 199static void __init at2440evb_init(void)
@@ -209,7 +211,7 @@ MACHINE_START(AT2440EVB, "AT2440EVB")
209 .atag_offset = 0x100, 211 .atag_offset = 0x100,
210 .map_io = at2440evb_map_io, 212 .map_io = at2440evb_map_io,
211 .init_machine = at2440evb_init, 213 .init_machine = at2440evb_init,
212 .init_irq = s3c24xx_init_irq, 214 .init_irq = s3c2440_init_irq,
213 .init_time = s3c24xx_timer_init, 215 .init_time = samsung_timer_init,
214 .restart = s3c244x_restart, 216 .restart = s3c244x_restart,
215MACHINE_END 217MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-bast.c b/arch/arm/mach-s3c24xx/mach-bast.c
index ca6618081041..22d6ae926d91 100644
--- a/arch/arm/mach-s3c24xx/mach-bast.c
+++ b/arch/arm/mach-s3c24xx/mach-bast.c
@@ -55,6 +55,7 @@
55#include <plat/devs.h> 55#include <plat/devs.h>
56#include <plat/gpio-cfg.h> 56#include <plat/gpio-cfg.h>
57#include <plat/regs-serial.h> 57#include <plat/regs-serial.h>
58#include <plat/samsung-time.h>
58 59
59#include "bast.h" 60#include "bast.h"
60#include "common.h" 61#include "common.h"
@@ -576,6 +577,7 @@ static void __init bast_map_io(void)
576 s3c24xx_init_io(bast_iodesc, ARRAY_SIZE(bast_iodesc)); 577 s3c24xx_init_io(bast_iodesc, ARRAY_SIZE(bast_iodesc));
577 s3c24xx_init_clocks(0); 578 s3c24xx_init_clocks(0);
578 s3c24xx_init_uarts(bast_uartcfgs, ARRAY_SIZE(bast_uartcfgs)); 579 s3c24xx_init_uarts(bast_uartcfgs, ARRAY_SIZE(bast_uartcfgs));
580 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
579} 581}
580 582
581static void __init bast_init(void) 583static void __init bast_init(void)
@@ -603,8 +605,8 @@ MACHINE_START(BAST, "Simtec-BAST")
603 /* Maintainer: Ben Dooks <ben@simtec.co.uk> */ 605 /* Maintainer: Ben Dooks <ben@simtec.co.uk> */
604 .atag_offset = 0x100, 606 .atag_offset = 0x100,
605 .map_io = bast_map_io, 607 .map_io = bast_map_io,
606 .init_irq = s3c24xx_init_irq, 608 .init_irq = s3c2410_init_irq,
607 .init_machine = bast_init, 609 .init_machine = bast_init,
608 .init_time = s3c24xx_timer_init, 610 .init_time = samsung_timer_init,
609 .restart = s3c2410_restart, 611 .restart = s3c2410_restart,
610MACHINE_END 612MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-gta02.c b/arch/arm/mach-s3c24xx/mach-gta02.c
index a25e8c5a7b4c..13d8d073675a 100644
--- a/arch/arm/mach-s3c24xx/mach-gta02.c
+++ b/arch/arm/mach-s3c24xx/mach-gta02.c
@@ -81,6 +81,7 @@
81#include <plat/gpio-cfg.h> 81#include <plat/gpio-cfg.h>
82#include <plat/pm.h> 82#include <plat/pm.h>
83#include <plat/regs-serial.h> 83#include <plat/regs-serial.h>
84#include <plat/samsung-time.h>
84 85
85#include "common.h" 86#include "common.h"
86#include "gta02.h" 87#include "gta02.h"
@@ -501,6 +502,7 @@ static void __init gta02_map_io(void)
501 s3c24xx_init_io(gta02_iodesc, ARRAY_SIZE(gta02_iodesc)); 502 s3c24xx_init_io(gta02_iodesc, ARRAY_SIZE(gta02_iodesc));
502 s3c24xx_init_clocks(12000000); 503 s3c24xx_init_clocks(12000000);
503 s3c24xx_init_uarts(gta02_uartcfgs, ARRAY_SIZE(gta02_uartcfgs)); 504 s3c24xx_init_uarts(gta02_uartcfgs, ARRAY_SIZE(gta02_uartcfgs));
505 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
504} 506}
505 507
506 508
@@ -587,8 +589,8 @@ MACHINE_START(NEO1973_GTA02, "GTA02")
587 /* Maintainer: Nelson Castillo <arhuaco@freaks-unidos.net> */ 589 /* Maintainer: Nelson Castillo <arhuaco@freaks-unidos.net> */
588 .atag_offset = 0x100, 590 .atag_offset = 0x100,
589 .map_io = gta02_map_io, 591 .map_io = gta02_map_io,
590 .init_irq = s3c24xx_init_irq, 592 .init_irq = s3c2442_init_irq,
591 .init_machine = gta02_machine_init, 593 .init_machine = gta02_machine_init,
592 .init_time = s3c24xx_timer_init, 594 .init_time = samsung_timer_init,
593 .restart = s3c244x_restart, 595 .restart = s3c244x_restart,
594MACHINE_END 596MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-h1940.c b/arch/arm/mach-s3c24xx/mach-h1940.c
index 79bc0830d740..af4334d6b4d5 100644
--- a/arch/arm/mach-s3c24xx/mach-h1940.c
+++ b/arch/arm/mach-s3c24xx/mach-h1940.c
@@ -62,7 +62,7 @@
62#include <plat/pll.h> 62#include <plat/pll.h>
63#include <plat/pm.h> 63#include <plat/pm.h>
64#include <plat/regs-serial.h> 64#include <plat/regs-serial.h>
65 65#include <plat/samsung-time.h>
66 66
67#include "common.h" 67#include "common.h"
68#include "h1940.h" 68#include "h1940.h"
@@ -646,6 +646,7 @@ static void __init h1940_map_io(void)
646 s3c24xx_init_io(h1940_iodesc, ARRAY_SIZE(h1940_iodesc)); 646 s3c24xx_init_io(h1940_iodesc, ARRAY_SIZE(h1940_iodesc));
647 s3c24xx_init_clocks(0); 647 s3c24xx_init_clocks(0);
648 s3c24xx_init_uarts(h1940_uartcfgs, ARRAY_SIZE(h1940_uartcfgs)); 648 s3c24xx_init_uarts(h1940_uartcfgs, ARRAY_SIZE(h1940_uartcfgs));
649 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
649 650
650 /* setup PM */ 651 /* setup PM */
651 652
@@ -666,11 +667,6 @@ static void __init h1940_reserve(void)
666 memblock_reserve(0x30081000, 0x1000); 667 memblock_reserve(0x30081000, 0x1000);
667} 668}
668 669
669static void __init h1940_init_irq(void)
670{
671 s3c24xx_init_irq();
672}
673
674static void __init h1940_init(void) 670static void __init h1940_init(void)
675{ 671{
676 u32 tmp; 672 u32 tmp;
@@ -739,8 +735,8 @@ MACHINE_START(H1940, "IPAQ-H1940")
739 .atag_offset = 0x100, 735 .atag_offset = 0x100,
740 .map_io = h1940_map_io, 736 .map_io = h1940_map_io,
741 .reserve = h1940_reserve, 737 .reserve = h1940_reserve,
742 .init_irq = h1940_init_irq, 738 .init_irq = s3c2410_init_irq,
743 .init_machine = h1940_init, 739 .init_machine = h1940_init,
744 .init_time = s3c24xx_timer_init, 740 .init_time = samsung_timer_init,
745 .restart = s3c2410_restart, 741 .restart = s3c2410_restart,
746MACHINE_END 742MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-jive.c b/arch/arm/mach-s3c24xx/mach-jive.c
index 54e83c1f780c..a45fcd8ccf79 100644
--- a/arch/arm/mach-s3c24xx/mach-jive.c
+++ b/arch/arm/mach-s3c24xx/mach-jive.c
@@ -46,14 +46,15 @@
46#include <linux/mtd/nand_ecc.h> 46#include <linux/mtd/nand_ecc.h>
47#include <linux/mtd/partitions.h> 47#include <linux/mtd/partitions.h>
48 48
49#include <plat/s3c2412.h>
50#include <plat/gpio-cfg.h> 49#include <plat/gpio-cfg.h>
51#include <plat/clock.h> 50#include <plat/clock.h>
52#include <plat/devs.h> 51#include <plat/devs.h>
53#include <plat/cpu.h> 52#include <plat/cpu.h>
54#include <plat/pm.h> 53#include <plat/pm.h>
55#include <linux/platform_data/usb-s3c2410_udc.h> 54#include <linux/platform_data/usb-s3c2410_udc.h>
55#include <plat/samsung-time.h>
56 56
57#include "common.h"
57#include "s3c2412-power.h" 58#include "s3c2412-power.h"
58 59
59static struct map_desc jive_iodesc[] __initdata = { 60static struct map_desc jive_iodesc[] __initdata = {
@@ -506,6 +507,7 @@ static void __init jive_map_io(void)
506 s3c24xx_init_io(jive_iodesc, ARRAY_SIZE(jive_iodesc)); 507 s3c24xx_init_io(jive_iodesc, ARRAY_SIZE(jive_iodesc));
507 s3c24xx_init_clocks(12000000); 508 s3c24xx_init_clocks(12000000);
508 s3c24xx_init_uarts(jive_uartcfgs, ARRAY_SIZE(jive_uartcfgs)); 509 s3c24xx_init_uarts(jive_uartcfgs, ARRAY_SIZE(jive_uartcfgs));
510 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
509} 511}
510 512
511static void jive_power_off(void) 513static void jive_power_off(void)
@@ -658,9 +660,9 @@ MACHINE_START(JIVE, "JIVE")
658 /* Maintainer: Ben Dooks <ben-linux@fluff.org> */ 660 /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
659 .atag_offset = 0x100, 661 .atag_offset = 0x100,
660 662
661 .init_irq = s3c24xx_init_irq, 663 .init_irq = s3c2412_init_irq,
662 .map_io = jive_map_io, 664 .map_io = jive_map_io,
663 .init_machine = jive_machine_init, 665 .init_machine = jive_machine_init,
664 .init_time = s3c24xx_timer_init, 666 .init_time = samsung_timer_init,
665 .restart = s3c2412_restart, 667 .restart = s3c2412_restart,
666MACHINE_END 668MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-mini2440.c b/arch/arm/mach-s3c24xx/mach-mini2440.c
index 2865e5919f2c..a83db46320bc 100644
--- a/arch/arm/mach-s3c24xx/mach-mini2440.c
+++ b/arch/arm/mach-s3c24xx/mach-mini2440.c
@@ -56,6 +56,7 @@
56#include <plat/clock.h> 56#include <plat/clock.h>
57#include <plat/devs.h> 57#include <plat/devs.h>
58#include <plat/cpu.h> 58#include <plat/cpu.h>
59#include <plat/samsung-time.h>
59 60
60#include <sound/s3c24xx_uda134x.h> 61#include <sound/s3c24xx_uda134x.h>
61 62
@@ -525,6 +526,7 @@ static void __init mini2440_map_io(void)
525 s3c24xx_init_io(mini2440_iodesc, ARRAY_SIZE(mini2440_iodesc)); 526 s3c24xx_init_io(mini2440_iodesc, ARRAY_SIZE(mini2440_iodesc));
526 s3c24xx_init_clocks(12000000); 527 s3c24xx_init_clocks(12000000);
527 s3c24xx_init_uarts(mini2440_uartcfgs, ARRAY_SIZE(mini2440_uartcfgs)); 528 s3c24xx_init_uarts(mini2440_uartcfgs, ARRAY_SIZE(mini2440_uartcfgs));
529 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
528} 530}
529 531
530/* 532/*
@@ -686,7 +688,7 @@ MACHINE_START(MINI2440, "MINI2440")
686 .atag_offset = 0x100, 688 .atag_offset = 0x100,
687 .map_io = mini2440_map_io, 689 .map_io = mini2440_map_io,
688 .init_machine = mini2440_init, 690 .init_machine = mini2440_init,
689 .init_irq = s3c24xx_init_irq, 691 .init_irq = s3c2440_init_irq,
690 .init_time = s3c24xx_timer_init, 692 .init_time = samsung_timer_init,
691 .restart = s3c244x_restart, 693 .restart = s3c244x_restart,
692MACHINE_END 694MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-n30.c b/arch/arm/mach-s3c24xx/mach-n30.c
index d9d04b240295..2cb46c37c920 100644
--- a/arch/arm/mach-s3c24xx/mach-n30.c
+++ b/arch/arm/mach-s3c24xx/mach-n30.c
@@ -48,8 +48,8 @@
48#include <plat/cpu.h> 48#include <plat/cpu.h>
49#include <plat/devs.h> 49#include <plat/devs.h>
50#include <linux/platform_data/mmc-s3cmci.h> 50#include <linux/platform_data/mmc-s3cmci.h>
51#include <plat/s3c2410.h>
52#include <linux/platform_data/usb-s3c2410_udc.h> 51#include <linux/platform_data/usb-s3c2410_udc.h>
52#include <plat/samsung-time.h>
53 53
54#include "common.h" 54#include "common.h"
55 55
@@ -536,6 +536,7 @@ static void __init n30_map_io(void)
536 n30_hwinit(); 536 n30_hwinit();
537 s3c24xx_init_clocks(0); 537 s3c24xx_init_clocks(0);
538 s3c24xx_init_uarts(n30_uartcfgs, ARRAY_SIZE(n30_uartcfgs)); 538 s3c24xx_init_uarts(n30_uartcfgs, ARRAY_SIZE(n30_uartcfgs));
539 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
539} 540}
540 541
541/* GPB3 is the line that controls the pull-up for the USB D+ line */ 542/* GPB3 is the line that controls the pull-up for the USB D+ line */
@@ -589,9 +590,9 @@ MACHINE_START(N30, "Acer-N30")
589 Ben Dooks <ben-linux@fluff.org> 590 Ben Dooks <ben-linux@fluff.org>
590 */ 591 */
591 .atag_offset = 0x100, 592 .atag_offset = 0x100,
592 .init_time = s3c24xx_timer_init, 593 .init_time = samsung_timer_init,
593 .init_machine = n30_init, 594 .init_machine = n30_init,
594 .init_irq = s3c24xx_init_irq, 595 .init_irq = s3c2410_init_irq,
595 .map_io = n30_map_io, 596 .map_io = n30_map_io,
596 .restart = s3c2410_restart, 597 .restart = s3c2410_restart,
597MACHINE_END 598MACHINE_END
@@ -600,9 +601,9 @@ MACHINE_START(N35, "Acer-N35")
600 /* Maintainer: Christer Weinigel <christer@weinigel.se> 601 /* Maintainer: Christer Weinigel <christer@weinigel.se>
601 */ 602 */
602 .atag_offset = 0x100, 603 .atag_offset = 0x100,
603 .init_time = s3c24xx_timer_init, 604 .init_time = samsung_timer_init,
604 .init_machine = n30_init, 605 .init_machine = n30_init,
605 .init_irq = s3c24xx_init_irq, 606 .init_irq = s3c2410_init_irq,
606 .map_io = n30_map_io, 607 .map_io = n30_map_io,
607 .restart = s3c2410_restart, 608 .restart = s3c2410_restart,
608MACHINE_END 609MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-nexcoder.c b/arch/arm/mach-s3c24xx/mach-nexcoder.c
index a454e2461860..01f4354206f9 100644
--- a/arch/arm/mach-s3c24xx/mach-nexcoder.c
+++ b/arch/arm/mach-s3c24xx/mach-nexcoder.c
@@ -41,11 +41,10 @@
41#include <linux/platform_data/i2c-s3c2410.h> 41#include <linux/platform_data/i2c-s3c2410.h>
42 42
43#include <plat/gpio-cfg.h> 43#include <plat/gpio-cfg.h>
44#include <plat/s3c2410.h>
45#include <plat/s3c244x.h>
46#include <plat/clock.h> 44#include <plat/clock.h>
47#include <plat/devs.h> 45#include <plat/devs.h>
48#include <plat/cpu.h> 46#include <plat/cpu.h>
47#include <plat/samsung-time.h>
49 48
50#include "common.h" 49#include "common.h"
51 50
@@ -137,6 +136,7 @@ static void __init nexcoder_map_io(void)
137 s3c24xx_init_io(nexcoder_iodesc, ARRAY_SIZE(nexcoder_iodesc)); 136 s3c24xx_init_io(nexcoder_iodesc, ARRAY_SIZE(nexcoder_iodesc));
138 s3c24xx_init_clocks(0); 137 s3c24xx_init_clocks(0);
139 s3c24xx_init_uarts(nexcoder_uartcfgs, ARRAY_SIZE(nexcoder_uartcfgs)); 138 s3c24xx_init_uarts(nexcoder_uartcfgs, ARRAY_SIZE(nexcoder_uartcfgs));
139 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
140 140
141 nexcoder_sensorboard_init(); 141 nexcoder_sensorboard_init();
142} 142}
@@ -152,7 +152,7 @@ MACHINE_START(NEXCODER_2440, "NexVision - Nexcoder 2440")
152 .atag_offset = 0x100, 152 .atag_offset = 0x100,
153 .map_io = nexcoder_map_io, 153 .map_io = nexcoder_map_io,
154 .init_machine = nexcoder_init, 154 .init_machine = nexcoder_init,
155 .init_irq = s3c24xx_init_irq, 155 .init_irq = s3c2440_init_irq,
156 .init_time = s3c24xx_timer_init, 156 .init_time = samsung_timer_init,
157 .restart = s3c244x_restart, 157 .restart = s3c244x_restart,
158MACHINE_END 158MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-osiris.c b/arch/arm/mach-s3c24xx/mach-osiris.c
index ae2cbdf3e3ca..58d6fbe5bf1f 100644
--- a/arch/arm/mach-s3c24xx/mach-osiris.c
+++ b/arch/arm/mach-s3c24xx/mach-osiris.c
@@ -45,6 +45,7 @@
45#include <plat/devs.h> 45#include <plat/devs.h>
46#include <plat/gpio-cfg.h> 46#include <plat/gpio-cfg.h>
47#include <plat/regs-serial.h> 47#include <plat/regs-serial.h>
48#include <plat/samsung-time.h>
48 49
49#include <mach/hardware.h> 50#include <mach/hardware.h>
50#include <mach/regs-gpio.h> 51#include <mach/regs-gpio.h>
@@ -384,6 +385,7 @@ static void __init osiris_map_io(void)
384 s3c24xx_init_io(osiris_iodesc, ARRAY_SIZE(osiris_iodesc)); 385 s3c24xx_init_io(osiris_iodesc, ARRAY_SIZE(osiris_iodesc));
385 s3c24xx_init_clocks(0); 386 s3c24xx_init_clocks(0);
386 s3c24xx_init_uarts(osiris_uartcfgs, ARRAY_SIZE(osiris_uartcfgs)); 387 s3c24xx_init_uarts(osiris_uartcfgs, ARRAY_SIZE(osiris_uartcfgs));
388 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
387 389
388 /* check for the newer revision boards with large page nand */ 390 /* check for the newer revision boards with large page nand */
389 391
@@ -424,8 +426,8 @@ MACHINE_START(OSIRIS, "Simtec-OSIRIS")
424 /* Maintainer: Ben Dooks <ben@simtec.co.uk> */ 426 /* Maintainer: Ben Dooks <ben@simtec.co.uk> */
425 .atag_offset = 0x100, 427 .atag_offset = 0x100,
426 .map_io = osiris_map_io, 428 .map_io = osiris_map_io,
427 .init_irq = s3c24xx_init_irq, 429 .init_irq = s3c2440_init_irq,
428 .init_machine = osiris_init, 430 .init_machine = osiris_init,
429 .init_time = s3c24xx_timer_init, 431 .init_time = samsung_timer_init,
430 .restart = s3c244x_restart, 432 .restart = s3c244x_restart,
431MACHINE_END 433MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-otom.c b/arch/arm/mach-s3c24xx/mach-otom.c
index 40a47d6c6a85..7e16b0740ec1 100644
--- a/arch/arm/mach-s3c24xx/mach-otom.c
+++ b/arch/arm/mach-s3c24xx/mach-otom.c
@@ -33,7 +33,7 @@
33#include <plat/cpu.h> 33#include <plat/cpu.h>
34#include <plat/devs.h> 34#include <plat/devs.h>
35#include <plat/regs-serial.h> 35#include <plat/regs-serial.h>
36#include <plat/s3c2410.h> 36#include <plat/samsung-time.h>
37 37
38#include "common.h" 38#include "common.h"
39#include "otom.h" 39#include "otom.h"
@@ -102,6 +102,7 @@ static void __init otom11_map_io(void)
102 s3c24xx_init_io(otom11_iodesc, ARRAY_SIZE(otom11_iodesc)); 102 s3c24xx_init_io(otom11_iodesc, ARRAY_SIZE(otom11_iodesc));
103 s3c24xx_init_clocks(0); 103 s3c24xx_init_clocks(0);
104 s3c24xx_init_uarts(otom11_uartcfgs, ARRAY_SIZE(otom11_uartcfgs)); 104 s3c24xx_init_uarts(otom11_uartcfgs, ARRAY_SIZE(otom11_uartcfgs));
105 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
105} 106}
106 107
107static void __init otom11_init(void) 108static void __init otom11_init(void)
@@ -115,7 +116,7 @@ MACHINE_START(OTOM, "Nex Vision - Otom 1.1")
115 .atag_offset = 0x100, 116 .atag_offset = 0x100,
116 .map_io = otom11_map_io, 117 .map_io = otom11_map_io,
117 .init_machine = otom11_init, 118 .init_machine = otom11_init,
118 .init_irq = s3c24xx_init_irq, 119 .init_irq = s3c2410_init_irq,
119 .init_time = s3c24xx_timer_init, 120 .init_time = samsung_timer_init,
120 .restart = s3c2410_restart, 121 .restart = s3c2410_restart,
121MACHINE_END 122MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-qt2410.c b/arch/arm/mach-s3c24xx/mach-qt2410.c
index 56175f0941b1..f8feaeadb55a 100644
--- a/arch/arm/mach-s3c24xx/mach-qt2410.c
+++ b/arch/arm/mach-s3c24xx/mach-qt2410.c
@@ -55,13 +55,14 @@
55#include <linux/platform_data/usb-s3c2410_udc.h> 55#include <linux/platform_data/usb-s3c2410_udc.h>
56#include <linux/platform_data/i2c-s3c2410.h> 56#include <linux/platform_data/i2c-s3c2410.h>
57 57
58#include <plat/common-smdk.h>
59#include <plat/gpio-cfg.h> 58#include <plat/gpio-cfg.h>
60#include <plat/devs.h> 59#include <plat/devs.h>
61#include <plat/cpu.h> 60#include <plat/cpu.h>
62#include <plat/pm.h> 61#include <plat/pm.h>
62#include <plat/samsung-time.h>
63 63
64#include "common.h" 64#include "common.h"
65#include "common-smdk.h"
65 66
66static struct map_desc qt2410_iodesc[] __initdata = { 67static struct map_desc qt2410_iodesc[] __initdata = {
67 { 0xe0000000, __phys_to_pfn(S3C2410_CS3+0x01000000), SZ_1M, MT_DEVICE } 68 { 0xe0000000, __phys_to_pfn(S3C2410_CS3+0x01000000), SZ_1M, MT_DEVICE }
@@ -304,6 +305,7 @@ static void __init qt2410_map_io(void)
304 s3c24xx_init_io(qt2410_iodesc, ARRAY_SIZE(qt2410_iodesc)); 305 s3c24xx_init_io(qt2410_iodesc, ARRAY_SIZE(qt2410_iodesc));
305 s3c24xx_init_clocks(12*1000*1000); 306 s3c24xx_init_clocks(12*1000*1000);
306 s3c24xx_init_uarts(smdk2410_uartcfgs, ARRAY_SIZE(smdk2410_uartcfgs)); 307 s3c24xx_init_uarts(smdk2410_uartcfgs, ARRAY_SIZE(smdk2410_uartcfgs));
308 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
307} 309}
308 310
309static void __init qt2410_machine_init(void) 311static void __init qt2410_machine_init(void)
@@ -341,8 +343,8 @@ static void __init qt2410_machine_init(void)
341MACHINE_START(QT2410, "QT2410") 343MACHINE_START(QT2410, "QT2410")
342 .atag_offset = 0x100, 344 .atag_offset = 0x100,
343 .map_io = qt2410_map_io, 345 .map_io = qt2410_map_io,
344 .init_irq = s3c24xx_init_irq, 346 .init_irq = s3c2410_init_irq,
345 .init_machine = qt2410_machine_init, 347 .init_machine = qt2410_machine_init,
346 .init_time = s3c24xx_timer_init, 348 .init_time = samsung_timer_init,
347 .restart = s3c2410_restart, 349 .restart = s3c2410_restart,
348MACHINE_END 350MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-rx1950.c b/arch/arm/mach-s3c24xx/mach-rx1950.c
index 1f9ba2ae5288..e4d67a33ebee 100644
--- a/arch/arm/mach-s3c24xx/mach-rx1950.c
+++ b/arch/arm/mach-s3c24xx/mach-rx1950.c
@@ -58,6 +58,7 @@
58#include <plat/pm.h> 58#include <plat/pm.h>
59#include <plat/regs-iic.h> 59#include <plat/regs-iic.h>
60#include <plat/regs-serial.h> 60#include <plat/regs-serial.h>
61#include <plat/samsung-time.h>
61 62
62#include "common.h" 63#include "common.h"
63#include "h1940.h" 64#include "h1940.h"
@@ -741,6 +742,7 @@ static void __init rx1950_map_io(void)
741 s3c24xx_init_io(rx1950_iodesc, ARRAY_SIZE(rx1950_iodesc)); 742 s3c24xx_init_io(rx1950_iodesc, ARRAY_SIZE(rx1950_iodesc));
742 s3c24xx_init_clocks(16934000); 743 s3c24xx_init_clocks(16934000);
743 s3c24xx_init_uarts(rx1950_uartcfgs, ARRAY_SIZE(rx1950_uartcfgs)); 744 s3c24xx_init_uarts(rx1950_uartcfgs, ARRAY_SIZE(rx1950_uartcfgs));
745 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
744 746
745 /* setup PM */ 747 /* setup PM */
746 748
@@ -811,8 +813,8 @@ MACHINE_START(RX1950, "HP iPAQ RX1950")
811 .atag_offset = 0x100, 813 .atag_offset = 0x100,
812 .map_io = rx1950_map_io, 814 .map_io = rx1950_map_io,
813 .reserve = rx1950_reserve, 815 .reserve = rx1950_reserve,
814 .init_irq = s3c24xx_init_irq, 816 .init_irq = s3c2442_init_irq,
815 .init_machine = rx1950_init_machine, 817 .init_machine = rx1950_init_machine,
816 .init_time = s3c24xx_timer_init, 818 .init_time = samsung_timer_init,
817 .restart = s3c244x_restart, 819 .restart = s3c244x_restart,
818MACHINE_END 820MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-rx3715.c b/arch/arm/mach-s3c24xx/mach-rx3715.c
index f20418a2fb1b..3bc6231d0a1f 100644
--- a/arch/arm/mach-s3c24xx/mach-rx3715.c
+++ b/arch/arm/mach-s3c24xx/mach-rx3715.c
@@ -49,6 +49,7 @@
49#include <plat/devs.h> 49#include <plat/devs.h>
50#include <plat/pm.h> 50#include <plat/pm.h>
51#include <plat/regs-serial.h> 51#include <plat/regs-serial.h>
52#include <plat/samsung-time.h>
52 53
53#include "common.h" 54#include "common.h"
54#include "h1940.h" 55#include "h1940.h"
@@ -179,6 +180,7 @@ static void __init rx3715_map_io(void)
179 s3c24xx_init_io(rx3715_iodesc, ARRAY_SIZE(rx3715_iodesc)); 180 s3c24xx_init_io(rx3715_iodesc, ARRAY_SIZE(rx3715_iodesc));
180 s3c24xx_init_clocks(16934000); 181 s3c24xx_init_clocks(16934000);
181 s3c24xx_init_uarts(rx3715_uartcfgs, ARRAY_SIZE(rx3715_uartcfgs)); 182 s3c24xx_init_uarts(rx3715_uartcfgs, ARRAY_SIZE(rx3715_uartcfgs));
183 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
182} 184}
183 185
184/* H1940 and RX3715 need to reserve this for suspend */ 186/* H1940 and RX3715 need to reserve this for suspend */
@@ -188,11 +190,6 @@ static void __init rx3715_reserve(void)
188 memblock_reserve(0x30081000, 0x1000); 190 memblock_reserve(0x30081000, 0x1000);
189} 191}
190 192
191static void __init rx3715_init_irq(void)
192{
193 s3c24xx_init_irq();
194}
195
196static void __init rx3715_init_machine(void) 193static void __init rx3715_init_machine(void)
197{ 194{
198#ifdef CONFIG_PM_H1940 195#ifdef CONFIG_PM_H1940
@@ -210,8 +207,8 @@ MACHINE_START(RX3715, "IPAQ-RX3715")
210 .atag_offset = 0x100, 207 .atag_offset = 0x100,
211 .map_io = rx3715_map_io, 208 .map_io = rx3715_map_io,
212 .reserve = rx3715_reserve, 209 .reserve = rx3715_reserve,
213 .init_irq = rx3715_init_irq, 210 .init_irq = s3c2440_init_irq,
214 .init_machine = rx3715_init_machine, 211 .init_machine = rx3715_init_machine,
215 .init_time = s3c24xx_timer_init, 212 .init_time = samsung_timer_init,
216 .restart = s3c244x_restart, 213 .restart = s3c244x_restart,
217MACHINE_END 214MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-smdk2410.c b/arch/arm/mach-s3c24xx/mach-smdk2410.c
index e184bfa9613a..a773789e4f38 100644
--- a/arch/arm/mach-s3c24xx/mach-smdk2410.c
+++ b/arch/arm/mach-s3c24xx/mach-smdk2410.c
@@ -51,10 +51,10 @@
51 51
52#include <plat/devs.h> 52#include <plat/devs.h>
53#include <plat/cpu.h> 53#include <plat/cpu.h>
54 54#include <plat/samsung-time.h>
55#include <plat/common-smdk.h>
56 55
57#include "common.h" 56#include "common.h"
57#include "common-smdk.h"
58 58
59static struct map_desc smdk2410_iodesc[] __initdata = { 59static struct map_desc smdk2410_iodesc[] __initdata = {
60 /* nothing here yet */ 60 /* nothing here yet */
@@ -101,6 +101,7 @@ static void __init smdk2410_map_io(void)
101 s3c24xx_init_io(smdk2410_iodesc, ARRAY_SIZE(smdk2410_iodesc)); 101 s3c24xx_init_io(smdk2410_iodesc, ARRAY_SIZE(smdk2410_iodesc));
102 s3c24xx_init_clocks(0); 102 s3c24xx_init_clocks(0);
103 s3c24xx_init_uarts(smdk2410_uartcfgs, ARRAY_SIZE(smdk2410_uartcfgs)); 103 s3c24xx_init_uarts(smdk2410_uartcfgs, ARRAY_SIZE(smdk2410_uartcfgs));
104 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
104} 105}
105 106
106static void __init smdk2410_init(void) 107static void __init smdk2410_init(void)
@@ -115,8 +116,8 @@ MACHINE_START(SMDK2410, "SMDK2410") /* @TODO: request a new identifier and switc
115 /* Maintainer: Jonas Dietsche */ 116 /* Maintainer: Jonas Dietsche */
116 .atag_offset = 0x100, 117 .atag_offset = 0x100,
117 .map_io = smdk2410_map_io, 118 .map_io = smdk2410_map_io,
118 .init_irq = s3c24xx_init_irq, 119 .init_irq = s3c2410_init_irq,
119 .init_machine = smdk2410_init, 120 .init_machine = smdk2410_init,
120 .init_time = s3c24xx_timer_init, 121 .init_time = samsung_timer_init,
121 .restart = s3c2410_restart, 122 .restart = s3c2410_restart,
122MACHINE_END 123MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-smdk2413.c b/arch/arm/mach-s3c24xx/mach-smdk2413.c
index 86d7847c9d45..8146e920f10d 100644
--- a/arch/arm/mach-s3c24xx/mach-smdk2413.c
+++ b/arch/arm/mach-s3c24xx/mach-smdk2413.c
@@ -41,13 +41,13 @@
41#include <linux/platform_data/i2c-s3c2410.h> 41#include <linux/platform_data/i2c-s3c2410.h>
42#include <mach/fb.h> 42#include <mach/fb.h>
43 43
44#include <plat/s3c2410.h>
45#include <plat/s3c2412.h>
46#include <plat/clock.h> 44#include <plat/clock.h>
47#include <plat/devs.h> 45#include <plat/devs.h>
48#include <plat/cpu.h> 46#include <plat/cpu.h>
47#include <plat/samsung-time.h>
49 48
50#include <plat/common-smdk.h> 49#include "common.h"
50#include "common-smdk.h"
51 51
52static struct map_desc smdk2413_iodesc[] __initdata = { 52static struct map_desc smdk2413_iodesc[] __initdata = {
53}; 53};
@@ -106,6 +106,7 @@ static void __init smdk2413_map_io(void)
106 s3c24xx_init_io(smdk2413_iodesc, ARRAY_SIZE(smdk2413_iodesc)); 106 s3c24xx_init_io(smdk2413_iodesc, ARRAY_SIZE(smdk2413_iodesc));
107 s3c24xx_init_clocks(12000000); 107 s3c24xx_init_clocks(12000000);
108 s3c24xx_init_uarts(smdk2413_uartcfgs, ARRAY_SIZE(smdk2413_uartcfgs)); 108 s3c24xx_init_uarts(smdk2413_uartcfgs, ARRAY_SIZE(smdk2413_uartcfgs));
109 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
109} 110}
110 111
111static void __init smdk2413_machine_init(void) 112static void __init smdk2413_machine_init(void)
@@ -129,10 +130,10 @@ MACHINE_START(S3C2413, "S3C2413")
129 .atag_offset = 0x100, 130 .atag_offset = 0x100,
130 131
131 .fixup = smdk2413_fixup, 132 .fixup = smdk2413_fixup,
132 .init_irq = s3c24xx_init_irq, 133 .init_irq = s3c2412_init_irq,
133 .map_io = smdk2413_map_io, 134 .map_io = smdk2413_map_io,
134 .init_machine = smdk2413_machine_init, 135 .init_machine = smdk2413_machine_init,
135 .init_time = s3c24xx_timer_init, 136 .init_time = samsung_timer_init,
136 .restart = s3c2412_restart, 137 .restart = s3c2412_restart,
137MACHINE_END 138MACHINE_END
138 139
@@ -141,10 +142,10 @@ MACHINE_START(SMDK2412, "SMDK2412")
141 .atag_offset = 0x100, 142 .atag_offset = 0x100,
142 143
143 .fixup = smdk2413_fixup, 144 .fixup = smdk2413_fixup,
144 .init_irq = s3c24xx_init_irq, 145 .init_irq = s3c2412_init_irq,
145 .map_io = smdk2413_map_io, 146 .map_io = smdk2413_map_io,
146 .init_machine = smdk2413_machine_init, 147 .init_machine = smdk2413_machine_init,
147 .init_time = s3c24xx_timer_init, 148 .init_time = samsung_timer_init,
148 .restart = s3c2412_restart, 149 .restart = s3c2412_restart,
149MACHINE_END 150MACHINE_END
150 151
@@ -153,9 +154,9 @@ MACHINE_START(SMDK2413, "SMDK2413")
153 .atag_offset = 0x100, 154 .atag_offset = 0x100,
154 155
155 .fixup = smdk2413_fixup, 156 .fixup = smdk2413_fixup,
156 .init_irq = s3c24xx_init_irq, 157 .init_irq = s3c2412_init_irq,
157 .map_io = smdk2413_map_io, 158 .map_io = smdk2413_map_io,
158 .init_machine = smdk2413_machine_init, 159 .init_machine = smdk2413_machine_init,
159 .init_time = s3c24xx_timer_init, 160 .init_time = samsung_timer_init,
160 .restart = s3c2412_restart, 161 .restart = s3c2412_restart,
161MACHINE_END 162MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-smdk2416.c b/arch/arm/mach-s3c24xx/mach-smdk2416.c
index ebb2e61f3d07..cb46847c66b4 100644
--- a/arch/arm/mach-s3c24xx/mach-smdk2416.c
+++ b/arch/arm/mach-s3c24xx/mach-smdk2416.c
@@ -42,7 +42,6 @@
42#include <linux/platform_data/leds-s3c24xx.h> 42#include <linux/platform_data/leds-s3c24xx.h>
43#include <linux/platform_data/i2c-s3c2410.h> 43#include <linux/platform_data/i2c-s3c2410.h>
44 44
45#include <plat/s3c2416.h>
46#include <plat/gpio-cfg.h> 45#include <plat/gpio-cfg.h>
47#include <plat/clock.h> 46#include <plat/clock.h>
48#include <plat/devs.h> 47#include <plat/devs.h>
@@ -51,10 +50,12 @@
51#include <plat/sdhci.h> 50#include <plat/sdhci.h>
52#include <linux/platform_data/usb-s3c2410_udc.h> 51#include <linux/platform_data/usb-s3c2410_udc.h>
53#include <linux/platform_data/s3c-hsudc.h> 52#include <linux/platform_data/s3c-hsudc.h>
53#include <plat/samsung-time.h>
54 54
55#include <plat/fb.h> 55#include <plat/fb.h>
56 56
57#include <plat/common-smdk.h> 57#include "common.h"
58#include "common-smdk.h"
58 59
59static struct map_desc smdk2416_iodesc[] __initdata = { 60static struct map_desc smdk2416_iodesc[] __initdata = {
60 /* ISA IO Space map (memory space selected by A24) */ 61 /* ISA IO Space map (memory space selected by A24) */
@@ -221,6 +222,7 @@ static void __init smdk2416_map_io(void)
221 s3c24xx_init_io(smdk2416_iodesc, ARRAY_SIZE(smdk2416_iodesc)); 222 s3c24xx_init_io(smdk2416_iodesc, ARRAY_SIZE(smdk2416_iodesc));
222 s3c24xx_init_clocks(12000000); 223 s3c24xx_init_clocks(12000000);
223 s3c24xx_init_uarts(smdk2416_uartcfgs, ARRAY_SIZE(smdk2416_uartcfgs)); 224 s3c24xx_init_uarts(smdk2416_uartcfgs, ARRAY_SIZE(smdk2416_uartcfgs));
225 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
224} 226}
225 227
226static void __init smdk2416_machine_init(void) 228static void __init smdk2416_machine_init(void)
@@ -253,6 +255,6 @@ MACHINE_START(SMDK2416, "SMDK2416")
253 .init_irq = s3c2416_init_irq, 255 .init_irq = s3c2416_init_irq,
254 .map_io = smdk2416_map_io, 256 .map_io = smdk2416_map_io,
255 .init_machine = smdk2416_machine_init, 257 .init_machine = smdk2416_machine_init,
256 .init_time = s3c24xx_timer_init, 258 .init_time = samsung_timer_init,
257 .restart = s3c2416_restart, 259 .restart = s3c2416_restart,
258MACHINE_END 260MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-smdk2440.c b/arch/arm/mach-s3c24xx/mach-smdk2440.c
index 08cc38c8a4ae..de2e5d39a847 100644
--- a/arch/arm/mach-s3c24xx/mach-smdk2440.c
+++ b/arch/arm/mach-s3c24xx/mach-smdk2440.c
@@ -38,15 +38,13 @@
38#include <mach/fb.h> 38#include <mach/fb.h>
39#include <linux/platform_data/i2c-s3c2410.h> 39#include <linux/platform_data/i2c-s3c2410.h>
40 40
41#include <plat/s3c2410.h>
42#include <plat/s3c244x.h>
43#include <plat/clock.h> 41#include <plat/clock.h>
44#include <plat/devs.h> 42#include <plat/devs.h>
45#include <plat/cpu.h> 43#include <plat/cpu.h>
46 44#include <plat/samsung-time.h>
47#include <plat/common-smdk.h>
48 45
49#include "common.h" 46#include "common.h"
47#include "common-smdk.h"
50 48
51static struct map_desc smdk2440_iodesc[] __initdata = { 49static struct map_desc smdk2440_iodesc[] __initdata = {
52 /* ISA IO Space map (memory space selected by A24) */ 50 /* ISA IO Space map (memory space selected by A24) */
@@ -163,6 +161,7 @@ static void __init smdk2440_map_io(void)
163 s3c24xx_init_io(smdk2440_iodesc, ARRAY_SIZE(smdk2440_iodesc)); 161 s3c24xx_init_io(smdk2440_iodesc, ARRAY_SIZE(smdk2440_iodesc));
164 s3c24xx_init_clocks(16934400); 162 s3c24xx_init_clocks(16934400);
165 s3c24xx_init_uarts(smdk2440_uartcfgs, ARRAY_SIZE(smdk2440_uartcfgs)); 163 s3c24xx_init_uarts(smdk2440_uartcfgs, ARRAY_SIZE(smdk2440_uartcfgs));
164 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
166} 165}
167 166
168static void __init smdk2440_machine_init(void) 167static void __init smdk2440_machine_init(void)
@@ -178,9 +177,9 @@ MACHINE_START(S3C2440, "SMDK2440")
178 /* Maintainer: Ben Dooks <ben-linux@fluff.org> */ 177 /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
179 .atag_offset = 0x100, 178 .atag_offset = 0x100,
180 179
181 .init_irq = s3c24xx_init_irq, 180 .init_irq = s3c2440_init_irq,
182 .map_io = smdk2440_map_io, 181 .map_io = smdk2440_map_io,
183 .init_machine = smdk2440_machine_init, 182 .init_machine = smdk2440_machine_init,
184 .init_time = s3c24xx_timer_init, 183 .init_time = samsung_timer_init,
185 .restart = s3c244x_restart, 184 .restart = s3c244x_restart,
186MACHINE_END 185MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-smdk2443.c b/arch/arm/mach-s3c24xx/mach-smdk2443.c
index fc65d74d3c73..9435c3bef18a 100644
--- a/arch/arm/mach-s3c24xx/mach-smdk2443.c
+++ b/arch/arm/mach-s3c24xx/mach-smdk2443.c
@@ -38,13 +38,13 @@
38#include <mach/fb.h> 38#include <mach/fb.h>
39#include <linux/platform_data/i2c-s3c2410.h> 39#include <linux/platform_data/i2c-s3c2410.h>
40 40
41#include <plat/s3c2410.h>
42#include <plat/s3c2443.h>
43#include <plat/clock.h> 41#include <plat/clock.h>
44#include <plat/devs.h> 42#include <plat/devs.h>
45#include <plat/cpu.h> 43#include <plat/cpu.h>
44#include <plat/samsung-time.h>
46 45
47#include <plat/common-smdk.h> 46#include "common.h"
47#include "common-smdk.h"
48 48
49static struct map_desc smdk2443_iodesc[] __initdata = { 49static struct map_desc smdk2443_iodesc[] __initdata = {
50 /* ISA IO Space map (memory space selected by A24) */ 50 /* ISA IO Space map (memory space selected by A24) */
@@ -122,6 +122,7 @@ static void __init smdk2443_map_io(void)
122 s3c24xx_init_io(smdk2443_iodesc, ARRAY_SIZE(smdk2443_iodesc)); 122 s3c24xx_init_io(smdk2443_iodesc, ARRAY_SIZE(smdk2443_iodesc));
123 s3c24xx_init_clocks(12000000); 123 s3c24xx_init_clocks(12000000);
124 s3c24xx_init_uarts(smdk2443_uartcfgs, ARRAY_SIZE(smdk2443_uartcfgs)); 124 s3c24xx_init_uarts(smdk2443_uartcfgs, ARRAY_SIZE(smdk2443_uartcfgs));
125 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
125} 126}
126 127
127static void __init smdk2443_machine_init(void) 128static void __init smdk2443_machine_init(void)
@@ -143,6 +144,6 @@ MACHINE_START(SMDK2443, "SMDK2443")
143 .init_irq = s3c2443_init_irq, 144 .init_irq = s3c2443_init_irq,
144 .map_io = smdk2443_map_io, 145 .map_io = smdk2443_map_io,
145 .init_machine = smdk2443_machine_init, 146 .init_machine = smdk2443_machine_init,
146 .init_time = s3c24xx_timer_init, 147 .init_time = samsung_timer_init,
147 .restart = s3c2443_restart, 148 .restart = s3c2443_restart,
148MACHINE_END 149MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-tct_hammer.c b/arch/arm/mach-s3c24xx/mach-tct_hammer.c
index 24b3d79e7b2c..7fad8f055cab 100644
--- a/arch/arm/mach-s3c24xx/mach-tct_hammer.c
+++ b/arch/arm/mach-s3c24xx/mach-tct_hammer.c
@@ -53,6 +53,7 @@
53#include <linux/mtd/partitions.h> 53#include <linux/mtd/partitions.h>
54#include <linux/mtd/map.h> 54#include <linux/mtd/map.h>
55#include <linux/mtd/physmap.h> 55#include <linux/mtd/physmap.h>
56#include <plat/samsung-time.h>
56 57
57#include "common.h" 58#include "common.h"
58 59
@@ -136,6 +137,7 @@ static void __init tct_hammer_map_io(void)
136 s3c24xx_init_io(tct_hammer_iodesc, ARRAY_SIZE(tct_hammer_iodesc)); 137 s3c24xx_init_io(tct_hammer_iodesc, ARRAY_SIZE(tct_hammer_iodesc));
137 s3c24xx_init_clocks(0); 138 s3c24xx_init_clocks(0);
138 s3c24xx_init_uarts(tct_hammer_uartcfgs, ARRAY_SIZE(tct_hammer_uartcfgs)); 139 s3c24xx_init_uarts(tct_hammer_uartcfgs, ARRAY_SIZE(tct_hammer_uartcfgs));
140 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
139} 141}
140 142
141static void __init tct_hammer_init(void) 143static void __init tct_hammer_init(void)
@@ -147,8 +149,8 @@ static void __init tct_hammer_init(void)
147MACHINE_START(TCT_HAMMER, "TCT_HAMMER") 149MACHINE_START(TCT_HAMMER, "TCT_HAMMER")
148 .atag_offset = 0x100, 150 .atag_offset = 0x100,
149 .map_io = tct_hammer_map_io, 151 .map_io = tct_hammer_map_io,
150 .init_irq = s3c24xx_init_irq, 152 .init_irq = s3c2410_init_irq,
151 .init_machine = tct_hammer_init, 153 .init_machine = tct_hammer_init,
152 .init_time = s3c24xx_timer_init, 154 .init_time = samsung_timer_init,
153 .restart = s3c2410_restart, 155 .restart = s3c2410_restart,
154MACHINE_END 156MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-vr1000.c b/arch/arm/mach-s3c24xx/mach-vr1000.c
index ec42d1e4e465..42e7187fed60 100644
--- a/arch/arm/mach-s3c24xx/mach-vr1000.c
+++ b/arch/arm/mach-s3c24xx/mach-vr1000.c
@@ -45,6 +45,7 @@
45#include <plat/cpu.h> 45#include <plat/cpu.h>
46#include <plat/devs.h> 46#include <plat/devs.h>
47#include <plat/regs-serial.h> 47#include <plat/regs-serial.h>
48#include <plat/samsung-time.h>
48 49
49#include "bast.h" 50#include "bast.h"
50#include "common.h" 51#include "common.h"
@@ -332,6 +333,7 @@ static void __init vr1000_map_io(void)
332 s3c24xx_init_io(vr1000_iodesc, ARRAY_SIZE(vr1000_iodesc)); 333 s3c24xx_init_io(vr1000_iodesc, ARRAY_SIZE(vr1000_iodesc));
333 s3c24xx_init_clocks(0); 334 s3c24xx_init_clocks(0);
334 s3c24xx_init_uarts(vr1000_uartcfgs, ARRAY_SIZE(vr1000_uartcfgs)); 335 s3c24xx_init_uarts(vr1000_uartcfgs, ARRAY_SIZE(vr1000_uartcfgs));
336 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
335} 337}
336 338
337static void __init vr1000_init(void) 339static void __init vr1000_init(void)
@@ -353,7 +355,7 @@ MACHINE_START(VR1000, "Thorcom-VR1000")
353 .atag_offset = 0x100, 355 .atag_offset = 0x100,
354 .map_io = vr1000_map_io, 356 .map_io = vr1000_map_io,
355 .init_machine = vr1000_init, 357 .init_machine = vr1000_init,
356 .init_irq = s3c24xx_init_irq, 358 .init_irq = s3c2410_init_irq,
357 .init_time = s3c24xx_timer_init, 359 .init_time = samsung_timer_init,
358 .restart = s3c2410_restart, 360 .restart = s3c2410_restart,
359MACHINE_END 361MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/mach-vstms.c b/arch/arm/mach-s3c24xx/mach-vstms.c
index 3e2bfddc9df1..b66588428ec9 100644
--- a/arch/arm/mach-s3c24xx/mach-vstms.c
+++ b/arch/arm/mach-s3c24xx/mach-vstms.c
@@ -41,12 +41,12 @@
41#include <linux/platform_data/i2c-s3c2410.h> 41#include <linux/platform_data/i2c-s3c2410.h>
42#include <linux/platform_data/mtd-nand-s3c2410.h> 42#include <linux/platform_data/mtd-nand-s3c2410.h>
43 43
44#include <plat/s3c2410.h>
45#include <plat/s3c2412.h>
46#include <plat/clock.h> 44#include <plat/clock.h>
47#include <plat/devs.h> 45#include <plat/devs.h>
48#include <plat/cpu.h> 46#include <plat/cpu.h>
47#include <plat/samsung-time.h>
49 48
49#include "common.h"
50 50
51static struct map_desc vstms_iodesc[] __initdata = { 51static struct map_desc vstms_iodesc[] __initdata = {
52}; 52};
@@ -143,6 +143,7 @@ static void __init vstms_map_io(void)
143 s3c24xx_init_io(vstms_iodesc, ARRAY_SIZE(vstms_iodesc)); 143 s3c24xx_init_io(vstms_iodesc, ARRAY_SIZE(vstms_iodesc));
144 s3c24xx_init_clocks(12000000); 144 s3c24xx_init_clocks(12000000);
145 s3c24xx_init_uarts(vstms_uartcfgs, ARRAY_SIZE(vstms_uartcfgs)); 145 s3c24xx_init_uarts(vstms_uartcfgs, ARRAY_SIZE(vstms_uartcfgs));
146 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
146} 147}
147 148
148static void __init vstms_init(void) 149static void __init vstms_init(void)
@@ -157,9 +158,9 @@ MACHINE_START(VSTMS, "VSTMS")
157 .atag_offset = 0x100, 158 .atag_offset = 0x100,
158 159
159 .fixup = vstms_fixup, 160 .fixup = vstms_fixup,
160 .init_irq = s3c24xx_init_irq, 161 .init_irq = s3c2412_init_irq,
161 .init_machine = vstms_init, 162 .init_machine = vstms_init,
162 .map_io = vstms_map_io, 163 .map_io = vstms_map_io,
163 .init_time = s3c24xx_timer_init, 164 .init_time = samsung_timer_init,
164 .restart = s3c2412_restart, 165 .restart = s3c2412_restart,
165MACHINE_END 166MACHINE_END
diff --git a/arch/arm/mach-s3c24xx/pm-s3c2412.c b/arch/arm/mach-s3c24xx/pm-s3c2412.c
index 668a78a8b195..d75f95e487ee 100644
--- a/arch/arm/mach-s3c24xx/pm-s3c2412.c
+++ b/arch/arm/mach-s3c24xx/pm-s3c2412.c
@@ -29,7 +29,7 @@
29 29
30#include <plat/cpu.h> 30#include <plat/cpu.h>
31#include <plat/pm.h> 31#include <plat/pm.h>
32#include <plat/s3c2412.h> 32#include <plat/wakeup-mask.h>
33 33
34#include "regs-dsc.h" 34#include "regs-dsc.h"
35#include "s3c2412-power.h" 35#include "s3c2412-power.h"
@@ -52,8 +52,15 @@ static int s3c2412_cpu_suspend(unsigned long arg)
52 return 1; /* Aborting suspend */ 52 return 1; /* Aborting suspend */
53} 53}
54 54
55/* mapping of interrupts to parts of the wakeup mask */
56static struct samsung_wakeup_mask wake_irqs[] = {
57 { .irq = IRQ_RTC, .bit = S3C2412_PWRCFG_RTC_MASKIRQ, },
58};
59
55static void s3c2412_pm_prepare(void) 60static void s3c2412_pm_prepare(void)
56{ 61{
62 samsung_sync_wakemask(S3C2412_PWRCFG,
63 wake_irqs, ARRAY_SIZE(wake_irqs));
57} 64}
58 65
59static int s3c2412_pm_add(struct device *dev, struct subsys_interface *sif) 66static int s3c2412_pm_add(struct device *dev, struct subsys_interface *sif)
diff --git a/arch/arm/mach-s3c24xx/s3c2410.c b/arch/arm/mach-s3c24xx/s3c2410.c
index 9ebef95da721..d850ea5adac2 100644
--- a/arch/arm/mach-s3c24xx/s3c2410.c
+++ b/arch/arm/mach-s3c24xx/s3c2410.c
@@ -37,7 +37,6 @@
37#include <mach/regs-clock.h> 37#include <mach/regs-clock.h>
38#include <plat/regs-serial.h> 38#include <plat/regs-serial.h>
39 39
40#include <plat/s3c2410.h>
41#include <plat/cpu.h> 40#include <plat/cpu.h>
42#include <plat/devs.h> 41#include <plat/devs.h>
43#include <plat/clock.h> 42#include <plat/clock.h>
diff --git a/arch/arm/mach-s3c24xx/s3c2412.c b/arch/arm/mach-s3c24xx/s3c2412.c
index 0d592159a5c3..0f864d4c97de 100644
--- a/arch/arm/mach-s3c24xx/s3c2412.c
+++ b/arch/arm/mach-s3c24xx/s3c2412.c
@@ -44,7 +44,6 @@
44#include <plat/pm.h> 44#include <plat/pm.h>
45#include <plat/regs-serial.h> 45#include <plat/regs-serial.h>
46#include <plat/regs-spi.h> 46#include <plat/regs-spi.h>
47#include <plat/s3c2412.h>
48 47
49#include "common.h" 48#include "common.h"
50#include "regs-dsc.h" 49#include "regs-dsc.h"
diff --git a/arch/arm/mach-s3c24xx/s3c2416.c b/arch/arm/mach-s3c24xx/s3c2416.c
index e30476db0295..b9c5d382dafb 100644
--- a/arch/arm/mach-s3c24xx/s3c2416.c
+++ b/arch/arm/mach-s3c24xx/s3c2416.c
@@ -50,7 +50,6 @@
50#include <plat/gpio-core.h> 50#include <plat/gpio-core.h>
51#include <plat/gpio-cfg.h> 51#include <plat/gpio-cfg.h>
52#include <plat/gpio-cfg-helpers.h> 52#include <plat/gpio-cfg-helpers.h>
53#include <plat/s3c2416.h>
54#include <plat/devs.h> 53#include <plat/devs.h>
55#include <plat/cpu.h> 54#include <plat/cpu.h>
56#include <plat/sdhci.h> 55#include <plat/sdhci.h>
diff --git a/arch/arm/mach-s3c24xx/s3c2440.c b/arch/arm/mach-s3c24xx/s3c2440.c
index 559e394e8989..5f9d6569475d 100644
--- a/arch/arm/mach-s3c24xx/s3c2440.c
+++ b/arch/arm/mach-s3c24xx/s3c2440.c
@@ -33,7 +33,6 @@
33 33
34#include <plat/devs.h> 34#include <plat/devs.h>
35#include <plat/cpu.h> 35#include <plat/cpu.h>
36#include <plat/s3c244x.h>
37#include <plat/pm.h> 36#include <plat/pm.h>
38 37
39#include <plat/gpio-core.h> 38#include <plat/gpio-core.h>
diff --git a/arch/arm/mach-s3c24xx/s3c2442.c b/arch/arm/mach-s3c24xx/s3c2442.c
index f732826c2359..6819961f6b19 100644
--- a/arch/arm/mach-s3c24xx/s3c2442.c
+++ b/arch/arm/mach-s3c24xx/s3c2442.c
@@ -44,7 +44,6 @@
44 44
45#include <plat/clock.h> 45#include <plat/clock.h>
46#include <plat/cpu.h> 46#include <plat/cpu.h>
47#include <plat/s3c244x.h>
48#include <plat/pm.h> 47#include <plat/pm.h>
49 48
50#include <plat/gpio-core.h> 49#include <plat/gpio-core.h>
diff --git a/arch/arm/mach-s3c24xx/s3c2443.c b/arch/arm/mach-s3c24xx/s3c2443.c
index 165b6a6b3daa..8328cd65bf3d 100644
--- a/arch/arm/mach-s3c24xx/s3c2443.c
+++ b/arch/arm/mach-s3c24xx/s3c2443.c
@@ -36,7 +36,6 @@
36#include <plat/gpio-core.h> 36#include <plat/gpio-core.h>
37#include <plat/gpio-cfg.h> 37#include <plat/gpio-cfg.h>
38#include <plat/gpio-cfg-helpers.h> 38#include <plat/gpio-cfg-helpers.h>
39#include <plat/s3c2443.h>
40#include <plat/devs.h> 39#include <plat/devs.h>
41#include <plat/cpu.h> 40#include <plat/cpu.h>
42#include <plat/fb-core.h> 41#include <plat/fb-core.h>
diff --git a/arch/arm/mach-s3c24xx/s3c244x.c b/arch/arm/mach-s3c24xx/s3c244x.c
index ad2671baa910..2a35edb67354 100644
--- a/arch/arm/mach-s3c24xx/s3c244x.c
+++ b/arch/arm/mach-s3c24xx/s3c244x.c
@@ -37,8 +37,6 @@
37#include <plat/regs-serial.h> 37#include <plat/regs-serial.h>
38#include <mach/regs-gpio.h> 38#include <mach/regs-gpio.h>
39 39
40#include <plat/s3c2410.h>
41#include <plat/s3c244x.h>
42#include <plat/clock.h> 40#include <plat/clock.h>
43#include <plat/devs.h> 41#include <plat/devs.h>
44#include <plat/cpu.h> 42#include <plat/cpu.h>
diff --git a/arch/arm/mach-s3c64xx/Kconfig b/arch/arm/mach-s3c64xx/Kconfig
index 131c86284711..283cb77d4721 100644
--- a/arch/arm/mach-s3c64xx/Kconfig
+++ b/arch/arm/mach-s3c64xx/Kconfig
@@ -17,11 +17,13 @@ config PLAT_S3C64XX
17# Configuration options for the S3C6410 CPU 17# Configuration options for the S3C6410 CPU
18 18
19config CPU_S3C6400 19config CPU_S3C6400
20 select SAMSUNG_HRT
20 bool 21 bool
21 help 22 help
22 Enable S3C6400 CPU support 23 Enable S3C6400 CPU support
23 24
24config CPU_S3C6410 25config CPU_S3C6410
26 select SAMSUNG_HRT
25 bool 27 bool
26 help 28 help
27 Enable S3C6410 CPU support 29 Enable S3C6410 CPU support
diff --git a/arch/arm/mach-s3c64xx/mach-anw6410.c b/arch/arm/mach-s3c64xx/mach-anw6410.c
index 728eef3296b2..35e3f54574ef 100644
--- a/arch/arm/mach-s3c64xx/mach-anw6410.c
+++ b/arch/arm/mach-s3c64xx/mach-anw6410.c
@@ -49,6 +49,7 @@
49#include <plat/devs.h> 49#include <plat/devs.h>
50#include <plat/cpu.h> 50#include <plat/cpu.h>
51#include <mach/regs-gpio.h> 51#include <mach/regs-gpio.h>
52#include <plat/samsung-time.h>
52 53
53#include "common.h" 54#include "common.h"
54#include "regs-modem.h" 55#include "regs-modem.h"
@@ -208,6 +209,7 @@ static void __init anw6410_map_io(void)
208 s3c64xx_init_io(anw6410_iodesc, ARRAY_SIZE(anw6410_iodesc)); 209 s3c64xx_init_io(anw6410_iodesc, ARRAY_SIZE(anw6410_iodesc));
209 s3c24xx_init_clocks(12000000); 210 s3c24xx_init_clocks(12000000);
210 s3c24xx_init_uarts(anw6410_uartcfgs, ARRAY_SIZE(anw6410_uartcfgs)); 211 s3c24xx_init_uarts(anw6410_uartcfgs, ARRAY_SIZE(anw6410_uartcfgs));
212 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
211 213
212 anw6410_lcd_mode_set(); 214 anw6410_lcd_mode_set();
213} 215}
@@ -232,6 +234,6 @@ MACHINE_START(ANW6410, "A&W6410")
232 .map_io = anw6410_map_io, 234 .map_io = anw6410_map_io,
233 .init_machine = anw6410_machine_init, 235 .init_machine = anw6410_machine_init,
234 .init_late = s3c64xx_init_late, 236 .init_late = s3c64xx_init_late,
235 .init_time = s3c24xx_timer_init, 237 .init_time = samsung_timer_init,
236 .restart = s3c64xx_restart, 238 .restart = s3c64xx_restart,
237MACHINE_END 239MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-crag6410.c b/arch/arm/mach-s3c64xx/mach-crag6410.c
index 1acf02bace57..8ad88ace795a 100644
--- a/arch/arm/mach-s3c64xx/mach-crag6410.c
+++ b/arch/arm/mach-s3c64xx/mach-crag6410.c
@@ -64,6 +64,7 @@
64#include <plat/adc.h> 64#include <plat/adc.h>
65#include <linux/platform_data/i2c-s3c2410.h> 65#include <linux/platform_data/i2c-s3c2410.h>
66#include <plat/pm.h> 66#include <plat/pm.h>
67#include <plat/samsung-time.h>
67 68
68#include "common.h" 69#include "common.h"
69#include "crag6410.h" 70#include "crag6410.h"
@@ -744,6 +745,7 @@ static void __init crag6410_map_io(void)
744 s3c64xx_init_io(NULL, 0); 745 s3c64xx_init_io(NULL, 0);
745 s3c24xx_init_clocks(12000000); 746 s3c24xx_init_clocks(12000000);
746 s3c24xx_init_uarts(crag6410_uartcfgs, ARRAY_SIZE(crag6410_uartcfgs)); 747 s3c24xx_init_uarts(crag6410_uartcfgs, ARRAY_SIZE(crag6410_uartcfgs));
748 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
747 749
748 /* LCD type and Bypass set by bootloader */ 750 /* LCD type and Bypass set by bootloader */
749} 751}
@@ -868,6 +870,6 @@ MACHINE_START(WLF_CRAGG_6410, "Wolfson Cragganmore 6410")
868 .map_io = crag6410_map_io, 870 .map_io = crag6410_map_io,
869 .init_machine = crag6410_machine_init, 871 .init_machine = crag6410_machine_init,
870 .init_late = s3c64xx_init_late, 872 .init_late = s3c64xx_init_late,
871 .init_time = s3c24xx_timer_init, 873 .init_time = samsung_timer_init,
872 .restart = s3c64xx_restart, 874 .restart = s3c64xx_restart,
873MACHINE_END 875MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-hmt.c b/arch/arm/mach-s3c64xx/mach-hmt.c
index 7212eb9cfeb9..5b7f357d8c22 100644
--- a/arch/arm/mach-s3c64xx/mach-hmt.c
+++ b/arch/arm/mach-s3c64xx/mach-hmt.c
@@ -41,6 +41,7 @@
41#include <plat/clock.h> 41#include <plat/clock.h>
42#include <plat/devs.h> 42#include <plat/devs.h>
43#include <plat/cpu.h> 43#include <plat/cpu.h>
44#include <plat/samsung-time.h>
44 45
45#include "common.h" 46#include "common.h"
46 47
@@ -248,6 +249,7 @@ static void __init hmt_map_io(void)
248 s3c64xx_init_io(hmt_iodesc, ARRAY_SIZE(hmt_iodesc)); 249 s3c64xx_init_io(hmt_iodesc, ARRAY_SIZE(hmt_iodesc));
249 s3c24xx_init_clocks(12000000); 250 s3c24xx_init_clocks(12000000);
250 s3c24xx_init_uarts(hmt_uartcfgs, ARRAY_SIZE(hmt_uartcfgs)); 251 s3c24xx_init_uarts(hmt_uartcfgs, ARRAY_SIZE(hmt_uartcfgs));
252 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
251} 253}
252 254
253static void __init hmt_machine_init(void) 255static void __init hmt_machine_init(void)
@@ -275,6 +277,6 @@ MACHINE_START(HMT, "Airgoo-HMT")
275 .map_io = hmt_map_io, 277 .map_io = hmt_map_io,
276 .init_machine = hmt_machine_init, 278 .init_machine = hmt_machine_init,
277 .init_late = s3c64xx_init_late, 279 .init_late = s3c64xx_init_late,
278 .init_time = s3c24xx_timer_init, 280 .init_time = samsung_timer_init,
279 .restart = s3c64xx_restart, 281 .restart = s3c64xx_restart,
280MACHINE_END 282MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-mini6410.c b/arch/arm/mach-s3c64xx/mach-mini6410.c
index 4b41fcdaa7b6..fc043e3ecdf8 100644
--- a/arch/arm/mach-s3c64xx/mach-mini6410.c
+++ b/arch/arm/mach-s3c64xx/mach-mini6410.c
@@ -41,6 +41,7 @@
41 41
42#include <video/platform_lcd.h> 42#include <video/platform_lcd.h>
43#include <video/samsung_fimd.h> 43#include <video/samsung_fimd.h>
44#include <plat/samsung-time.h>
44 45
45#include "common.h" 46#include "common.h"
46#include "regs-modem.h" 47#include "regs-modem.h"
@@ -232,6 +233,7 @@ static void __init mini6410_map_io(void)
232 s3c64xx_init_io(NULL, 0); 233 s3c64xx_init_io(NULL, 0);
233 s3c24xx_init_clocks(12000000); 234 s3c24xx_init_clocks(12000000);
234 s3c24xx_init_uarts(mini6410_uartcfgs, ARRAY_SIZE(mini6410_uartcfgs)); 235 s3c24xx_init_uarts(mini6410_uartcfgs, ARRAY_SIZE(mini6410_uartcfgs));
236 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
235 237
236 /* set the LCD type */ 238 /* set the LCD type */
237 tmp = __raw_readl(S3C64XX_SPCON); 239 tmp = __raw_readl(S3C64XX_SPCON);
@@ -354,6 +356,6 @@ MACHINE_START(MINI6410, "MINI6410")
354 .map_io = mini6410_map_io, 356 .map_io = mini6410_map_io,
355 .init_machine = mini6410_machine_init, 357 .init_machine = mini6410_machine_init,
356 .init_late = s3c64xx_init_late, 358 .init_late = s3c64xx_init_late,
357 .init_time = s3c24xx_timer_init, 359 .init_time = samsung_timer_init,
358 .restart = s3c64xx_restart, 360 .restart = s3c64xx_restart,
359MACHINE_END 361MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-ncp.c b/arch/arm/mach-s3c64xx/mach-ncp.c
index 8d3cedd995ff..7e2c3908f1f8 100644
--- a/arch/arm/mach-s3c64xx/mach-ncp.c
+++ b/arch/arm/mach-s3c64xx/mach-ncp.c
@@ -43,6 +43,7 @@
43#include <plat/clock.h> 43#include <plat/clock.h>
44#include <plat/devs.h> 44#include <plat/devs.h>
45#include <plat/cpu.h> 45#include <plat/cpu.h>
46#include <plat/samsung-time.h>
46 47
47#include "common.h" 48#include "common.h"
48 49
@@ -87,6 +88,7 @@ static void __init ncp_map_io(void)
87 s3c64xx_init_io(ncp_iodesc, ARRAY_SIZE(ncp_iodesc)); 88 s3c64xx_init_io(ncp_iodesc, ARRAY_SIZE(ncp_iodesc));
88 s3c24xx_init_clocks(12000000); 89 s3c24xx_init_clocks(12000000);
89 s3c24xx_init_uarts(ncp_uartcfgs, ARRAY_SIZE(ncp_uartcfgs)); 90 s3c24xx_init_uarts(ncp_uartcfgs, ARRAY_SIZE(ncp_uartcfgs));
91 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
90} 92}
91 93
92static void __init ncp_machine_init(void) 94static void __init ncp_machine_init(void)
@@ -103,6 +105,6 @@ MACHINE_START(NCP, "NCP")
103 .map_io = ncp_map_io, 105 .map_io = ncp_map_io,
104 .init_machine = ncp_machine_init, 106 .init_machine = ncp_machine_init,
105 .init_late = s3c64xx_init_late, 107 .init_late = s3c64xx_init_late,
106 .init_time = s3c24xx_timer_init, 108 .init_time = samsung_timer_init,
107 .restart = s3c64xx_restart, 109 .restart = s3c64xx_restart,
108MACHINE_END 110MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-real6410.c b/arch/arm/mach-s3c64xx/mach-real6410.c
index fa12bd21ad82..8bed37b3d5ac 100644
--- a/arch/arm/mach-s3c64xx/mach-real6410.c
+++ b/arch/arm/mach-s3c64xx/mach-real6410.c
@@ -42,6 +42,7 @@
42 42
43#include <video/platform_lcd.h> 43#include <video/platform_lcd.h>
44#include <video/samsung_fimd.h> 44#include <video/samsung_fimd.h>
45#include <plat/samsung-time.h>
45 46
46#include "common.h" 47#include "common.h"
47#include "regs-modem.h" 48#include "regs-modem.h"
@@ -211,6 +212,7 @@ static void __init real6410_map_io(void)
211 s3c64xx_init_io(NULL, 0); 212 s3c64xx_init_io(NULL, 0);
212 s3c24xx_init_clocks(12000000); 213 s3c24xx_init_clocks(12000000);
213 s3c24xx_init_uarts(real6410_uartcfgs, ARRAY_SIZE(real6410_uartcfgs)); 214 s3c24xx_init_uarts(real6410_uartcfgs, ARRAY_SIZE(real6410_uartcfgs));
215 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
214 216
215 /* set the LCD type */ 217 /* set the LCD type */
216 tmp = __raw_readl(S3C64XX_SPCON); 218 tmp = __raw_readl(S3C64XX_SPCON);
@@ -333,6 +335,6 @@ MACHINE_START(REAL6410, "REAL6410")
333 .map_io = real6410_map_io, 335 .map_io = real6410_map_io,
334 .init_machine = real6410_machine_init, 336 .init_machine = real6410_machine_init,
335 .init_late = s3c64xx_init_late, 337 .init_late = s3c64xx_init_late,
336 .init_time = s3c24xx_timer_init, 338 .init_time = samsung_timer_init,
337 .restart = s3c64xx_restart, 339 .restart = s3c64xx_restart,
338MACHINE_END 340MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-smartq.c b/arch/arm/mach-s3c64xx/mach-smartq.c
index fc3e9b32e26f..58ac99041274 100644
--- a/arch/arm/mach-s3c64xx/mach-smartq.c
+++ b/arch/arm/mach-s3c64xx/mach-smartq.c
@@ -38,6 +38,7 @@
38#include <linux/platform_data/touchscreen-s3c2410.h> 38#include <linux/platform_data/touchscreen-s3c2410.h>
39 39
40#include <video/platform_lcd.h> 40#include <video/platform_lcd.h>
41#include <plat/samsung-time.h>
41 42
42#include "common.h" 43#include "common.h"
43#include "regs-modem.h" 44#include "regs-modem.h"
@@ -378,6 +379,7 @@ void __init smartq_map_io(void)
378 s3c64xx_init_io(smartq_iodesc, ARRAY_SIZE(smartq_iodesc)); 379 s3c64xx_init_io(smartq_iodesc, ARRAY_SIZE(smartq_iodesc));
379 s3c24xx_init_clocks(12000000); 380 s3c24xx_init_clocks(12000000);
380 s3c24xx_init_uarts(smartq_uartcfgs, ARRAY_SIZE(smartq_uartcfgs)); 381 s3c24xx_init_uarts(smartq_uartcfgs, ARRAY_SIZE(smartq_uartcfgs));
382 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
381 383
382 smartq_lcd_mode_set(); 384 smartq_lcd_mode_set();
383} 385}
diff --git a/arch/arm/mach-s3c64xx/mach-smartq5.c b/arch/arm/mach-s3c64xx/mach-smartq5.c
index ca2afcfce573..8aca5daf3d05 100644
--- a/arch/arm/mach-s3c64xx/mach-smartq5.c
+++ b/arch/arm/mach-s3c64xx/mach-smartq5.c
@@ -28,6 +28,7 @@
28#include <plat/devs.h> 28#include <plat/devs.h>
29#include <plat/fb.h> 29#include <plat/fb.h>
30#include <plat/gpio-cfg.h> 30#include <plat/gpio-cfg.h>
31#include <plat/samsung-time.h>
31 32
32#include "common.h" 33#include "common.h"
33#include "mach-smartq.h" 34#include "mach-smartq.h"
@@ -155,6 +156,6 @@ MACHINE_START(SMARTQ5, "SmartQ 5")
155 .map_io = smartq_map_io, 156 .map_io = smartq_map_io,
156 .init_machine = smartq5_machine_init, 157 .init_machine = smartq5_machine_init,
157 .init_late = s3c64xx_init_late, 158 .init_late = s3c64xx_init_late,
158 .init_time = s3c24xx_timer_init, 159 .init_time = samsung_timer_init,
159 .restart = s3c64xx_restart, 160 .restart = s3c64xx_restart,
160MACHINE_END 161MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-smartq7.c b/arch/arm/mach-s3c64xx/mach-smartq7.c
index 37bb0c632a5e..a052e107c0b4 100644
--- a/arch/arm/mach-s3c64xx/mach-smartq7.c
+++ b/arch/arm/mach-s3c64xx/mach-smartq7.c
@@ -28,6 +28,7 @@
28#include <plat/devs.h> 28#include <plat/devs.h>
29#include <plat/fb.h> 29#include <plat/fb.h>
30#include <plat/gpio-cfg.h> 30#include <plat/gpio-cfg.h>
31#include <plat/samsung-time.h>
31 32
32#include "common.h" 33#include "common.h"
33#include "mach-smartq.h" 34#include "mach-smartq.h"
@@ -171,6 +172,6 @@ MACHINE_START(SMARTQ7, "SmartQ 7")
171 .map_io = smartq_map_io, 172 .map_io = smartq_map_io,
172 .init_machine = smartq7_machine_init, 173 .init_machine = smartq7_machine_init,
173 .init_late = s3c64xx_init_late, 174 .init_late = s3c64xx_init_late,
174 .init_time = s3c24xx_timer_init, 175 .init_time = samsung_timer_init,
175 .restart = s3c64xx_restart, 176 .restart = s3c64xx_restart,
176MACHINE_END 177MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-smdk6400.c b/arch/arm/mach-s3c64xx/mach-smdk6400.c
index a392869c8342..d70c0843aea2 100644
--- a/arch/arm/mach-s3c64xx/mach-smdk6400.c
+++ b/arch/arm/mach-s3c64xx/mach-smdk6400.c
@@ -35,6 +35,7 @@
35#include <plat/devs.h> 35#include <plat/devs.h>
36#include <plat/cpu.h> 36#include <plat/cpu.h>
37#include <linux/platform_data/i2c-s3c2410.h> 37#include <linux/platform_data/i2c-s3c2410.h>
38#include <plat/samsung-time.h>
38 39
39#include "common.h" 40#include "common.h"
40 41
@@ -66,6 +67,7 @@ static void __init smdk6400_map_io(void)
66 s3c64xx_init_io(smdk6400_iodesc, ARRAY_SIZE(smdk6400_iodesc)); 67 s3c64xx_init_io(smdk6400_iodesc, ARRAY_SIZE(smdk6400_iodesc));
67 s3c24xx_init_clocks(12000000); 68 s3c24xx_init_clocks(12000000);
68 s3c24xx_init_uarts(smdk6400_uartcfgs, ARRAY_SIZE(smdk6400_uartcfgs)); 69 s3c24xx_init_uarts(smdk6400_uartcfgs, ARRAY_SIZE(smdk6400_uartcfgs));
70 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
69} 71}
70 72
71static struct platform_device *smdk6400_devices[] __initdata = { 73static struct platform_device *smdk6400_devices[] __initdata = {
@@ -92,6 +94,6 @@ MACHINE_START(SMDK6400, "SMDK6400")
92 .map_io = smdk6400_map_io, 94 .map_io = smdk6400_map_io,
93 .init_machine = smdk6400_machine_init, 95 .init_machine = smdk6400_machine_init,
94 .init_late = s3c64xx_init_late, 96 .init_late = s3c64xx_init_late,
95 .init_time = s3c24xx_timer_init, 97 .init_time = samsung_timer_init,
96 .restart = s3c64xx_restart, 98 .restart = s3c64xx_restart,
97MACHINE_END 99MACHINE_END
diff --git a/arch/arm/mach-s3c64xx/mach-smdk6410.c b/arch/arm/mach-s3c64xx/mach-smdk6410.c
index ba7544e2d04d..bd3295a19ad7 100644
--- a/arch/arm/mach-s3c64xx/mach-smdk6410.c
+++ b/arch/arm/mach-s3c64xx/mach-smdk6410.c
@@ -69,6 +69,7 @@
69#include <linux/platform_data/touchscreen-s3c2410.h> 69#include <linux/platform_data/touchscreen-s3c2410.h>
70#include <plat/keypad.h> 70#include <plat/keypad.h>
71#include <plat/backlight.h> 71#include <plat/backlight.h>
72#include <plat/samsung-time.h>
72 73
73#include "common.h" 74#include "common.h"
74#include "regs-modem.h" 75#include "regs-modem.h"
@@ -634,6 +635,7 @@ static void __init smdk6410_map_io(void)
634 s3c64xx_init_io(smdk6410_iodesc, ARRAY_SIZE(smdk6410_iodesc)); 635 s3c64xx_init_io(smdk6410_iodesc, ARRAY_SIZE(smdk6410_iodesc));
635 s3c24xx_init_clocks(12000000); 636 s3c24xx_init_clocks(12000000);
636 s3c24xx_init_uarts(smdk6410_uartcfgs, ARRAY_SIZE(smdk6410_uartcfgs)); 637 s3c24xx_init_uarts(smdk6410_uartcfgs, ARRAY_SIZE(smdk6410_uartcfgs));
638 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
637 639
638 /* set the LCD type */ 640 /* set the LCD type */
639 641
@@ -702,6 +704,6 @@ MACHINE_START(SMDK6410, "SMDK6410")
702 .map_io = smdk6410_map_io, 704 .map_io = smdk6410_map_io,
703 .init_machine = smdk6410_machine_init, 705 .init_machine = smdk6410_machine_init,
704 .init_late = s3c64xx_init_late, 706 .init_late = s3c64xx_init_late,
705 .init_time = s3c24xx_timer_init, 707 .init_time = samsung_timer_init,
706 .restart = s3c64xx_restart, 708 .restart = s3c64xx_restart,
707MACHINE_END 709MACHINE_END
diff --git a/arch/arm/mach-s5p64x0/Kconfig b/arch/arm/mach-s5p64x0/Kconfig
index e8742cb7ddd9..5a707bdb9ea0 100644
--- a/arch/arm/mach-s5p64x0/Kconfig
+++ b/arch/arm/mach-s5p64x0/Kconfig
@@ -9,16 +9,16 @@ if ARCH_S5P64X0
9 9
10config CPU_S5P6440 10config CPU_S5P6440
11 bool 11 bool
12 select S5P_HRT
13 select S5P_SLEEP if PM 12 select S5P_SLEEP if PM
14 select SAMSUNG_DMADEV 13 select SAMSUNG_DMADEV
14 select SAMSUNG_HRT
15 select SAMSUNG_WAKEMASK if PM 15 select SAMSUNG_WAKEMASK if PM
16 help 16 help
17 Enable S5P6440 CPU support 17 Enable S5P6440 CPU support
18 18
19config CPU_S5P6450 19config CPU_S5P6450
20 bool 20 bool
21 select S5P_HRT 21 select SAMSUNG_HRT
22 select S5P_SLEEP if PM 22 select S5P_SLEEP if PM
23 select SAMSUNG_DMADEV 23 select SAMSUNG_DMADEV
24 select SAMSUNG_WAKEMASK if PM 24 select SAMSUNG_WAKEMASK if PM
diff --git a/arch/arm/mach-s5p64x0/mach-smdk6440.c b/arch/arm/mach-s5p64x0/mach-smdk6440.c
index e23723a5a214..73f71a698a34 100644
--- a/arch/arm/mach-s5p64x0/mach-smdk6440.c
+++ b/arch/arm/mach-s5p64x0/mach-smdk6440.c
@@ -48,7 +48,7 @@
48#include <plat/pll.h> 48#include <plat/pll.h>
49#include <plat/adc.h> 49#include <plat/adc.h>
50#include <linux/platform_data/touchscreen-s3c2410.h> 50#include <linux/platform_data/touchscreen-s3c2410.h>
51#include <plat/s5p-time.h> 51#include <plat/samsung-time.h>
52#include <plat/backlight.h> 52#include <plat/backlight.h>
53#include <plat/fb.h> 53#include <plat/fb.h>
54#include <plat/sdhci.h> 54#include <plat/sdhci.h>
@@ -229,7 +229,7 @@ static void __init smdk6440_map_io(void)
229 s5p64x0_init_io(NULL, 0); 229 s5p64x0_init_io(NULL, 0);
230 s3c24xx_init_clocks(12000000); 230 s3c24xx_init_clocks(12000000);
231 s3c24xx_init_uarts(smdk6440_uartcfgs, ARRAY_SIZE(smdk6440_uartcfgs)); 231 s3c24xx_init_uarts(smdk6440_uartcfgs, ARRAY_SIZE(smdk6440_uartcfgs));
232 s5p_set_timer_source(S5P_PWM3, S5P_PWM4); 232 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
233} 233}
234 234
235static void s5p6440_set_lcd_interface(void) 235static void s5p6440_set_lcd_interface(void)
@@ -273,6 +273,6 @@ MACHINE_START(SMDK6440, "SMDK6440")
273 .init_irq = s5p6440_init_irq, 273 .init_irq = s5p6440_init_irq,
274 .map_io = smdk6440_map_io, 274 .map_io = smdk6440_map_io,
275 .init_machine = smdk6440_machine_init, 275 .init_machine = smdk6440_machine_init,
276 .init_time = s5p_timer_init, 276 .init_time = samsung_timer_init,
277 .restart = s5p64x0_restart, 277 .restart = s5p64x0_restart,
278MACHINE_END 278MACHINE_END
diff --git a/arch/arm/mach-s5p64x0/mach-smdk6450.c b/arch/arm/mach-s5p64x0/mach-smdk6450.c
index ca10963a959e..18303e12019f 100644
--- a/arch/arm/mach-s5p64x0/mach-smdk6450.c
+++ b/arch/arm/mach-s5p64x0/mach-smdk6450.c
@@ -48,7 +48,7 @@
48#include <plat/pll.h> 48#include <plat/pll.h>
49#include <plat/adc.h> 49#include <plat/adc.h>
50#include <linux/platform_data/touchscreen-s3c2410.h> 50#include <linux/platform_data/touchscreen-s3c2410.h>
51#include <plat/s5p-time.h> 51#include <plat/samsung-time.h>
52#include <plat/backlight.h> 52#include <plat/backlight.h>
53#include <plat/fb.h> 53#include <plat/fb.h>
54#include <plat/sdhci.h> 54#include <plat/sdhci.h>
@@ -248,7 +248,7 @@ static void __init smdk6450_map_io(void)
248 s5p64x0_init_io(NULL, 0); 248 s5p64x0_init_io(NULL, 0);
249 s3c24xx_init_clocks(19200000); 249 s3c24xx_init_clocks(19200000);
250 s3c24xx_init_uarts(smdk6450_uartcfgs, ARRAY_SIZE(smdk6450_uartcfgs)); 250 s3c24xx_init_uarts(smdk6450_uartcfgs, ARRAY_SIZE(smdk6450_uartcfgs));
251 s5p_set_timer_source(S5P_PWM3, S5P_PWM4); 251 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
252} 252}
253 253
254static void s5p6450_set_lcd_interface(void) 254static void s5p6450_set_lcd_interface(void)
@@ -292,6 +292,6 @@ MACHINE_START(SMDK6450, "SMDK6450")
292 .init_irq = s5p6450_init_irq, 292 .init_irq = s5p6450_init_irq,
293 .map_io = smdk6450_map_io, 293 .map_io = smdk6450_map_io,
294 .init_machine = smdk6450_machine_init, 294 .init_machine = smdk6450_machine_init,
295 .init_time = s5p_timer_init, 295 .init_time = samsung_timer_init,
296 .restart = s5p64x0_restart, 296 .restart = s5p64x0_restart,
297MACHINE_END 297MACHINE_END
diff --git a/arch/arm/mach-s5pc100/Kconfig b/arch/arm/mach-s5pc100/Kconfig
index 15170be97a74..2f456a4533ba 100644
--- a/arch/arm/mach-s5pc100/Kconfig
+++ b/arch/arm/mach-s5pc100/Kconfig
@@ -11,6 +11,7 @@ config CPU_S5PC100
11 bool 11 bool
12 select S5P_EXT_INT 12 select S5P_EXT_INT
13 select SAMSUNG_DMADEV 13 select SAMSUNG_DMADEV
14 select SAMSUNG_HRT
14 help 15 help
15 Enable S5PC100 CPU support 16 Enable S5PC100 CPU support
16 17
diff --git a/arch/arm/mach-s5pc100/mach-smdkc100.c b/arch/arm/mach-s5pc100/mach-smdkc100.c
index 185a19583898..8c880f76f274 100644
--- a/arch/arm/mach-s5pc100/mach-smdkc100.c
+++ b/arch/arm/mach-s5pc100/mach-smdkc100.c
@@ -51,6 +51,7 @@
51#include <linux/platform_data/touchscreen-s3c2410.h> 51#include <linux/platform_data/touchscreen-s3c2410.h>
52#include <linux/platform_data/asoc-s3c.h> 52#include <linux/platform_data/asoc-s3c.h>
53#include <plat/backlight.h> 53#include <plat/backlight.h>
54#include <plat/samsung-time.h>
54 55
55#include "common.h" 56#include "common.h"
56 57
@@ -221,6 +222,7 @@ static void __init smdkc100_map_io(void)
221 s5pc100_init_io(NULL, 0); 222 s5pc100_init_io(NULL, 0);
222 s3c24xx_init_clocks(12000000); 223 s3c24xx_init_clocks(12000000);
223 s3c24xx_init_uarts(smdkc100_uartcfgs, ARRAY_SIZE(smdkc100_uartcfgs)); 224 s3c24xx_init_uarts(smdkc100_uartcfgs, ARRAY_SIZE(smdkc100_uartcfgs));
225 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
224} 226}
225 227
226static void __init smdkc100_machine_init(void) 228static void __init smdkc100_machine_init(void)
@@ -255,6 +257,6 @@ MACHINE_START(SMDKC100, "SMDKC100")
255 .init_irq = s5pc100_init_irq, 257 .init_irq = s5pc100_init_irq,
256 .map_io = smdkc100_map_io, 258 .map_io = smdkc100_map_io,
257 .init_machine = smdkc100_machine_init, 259 .init_machine = smdkc100_machine_init,
258 .init_time = s3c24xx_timer_init, 260 .init_time = samsung_timer_init,
259 .restart = s5pc100_restart, 261 .restart = s5pc100_restart,
260MACHINE_END 262MACHINE_END
diff --git a/arch/arm/mach-s5pv210/Kconfig b/arch/arm/mach-s5pv210/Kconfig
index 92ad72f0ef98..0963283a7c5d 100644
--- a/arch/arm/mach-s5pv210/Kconfig
+++ b/arch/arm/mach-s5pv210/Kconfig
@@ -12,10 +12,10 @@ if ARCH_S5PV210
12config CPU_S5PV210 12config CPU_S5PV210
13 bool 13 bool
14 select S5P_EXT_INT 14 select S5P_EXT_INT
15 select S5P_HRT
16 select S5P_PM if PM 15 select S5P_PM if PM
17 select S5P_SLEEP if PM 16 select S5P_SLEEP if PM
18 select SAMSUNG_DMADEV 17 select SAMSUNG_DMADEV
18 select SAMSUNG_HRT
19 help 19 help
20 Enable S5PV210 CPU support 20 Enable S5PV210 CPU support
21 21
diff --git a/arch/arm/mach-s5pv210/mach-aquila.c b/arch/arm/mach-s5pv210/mach-aquila.c
index 11900a8e88a3..ed2b85485b9d 100644
--- a/arch/arm/mach-s5pv210/mach-aquila.c
+++ b/arch/arm/mach-s5pv210/mach-aquila.c
@@ -38,7 +38,7 @@
38#include <plat/fb.h> 38#include <plat/fb.h>
39#include <plat/fimc-core.h> 39#include <plat/fimc-core.h>
40#include <plat/sdhci.h> 40#include <plat/sdhci.h>
41#include <plat/s5p-time.h> 41#include <plat/samsung-time.h>
42 42
43#include "common.h" 43#include "common.h"
44 44
@@ -651,7 +651,7 @@ static void __init aquila_map_io(void)
651 s5pv210_init_io(NULL, 0); 651 s5pv210_init_io(NULL, 0);
652 s3c24xx_init_clocks(24000000); 652 s3c24xx_init_clocks(24000000);
653 s3c24xx_init_uarts(aquila_uartcfgs, ARRAY_SIZE(aquila_uartcfgs)); 653 s3c24xx_init_uarts(aquila_uartcfgs, ARRAY_SIZE(aquila_uartcfgs));
654 s5p_set_timer_source(S5P_PWM3, S5P_PWM4); 654 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
655} 655}
656 656
657static void __init aquila_machine_init(void) 657static void __init aquila_machine_init(void)
@@ -686,6 +686,6 @@ MACHINE_START(AQUILA, "Aquila")
686 .init_irq = s5pv210_init_irq, 686 .init_irq = s5pv210_init_irq,
687 .map_io = aquila_map_io, 687 .map_io = aquila_map_io,
688 .init_machine = aquila_machine_init, 688 .init_machine = aquila_machine_init,
689 .init_time = s5p_timer_init, 689 .init_time = samsung_timer_init,
690 .restart = s5pv210_restart, 690 .restart = s5pv210_restart,
691MACHINE_END 691MACHINE_END
diff --git a/arch/arm/mach-s5pv210/mach-goni.c b/arch/arm/mach-s5pv210/mach-goni.c
index e373de44a8b6..30b24ad84f49 100644
--- a/arch/arm/mach-s5pv210/mach-goni.c
+++ b/arch/arm/mach-s5pv210/mach-goni.c
@@ -47,7 +47,7 @@
47#include <plat/keypad.h> 47#include <plat/keypad.h>
48#include <plat/sdhci.h> 48#include <plat/sdhci.h>
49#include <plat/clock.h> 49#include <plat/clock.h>
50#include <plat/s5p-time.h> 50#include <plat/samsung-time.h>
51#include <plat/mfc.h> 51#include <plat/mfc.h>
52#include <plat/camport.h> 52#include <plat/camport.h>
53 53
@@ -908,7 +908,7 @@ static void __init goni_map_io(void)
908 s5pv210_init_io(NULL, 0); 908 s5pv210_init_io(NULL, 0);
909 s3c24xx_init_clocks(clk_xusbxti.rate); 909 s3c24xx_init_clocks(clk_xusbxti.rate);
910 s3c24xx_init_uarts(goni_uartcfgs, ARRAY_SIZE(goni_uartcfgs)); 910 s3c24xx_init_uarts(goni_uartcfgs, ARRAY_SIZE(goni_uartcfgs));
911 s5p_set_timer_source(S5P_PWM3, S5P_PWM4); 911 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
912} 912}
913 913
914static void __init goni_reserve(void) 914static void __init goni_reserve(void)
@@ -973,7 +973,7 @@ MACHINE_START(GONI, "GONI")
973 .init_irq = s5pv210_init_irq, 973 .init_irq = s5pv210_init_irq,
974 .map_io = goni_map_io, 974 .map_io = goni_map_io,
975 .init_machine = goni_machine_init, 975 .init_machine = goni_machine_init,
976 .init_time = s5p_timer_init, 976 .init_time = samsung_timer_init,
977 .reserve = &goni_reserve, 977 .reserve = &goni_reserve,
978 .restart = s5pv210_restart, 978 .restart = s5pv210_restart,
979MACHINE_END 979MACHINE_END
diff --git a/arch/arm/mach-s5pv210/mach-smdkc110.c b/arch/arm/mach-s5pv210/mach-smdkc110.c
index 28bd0248a3e2..7c0ed07a78a3 100644
--- a/arch/arm/mach-s5pv210/mach-smdkc110.c
+++ b/arch/arm/mach-s5pv210/mach-smdkc110.c
@@ -29,7 +29,7 @@
29#include <linux/platform_data/ata-samsung_cf.h> 29#include <linux/platform_data/ata-samsung_cf.h>
30#include <linux/platform_data/i2c-s3c2410.h> 30#include <linux/platform_data/i2c-s3c2410.h>
31#include <plat/pm.h> 31#include <plat/pm.h>
32#include <plat/s5p-time.h> 32#include <plat/samsung-time.h>
33#include <plat/mfc.h> 33#include <plat/mfc.h>
34 34
35#include "common.h" 35#include "common.h"
@@ -120,7 +120,7 @@ static void __init smdkc110_map_io(void)
120 s5pv210_init_io(NULL, 0); 120 s5pv210_init_io(NULL, 0);
121 s3c24xx_init_clocks(24000000); 121 s3c24xx_init_clocks(24000000);
122 s3c24xx_init_uarts(smdkv210_uartcfgs, ARRAY_SIZE(smdkv210_uartcfgs)); 122 s3c24xx_init_uarts(smdkv210_uartcfgs, ARRAY_SIZE(smdkv210_uartcfgs));
123 s5p_set_timer_source(S5P_PWM3, S5P_PWM4); 123 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
124} 124}
125 125
126static void __init smdkc110_reserve(void) 126static void __init smdkc110_reserve(void)
@@ -153,7 +153,7 @@ MACHINE_START(SMDKC110, "SMDKC110")
153 .init_irq = s5pv210_init_irq, 153 .init_irq = s5pv210_init_irq,
154 .map_io = smdkc110_map_io, 154 .map_io = smdkc110_map_io,
155 .init_machine = smdkc110_machine_init, 155 .init_machine = smdkc110_machine_init,
156 .init_time = s5p_timer_init, 156 .init_time = samsung_timer_init,
157 .restart = s5pv210_restart, 157 .restart = s5pv210_restart,
158 .reserve = &smdkc110_reserve, 158 .reserve = &smdkc110_reserve,
159MACHINE_END 159MACHINE_END
diff --git a/arch/arm/mach-s5pv210/mach-smdkv210.c b/arch/arm/mach-s5pv210/mach-smdkv210.c
index 3c73f36869bb..d50b6f124465 100644
--- a/arch/arm/mach-s5pv210/mach-smdkv210.c
+++ b/arch/arm/mach-s5pv210/mach-smdkv210.c
@@ -44,7 +44,7 @@
44#include <plat/keypad.h> 44#include <plat/keypad.h>
45#include <plat/pm.h> 45#include <plat/pm.h>
46#include <plat/fb.h> 46#include <plat/fb.h>
47#include <plat/s5p-time.h> 47#include <plat/samsung-time.h>
48#include <plat/backlight.h> 48#include <plat/backlight.h>
49#include <plat/mfc.h> 49#include <plat/mfc.h>
50#include <plat/clock.h> 50#include <plat/clock.h>
@@ -285,7 +285,7 @@ static void __init smdkv210_map_io(void)
285 s5pv210_init_io(NULL, 0); 285 s5pv210_init_io(NULL, 0);
286 s3c24xx_init_clocks(clk_xusbxti.rate); 286 s3c24xx_init_clocks(clk_xusbxti.rate);
287 s3c24xx_init_uarts(smdkv210_uartcfgs, ARRAY_SIZE(smdkv210_uartcfgs)); 287 s3c24xx_init_uarts(smdkv210_uartcfgs, ARRAY_SIZE(smdkv210_uartcfgs));
288 s5p_set_timer_source(S5P_PWM2, S5P_PWM4); 288 samsung_set_timer_source(SAMSUNG_PWM2, SAMSUNG_PWM4);
289} 289}
290 290
291static void __init smdkv210_reserve(void) 291static void __init smdkv210_reserve(void)
@@ -329,7 +329,7 @@ MACHINE_START(SMDKV210, "SMDKV210")
329 .init_irq = s5pv210_init_irq, 329 .init_irq = s5pv210_init_irq,
330 .map_io = smdkv210_map_io, 330 .map_io = smdkv210_map_io,
331 .init_machine = smdkv210_machine_init, 331 .init_machine = smdkv210_machine_init,
332 .init_time = s5p_timer_init, 332 .init_time = samsung_timer_init,
333 .restart = s5pv210_restart, 333 .restart = s5pv210_restart,
334 .reserve = &smdkv210_reserve, 334 .reserve = &smdkv210_reserve,
335MACHINE_END 335MACHINE_END
diff --git a/arch/arm/mach-s5pv210/mach-torbreck.c b/arch/arm/mach-s5pv210/mach-torbreck.c
index 2d4c5531819c..579afe89842a 100644
--- a/arch/arm/mach-s5pv210/mach-torbreck.c
+++ b/arch/arm/mach-s5pv210/mach-torbreck.c
@@ -26,7 +26,7 @@
26#include <plat/devs.h> 26#include <plat/devs.h>
27#include <plat/cpu.h> 27#include <plat/cpu.h>
28#include <linux/platform_data/i2c-s3c2410.h> 28#include <linux/platform_data/i2c-s3c2410.h>
29#include <plat/s5p-time.h> 29#include <plat/samsung-time.h>
30 30
31#include "common.h" 31#include "common.h"
32 32
@@ -106,7 +106,7 @@ static void __init torbreck_map_io(void)
106 s5pv210_init_io(NULL, 0); 106 s5pv210_init_io(NULL, 0);
107 s3c24xx_init_clocks(24000000); 107 s3c24xx_init_clocks(24000000);
108 s3c24xx_init_uarts(torbreck_uartcfgs, ARRAY_SIZE(torbreck_uartcfgs)); 108 s3c24xx_init_uarts(torbreck_uartcfgs, ARRAY_SIZE(torbreck_uartcfgs));
109 s5p_set_timer_source(S5P_PWM3, S5P_PWM4); 109 samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
110} 110}
111 111
112static void __init torbreck_machine_init(void) 112static void __init torbreck_machine_init(void)
@@ -130,6 +130,6 @@ MACHINE_START(TORBRECK, "TORBRECK")
130 .init_irq = s5pv210_init_irq, 130 .init_irq = s5pv210_init_irq,
131 .map_io = torbreck_map_io, 131 .map_io = torbreck_map_io,
132 .init_machine = torbreck_machine_init, 132 .init_machine = torbreck_machine_init,
133 .init_time = s5p_timer_init, 133 .init_time = samsung_timer_init,
134 .restart = s5pv210_restart, 134 .restart = s5pv210_restart,
135MACHINE_END 135MACHINE_END
diff --git a/arch/arm/mach-shmobile/Kconfig b/arch/arm/mach-shmobile/Kconfig
index 9255546e7bf6..75d413c004b6 100644
--- a/arch/arm/mach-shmobile/Kconfig
+++ b/arch/arm/mach-shmobile/Kconfig
@@ -16,6 +16,7 @@ config ARCH_SH73A0
16 select CPU_V7 16 select CPU_V7
17 select I2C 17 select I2C
18 select SH_CLK_CPG 18 select SH_CLK_CPG
19 select RENESAS_INTC_IRQPIN
19 20
20config ARCH_R8A7740 21config ARCH_R8A7740
21 bool "R-Mobile A1 (R8A77400)" 22 bool "R-Mobile A1 (R8A77400)"
@@ -31,6 +32,7 @@ config ARCH_R8A7779
31 select SH_CLK_CPG 32 select SH_CLK_CPG
32 select USB_ARCH_HAS_EHCI 33 select USB_ARCH_HAS_EHCI
33 select USB_ARCH_HAS_OHCI 34 select USB_ARCH_HAS_OHCI
35 select RENESAS_INTC_IRQPIN
34 36
35config ARCH_EMEV2 37config ARCH_EMEV2
36 bool "Emma Mobile EV2" 38 bool "Emma Mobile EV2"
diff --git a/arch/arm/mach-shmobile/Makefile b/arch/arm/mach-shmobile/Makefile
index e1fac57514b9..b646ff4d742a 100644
--- a/arch/arm/mach-shmobile/Makefile
+++ b/arch/arm/mach-shmobile/Makefile
@@ -14,10 +14,9 @@ obj-$(CONFIG_ARCH_EMEV2) += setup-emev2.o clock-emev2.o
14 14
15# SMP objects 15# SMP objects
16smp-y := platsmp.o headsmp.o 16smp-y := platsmp.o headsmp.o
17smp-$(CONFIG_HOTPLUG_CPU) += hotplug.o 17smp-$(CONFIG_ARCH_SH73A0) += smp-sh73a0.o headsmp-scu.o
18smp-$(CONFIG_ARCH_SH73A0) += smp-sh73a0.o headsmp-sh73a0.o 18smp-$(CONFIG_ARCH_R8A7779) += smp-r8a7779.o headsmp-scu.o
19smp-$(CONFIG_ARCH_R8A7779) += smp-r8a7779.o 19smp-$(CONFIG_ARCH_EMEV2) += smp-emev2.o headsmp-scu.o
20smp-$(CONFIG_ARCH_EMEV2) += smp-emev2.o
21 20
22# IRQ objects 21# IRQ objects
23obj-$(CONFIG_ARCH_SH7372) += entry-intc.o 22obj-$(CONFIG_ARCH_SH7372) += entry-intc.o
diff --git a/arch/arm/mach-shmobile/board-kzm9d.c b/arch/arm/mach-shmobile/board-kzm9d.c
index c254782aa727..c016ccd92433 100644
--- a/arch/arm/mach-shmobile/board-kzm9d.c
+++ b/arch/arm/mach-shmobile/board-kzm9d.c
@@ -90,6 +90,5 @@ DT_MACHINE_START(KZM9D_DT, "kzm9d")
90 .init_irq = emev2_init_irq, 90 .init_irq = emev2_init_irq,
91 .init_machine = kzm9d_add_standard_devices, 91 .init_machine = kzm9d_add_standard_devices,
92 .init_late = shmobile_init_late, 92 .init_late = shmobile_init_late,
93 .init_time = shmobile_timer_init,
94 .dt_compat = kzm9d_boards_compat_dt, 93 .dt_compat = kzm9d_boards_compat_dt,
95MACHINE_END 94MACHINE_END
diff --git a/arch/arm/mach-shmobile/board-kzm9g.c b/arch/arm/mach-shmobile/board-kzm9g.c
index 7f3a6b7e7b7c..d34d12ae496b 100644
--- a/arch/arm/mach-shmobile/board-kzm9g.c
+++ b/arch/arm/mach-shmobile/board-kzm9g.c
@@ -81,7 +81,7 @@ static struct resource smsc9221_resources[] = {
81 .flags = IORESOURCE_MEM, 81 .flags = IORESOURCE_MEM,
82 }, 82 },
83 [1] = { 83 [1] = {
84 .start = intcs_evt2irq(0x260), /* IRQ3 */ 84 .start = irq_pin(3), /* IRQ3 */
85 .flags = IORESOURCE_IRQ, 85 .flags = IORESOURCE_IRQ,
86 }, 86 },
87}; 87};
@@ -115,7 +115,7 @@ static struct resource usb_resources[] = {
115 .flags = IORESOURCE_MEM, 115 .flags = IORESOURCE_MEM,
116 }, 116 },
117 [1] = { 117 [1] = {
118 .start = intcs_evt2irq(0x220), /* IRQ1 */ 118 .start = irq_pin(1), /* IRQ1 */
119 .flags = IORESOURCE_IRQ, 119 .flags = IORESOURCE_IRQ,
120 }, 120 },
121}; 121};
@@ -138,7 +138,7 @@ struct usbhs_private {
138 struct renesas_usbhs_platform_info info; 138 struct renesas_usbhs_platform_info info;
139}; 139};
140 140
141#define IRQ15 intcs_evt2irq(0x03e0) 141#define IRQ15 irq_pin(15)
142#define USB_PHY_MODE (1 << 4) 142#define USB_PHY_MODE (1 << 4)
143#define USB_PHY_INT_EN ((1 << 3) | (1 << 2)) 143#define USB_PHY_INT_EN ((1 << 3) | (1 << 2))
144#define USB_PHY_ON (1 << 1) 144#define USB_PHY_ON (1 << 1)
@@ -563,25 +563,25 @@ static struct i2c_board_info i2c0_devices[] = {
563 }, 563 },
564 { 564 {
565 I2C_BOARD_INFO("ak8975", 0x0c), 565 I2C_BOARD_INFO("ak8975", 0x0c),
566 .irq = intcs_evt2irq(0x3380), /* IRQ28 */ 566 .irq = irq_pin(28), /* IRQ28 */
567 }, 567 },
568 { 568 {
569 I2C_BOARD_INFO("adxl34x", 0x1d), 569 I2C_BOARD_INFO("adxl34x", 0x1d),
570 .irq = intcs_evt2irq(0x3340), /* IRQ26 */ 570 .irq = irq_pin(26), /* IRQ26 */
571 }, 571 },
572}; 572};
573 573
574static struct i2c_board_info i2c1_devices[] = { 574static struct i2c_board_info i2c1_devices[] = {
575 { 575 {
576 I2C_BOARD_INFO("st1232-ts", 0x55), 576 I2C_BOARD_INFO("st1232-ts", 0x55),
577 .irq = intcs_evt2irq(0x300), /* IRQ8 */ 577 .irq = irq_pin(8), /* IRQ8 */
578 }, 578 },
579}; 579};
580 580
581static struct i2c_board_info i2c3_devices[] = { 581static struct i2c_board_info i2c3_devices[] = {
582 { 582 {
583 I2C_BOARD_INFO("pcf8575", 0x20), 583 I2C_BOARD_INFO("pcf8575", 0x20),
584 .irq = intcs_evt2irq(0x3260), /* IRQ19 */ 584 .irq = irq_pin(19), /* IRQ19 */
585 .platform_data = &pcf8575_pdata, 585 .platform_data = &pcf8575_pdata,
586 }, 586 },
587}; 587};
diff --git a/arch/arm/mach-shmobile/clock-r8a7740.c b/arch/arm/mach-shmobile/clock-r8a7740.c
index 19ce885a3b43..1feb9a2286a8 100644
--- a/arch/arm/mach-shmobile/clock-r8a7740.c
+++ b/arch/arm/mach-shmobile/clock-r8a7740.c
@@ -593,29 +593,42 @@ static struct clk_lookup lookups[] = {
593 CLKDEV_DEV_ID("sh_mobile_ceu.1", &mstp_clks[MSTP128]), 593 CLKDEV_DEV_ID("sh_mobile_ceu.1", &mstp_clks[MSTP128]),
594 594
595 CLKDEV_DEV_ID("sh-sci.4", &mstp_clks[MSTP200]), 595 CLKDEV_DEV_ID("sh-sci.4", &mstp_clks[MSTP200]),
596 CLKDEV_DEV_ID("e6c80000.sci", &mstp_clks[MSTP200]),
596 CLKDEV_DEV_ID("sh-sci.3", &mstp_clks[MSTP201]), 597 CLKDEV_DEV_ID("sh-sci.3", &mstp_clks[MSTP201]),
598 CLKDEV_DEV_ID("e6c70000.sci", &mstp_clks[MSTP201]),
597 CLKDEV_DEV_ID("sh-sci.2", &mstp_clks[MSTP202]), 599 CLKDEV_DEV_ID("sh-sci.2", &mstp_clks[MSTP202]),
600 CLKDEV_DEV_ID("e6c60000.sci", &mstp_clks[MSTP202]),
598 CLKDEV_DEV_ID("sh-sci.1", &mstp_clks[MSTP203]), 601 CLKDEV_DEV_ID("sh-sci.1", &mstp_clks[MSTP203]),
602 CLKDEV_DEV_ID("e6c50000.sci", &mstp_clks[MSTP203]),
599 CLKDEV_DEV_ID("sh-sci.0", &mstp_clks[MSTP204]), 603 CLKDEV_DEV_ID("sh-sci.0", &mstp_clks[MSTP204]),
604 CLKDEV_DEV_ID("e6c40000.sci", &mstp_clks[MSTP204]),
600 CLKDEV_DEV_ID("sh-sci.8", &mstp_clks[MSTP206]), 605 CLKDEV_DEV_ID("sh-sci.8", &mstp_clks[MSTP206]),
606 CLKDEV_DEV_ID("e6c30000.sci", &mstp_clks[MSTP206]),
601 CLKDEV_DEV_ID("sh-sci.5", &mstp_clks[MSTP207]), 607 CLKDEV_DEV_ID("sh-sci.5", &mstp_clks[MSTP207]),
608 CLKDEV_DEV_ID("e6cb0000.sci", &mstp_clks[MSTP207]),
602 CLKDEV_DEV_ID("sh-dma-engine.3", &mstp_clks[MSTP214]), 609 CLKDEV_DEV_ID("sh-dma-engine.3", &mstp_clks[MSTP214]),
603 CLKDEV_DEV_ID("sh-dma-engine.2", &mstp_clks[MSTP216]), 610 CLKDEV_DEV_ID("sh-dma-engine.2", &mstp_clks[MSTP216]),
604 CLKDEV_DEV_ID("sh-dma-engine.1", &mstp_clks[MSTP217]), 611 CLKDEV_DEV_ID("sh-dma-engine.1", &mstp_clks[MSTP217]),
605 CLKDEV_DEV_ID("sh-dma-engine.0", &mstp_clks[MSTP218]), 612 CLKDEV_DEV_ID("sh-dma-engine.0", &mstp_clks[MSTP218]),
606 CLKDEV_DEV_ID("sh-sci.7", &mstp_clks[MSTP222]), 613 CLKDEV_DEV_ID("sh-sci.7", &mstp_clks[MSTP222]),
614 CLKDEV_DEV_ID("e6cd0000.sci", &mstp_clks[MSTP222]),
607 CLKDEV_DEV_ID("sh-sci.6", &mstp_clks[MSTP230]), 615 CLKDEV_DEV_ID("sh-sci.6", &mstp_clks[MSTP230]),
616 CLKDEV_DEV_ID("e6cc0000.sci", &mstp_clks[MSTP230]),
608 617
609 CLKDEV_DEV_ID("sh_cmt.10", &mstp_clks[MSTP329]), 618 CLKDEV_DEV_ID("sh_cmt.10", &mstp_clks[MSTP329]),
610 CLKDEV_DEV_ID("sh_fsi2", &mstp_clks[MSTP328]), 619 CLKDEV_DEV_ID("sh_fsi2", &mstp_clks[MSTP328]),
611 CLKDEV_DEV_ID("i2c-sh_mobile.1", &mstp_clks[MSTP323]), 620 CLKDEV_DEV_ID("i2c-sh_mobile.1", &mstp_clks[MSTP323]),
612 CLKDEV_DEV_ID("renesas_usbhs", &mstp_clks[MSTP320]), 621 CLKDEV_DEV_ID("renesas_usbhs", &mstp_clks[MSTP320]),
613 CLKDEV_DEV_ID("sh_mobile_sdhi.0", &mstp_clks[MSTP314]), 622 CLKDEV_DEV_ID("sh_mobile_sdhi.0", &mstp_clks[MSTP314]),
623 CLKDEV_DEV_ID("e6850000.sdhi", &mstp_clks[MSTP314]),
614 CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP313]), 624 CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP313]),
625 CLKDEV_DEV_ID("e6860000.sdhi", &mstp_clks[MSTP313]),
615 CLKDEV_DEV_ID("sh_mmcif", &mstp_clks[MSTP312]), 626 CLKDEV_DEV_ID("sh_mmcif", &mstp_clks[MSTP312]),
627 CLKDEV_DEV_ID("e6bd0000.mmcif", &mstp_clks[MSTP312]),
616 CLKDEV_DEV_ID("sh-eth", &mstp_clks[MSTP309]), 628 CLKDEV_DEV_ID("sh-eth", &mstp_clks[MSTP309]),
617 629
618 CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP415]), 630 CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP415]),
631 CLKDEV_DEV_ID("e6870000.sdhi", &mstp_clks[MSTP415]),
619 632
620 /* ICK */ 633 /* ICK */
621 CLKDEV_ICK_ID("host", "renesas_usbhs", &mstp_clks[MSTP416]), 634 CLKDEV_ICK_ID("host", "renesas_usbhs", &mstp_clks[MSTP416]),
diff --git a/arch/arm/mach-shmobile/clock-r8a7779.c b/arch/arm/mach-shmobile/clock-r8a7779.c
index 1db36537255c..d9edeaf66007 100644
--- a/arch/arm/mach-shmobile/clock-r8a7779.c
+++ b/arch/arm/mach-shmobile/clock-r8a7779.c
@@ -87,7 +87,8 @@ static struct clk div4_clks[DIV4_NR] = {
87}; 87};
88 88
89enum { MSTP323, MSTP322, MSTP321, MSTP320, 89enum { MSTP323, MSTP322, MSTP321, MSTP320,
90 MSTP101, MSTP100, 90 MSTP115,
91 MSTP103, MSTP101, MSTP100,
91 MSTP030, 92 MSTP030,
92 MSTP029, MSTP028, MSTP027, MSTP026, MSTP025, MSTP024, MSTP023, MSTP022, MSTP021, 93 MSTP029, MSTP028, MSTP027, MSTP026, MSTP025, MSTP024, MSTP023, MSTP022, MSTP021,
93 MSTP016, MSTP015, MSTP014, 94 MSTP016, MSTP015, MSTP014,
@@ -99,6 +100,8 @@ static struct clk mstp_clks[MSTP_NR] = {
99 [MSTP322] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR3, 22, 0), /* SDHI1 */ 100 [MSTP322] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR3, 22, 0), /* SDHI1 */
100 [MSTP321] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR3, 21, 0), /* SDHI2 */ 101 [MSTP321] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR3, 21, 0), /* SDHI2 */
101 [MSTP320] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR3, 20, 0), /* SDHI3 */ 102 [MSTP320] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR3, 20, 0), /* SDHI3 */
103 [MSTP115] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR1, 15, 0), /* SATA */
104 [MSTP103] = SH_CLK_MSTP32(&div4_clks[DIV4_S], MSTPCR1, 3, 0), /* DU */
102 [MSTP101] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR1, 1, 0), /* USB2 */ 105 [MSTP101] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR1, 1, 0), /* USB2 */
103 [MSTP100] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR1, 0, 0), /* USB0/1 */ 106 [MSTP100] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR1, 0, 0), /* USB0/1 */
104 [MSTP030] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR0, 30, 0), /* I2C0 */ 107 [MSTP030] = SH_CLK_MSTP32(&div4_clks[DIV4_P], MSTPCR0, 30, 0), /* I2C0 */
@@ -156,6 +159,8 @@ static struct clk_lookup lookups[] = {
156 CLKDEV_CON_ID("peripheral_clk", &div4_clks[DIV4_P]), 159 CLKDEV_CON_ID("peripheral_clk", &div4_clks[DIV4_P]),
157 160
158 /* MSTP32 clocks */ 161 /* MSTP32 clocks */
162 CLKDEV_DEV_ID("sata_rcar", &mstp_clks[MSTP115]), /* SATA */
163 CLKDEV_DEV_ID("fc600000.sata", &mstp_clks[MSTP115]), /* SATA w/DT */
159 CLKDEV_DEV_ID("ehci-platform.1", &mstp_clks[MSTP101]), /* USB EHCI port2 */ 164 CLKDEV_DEV_ID("ehci-platform.1", &mstp_clks[MSTP101]), /* USB EHCI port2 */
160 CLKDEV_DEV_ID("ohci-platform.1", &mstp_clks[MSTP101]), /* USB OHCI port2 */ 165 CLKDEV_DEV_ID("ohci-platform.1", &mstp_clks[MSTP101]), /* USB OHCI port2 */
161 CLKDEV_DEV_ID("ehci-platform.0", &mstp_clks[MSTP100]), /* USB EHCI port0/1 */ 166 CLKDEV_DEV_ID("ehci-platform.0", &mstp_clks[MSTP100]), /* USB EHCI port0/1 */
@@ -180,6 +185,7 @@ static struct clk_lookup lookups[] = {
180 CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP322]), /* SDHI1 */ 185 CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP322]), /* SDHI1 */
181 CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP321]), /* SDHI2 */ 186 CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP321]), /* SDHI2 */
182 CLKDEV_DEV_ID("sh_mobile_sdhi.3", &mstp_clks[MSTP320]), /* SDHI3 */ 187 CLKDEV_DEV_ID("sh_mobile_sdhi.3", &mstp_clks[MSTP320]), /* SDHI3 */
188 CLKDEV_DEV_ID("rcar-du.0", &mstp_clks[MSTP103]), /* DU */
183}; 189};
184 190
185void __init r8a7779_clock_init(void) 191void __init r8a7779_clock_init(void)
diff --git a/arch/arm/mach-shmobile/clock-sh73a0.c b/arch/arm/mach-shmobile/clock-sh73a0.c
index afa5423a0f93..71843dd39e16 100644
--- a/arch/arm/mach-shmobile/clock-sh73a0.c
+++ b/arch/arm/mach-shmobile/clock-sh73a0.c
@@ -265,12 +265,12 @@ enum { DIV4_I, DIV4_ZG, DIV4_M3, DIV4_B, DIV4_M1, DIV4_M2,
265 265
266static struct clk div4_clks[DIV4_NR] = { 266static struct clk div4_clks[DIV4_NR] = {
267 [DIV4_I] = DIV4(FRQCRA, 20, 0xdff, CLK_ENABLE_ON_INIT), 267 [DIV4_I] = DIV4(FRQCRA, 20, 0xdff, CLK_ENABLE_ON_INIT),
268 [DIV4_ZG] = DIV4(FRQCRA, 16, 0xd7f, CLK_ENABLE_ON_INIT), 268 [DIV4_ZG] = SH_CLK_DIV4(&pll0_clk, FRQCRA, 16, 0xd7f, CLK_ENABLE_ON_INIT),
269 [DIV4_M3] = DIV4(FRQCRA, 12, 0x1dff, CLK_ENABLE_ON_INIT), 269 [DIV4_M3] = DIV4(FRQCRA, 12, 0x1dff, CLK_ENABLE_ON_INIT),
270 [DIV4_B] = DIV4(FRQCRA, 8, 0xdff, CLK_ENABLE_ON_INIT), 270 [DIV4_B] = DIV4(FRQCRA, 8, 0xdff, CLK_ENABLE_ON_INIT),
271 [DIV4_M1] = DIV4(FRQCRA, 4, 0x1dff, 0), 271 [DIV4_M1] = DIV4(FRQCRA, 4, 0x1dff, 0),
272 [DIV4_M2] = DIV4(FRQCRA, 0, 0x1dff, 0), 272 [DIV4_M2] = DIV4(FRQCRA, 0, 0x1dff, 0),
273 [DIV4_Z] = DIV4(FRQCRB, 24, 0x97f, 0), 273 [DIV4_Z] = SH_CLK_DIV4(&pll0_clk, FRQCRB, 24, 0x97f, 0),
274 [DIV4_ZTR] = DIV4(FRQCRB, 20, 0xdff, 0), 274 [DIV4_ZTR] = DIV4(FRQCRB, 20, 0xdff, 0),
275 [DIV4_ZT] = DIV4(FRQCRB, 16, 0xdff, 0), 275 [DIV4_ZT] = DIV4(FRQCRB, 16, 0xdff, 0),
276 [DIV4_ZX] = DIV4(FRQCRB, 12, 0xdff, 0), 276 [DIV4_ZX] = DIV4(FRQCRB, 12, 0xdff, 0),
@@ -581,10 +581,13 @@ static struct clk_lookup lookups[] = {
581 CLKDEV_DEV_ID("e6822000.i2c", &mstp_clks[MSTP323]), /* I2C1 */ 581 CLKDEV_DEV_ID("e6822000.i2c", &mstp_clks[MSTP323]), /* I2C1 */
582 CLKDEV_DEV_ID("renesas_usbhs", &mstp_clks[MSTP322]), /* USB */ 582 CLKDEV_DEV_ID("renesas_usbhs", &mstp_clks[MSTP322]), /* USB */
583 CLKDEV_DEV_ID("sh_mobile_sdhi.0", &mstp_clks[MSTP314]), /* SDHI0 */ 583 CLKDEV_DEV_ID("sh_mobile_sdhi.0", &mstp_clks[MSTP314]), /* SDHI0 */
584 CLKDEV_DEV_ID("ee100000.sdhi", &mstp_clks[MSTP314]), /* SDHI0 */
584 CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP313]), /* SDHI1 */ 585 CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP313]), /* SDHI1 */
586 CLKDEV_DEV_ID("ee120000.sdhi", &mstp_clks[MSTP313]), /* SDHI1 */
585 CLKDEV_DEV_ID("sh_mmcif.0", &mstp_clks[MSTP312]), /* MMCIF0 */ 587 CLKDEV_DEV_ID("sh_mmcif.0", &mstp_clks[MSTP312]), /* MMCIF0 */
586 CLKDEV_DEV_ID("e6bd0000.mmcif", &mstp_clks[MSTP312]), /* MMCIF0 */ 588 CLKDEV_DEV_ID("e6bd0000.mmcif", &mstp_clks[MSTP312]), /* MMCIF0 */
587 CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP311]), /* SDHI2 */ 589 CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP311]), /* SDHI2 */
590 CLKDEV_DEV_ID("ee140000.sdhi", &mstp_clks[MSTP311]), /* SDHI2 */
588 CLKDEV_DEV_ID("leds-renesas-tpu.12", &mstp_clks[MSTP303]), /* TPU1 */ 591 CLKDEV_DEV_ID("leds-renesas-tpu.12", &mstp_clks[MSTP303]), /* TPU1 */
589 CLKDEV_DEV_ID("leds-renesas-tpu.21", &mstp_clks[MSTP302]), /* TPU2 */ 592 CLKDEV_DEV_ID("leds-renesas-tpu.21", &mstp_clks[MSTP302]), /* TPU2 */
590 CLKDEV_DEV_ID("leds-renesas-tpu.30", &mstp_clks[MSTP301]), /* TPU3 */ 593 CLKDEV_DEV_ID("leds-renesas-tpu.30", &mstp_clks[MSTP301]), /* TPU3 */
diff --git a/arch/arm/mach-shmobile/headsmp-sh73a0.S b/arch/arm/mach-shmobile/headsmp-scu.S
index bec4c0d9b713..7d113f898e7f 100644
--- a/arch/arm/mach-shmobile/headsmp-sh73a0.S
+++ b/arch/arm/mach-shmobile/headsmp-scu.S
@@ -1,5 +1,5 @@
1/* 1/*
2 * SMP support for SoC sh73a0 2 * Shared SCU setup for mach-shmobile
3 * 3 *
4 * Copyright (C) 2012 Bastian Hecht 4 * Copyright (C) 2012 Bastian Hecht
5 * 5 *
@@ -35,11 +35,12 @@
35 * the physical address as the MMU is still turned off. 35 * the physical address as the MMU is still turned off.
36 */ 36 */
37 .align 12 37 .align 12
38ENTRY(sh73a0_secondary_vector) 38ENTRY(shmobile_secondary_vector_scu)
39 mrc p15, 0, r0, c0, c0, 5 @ read MIPDR 39 mrc p15, 0, r0, c0, c0, 5 @ read MIPDR
40 and r0, r0, #3 @ mask out cpu ID 40 and r0, r0, #3 @ mask out cpu ID
41 lsl r0, r0, #3 @ we will shift by cpu_id * 8 bits 41 lsl r0, r0, #3 @ we will shift by cpu_id * 8 bits
42 mov r1, #0xf0000000 @ SCU base address 42 ldr r1, 2f
43 ldr r1, [r1] @ SCU base address
43 ldr r2, [r1, #8] @ SCU Power Status Register 44 ldr r2, [r1, #8] @ SCU Power Status Register
44 mov r3, #3 45 mov r3, #3
45 bic r2, r2, r3, lsl r0 @ Clear bits of our CPU (Run Mode) 46 bic r2, r2, r3, lsl r0 @ Clear bits of our CPU (Run Mode)
@@ -47,4 +48,10 @@ ENTRY(sh73a0_secondary_vector)
47 48
48 ldr pc, 1f 49 ldr pc, 1f
491: .long shmobile_invalidate_start - PAGE_OFFSET + PLAT_PHYS_OFFSET 501: .long shmobile_invalidate_start - PAGE_OFFSET + PLAT_PHYS_OFFSET
50ENDPROC(sh73a0_secondary_vector) 512: .long shmobile_scu_base - PAGE_OFFSET + PLAT_PHYS_OFFSET
52ENDPROC(shmobile_secondary_vector_scu)
53
54 .text
55 .globl shmobile_scu_base
56shmobile_scu_base:
57 .space 4
diff --git a/arch/arm/mach-shmobile/hotplug.c b/arch/arm/mach-shmobile/hotplug.c
deleted file mode 100644
index a1524e3367b0..000000000000
--- a/arch/arm/mach-shmobile/hotplug.c
+++ /dev/null
@@ -1,68 +0,0 @@
1/*
2 * SMP support for R-Mobile / SH-Mobile
3 *
4 * Copyright (C) 2010 Magnus Damm
5 *
6 * Based on realview, Copyright (C) 2002 ARM Ltd, All Rights Reserved
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11 */
12#include <linux/kernel.h>
13#include <linux/errno.h>
14#include <linux/smp.h>
15#include <linux/cpumask.h>
16#include <linux/delay.h>
17#include <linux/of.h>
18#include <mach/common.h>
19#include <mach/r8a7779.h>
20#include <mach/emev2.h>
21#include <asm/cacheflush.h>
22#include <asm/mach-types.h>
23
24static cpumask_t dead_cpus;
25
26void shmobile_cpu_die(unsigned int cpu)
27{
28 /* hardware shutdown code running on the CPU that is being offlined */
29 flush_cache_all();
30 dsb();
31
32 /* notify platform_cpu_kill() that hardware shutdown is finished */
33 cpumask_set_cpu(cpu, &dead_cpus);
34
35 /* wait for SoC code in platform_cpu_kill() to shut off CPU core
36 * power. CPU bring up starts from the reset vector.
37 */
38 while (1) {
39 /*
40 * here's the WFI
41 */
42 asm(".word 0xe320f003\n"
43 :
44 :
45 : "memory", "cc");
46 }
47}
48
49int shmobile_cpu_disable(unsigned int cpu)
50{
51 cpumask_clear_cpu(cpu, &dead_cpus);
52 /*
53 * we don't allow CPU 0 to be shutdown (it is still too special
54 * e.g. clock tick interrupts)
55 */
56 return cpu == 0 ? -EPERM : 0;
57}
58
59int shmobile_cpu_disable_any(unsigned int cpu)
60{
61 cpumask_clear_cpu(cpu, &dead_cpus);
62 return 0;
63}
64
65int shmobile_cpu_is_dead(unsigned int cpu)
66{
67 return cpumask_test_cpu(cpu, &dead_cpus);
68}
diff --git a/arch/arm/mach-shmobile/include/mach/common.h b/arch/arm/mach-shmobile/include/mach/common.h
index e48606d8a2be..03f73def2fc6 100644
--- a/arch/arm/mach-shmobile/include/mach/common.h
+++ b/arch/arm/mach-shmobile/include/mach/common.h
@@ -8,6 +8,7 @@ extern void shmobile_setup_delay(unsigned int max_cpu_core_mhz,
8struct twd_local_timer; 8struct twd_local_timer;
9extern void shmobile_setup_console(void); 9extern void shmobile_setup_console(void);
10extern void shmobile_secondary_vector(void); 10extern void shmobile_secondary_vector(void);
11extern void shmobile_secondary_vector_scu(void);
11struct clk; 12struct clk;
12extern int shmobile_clk_init(void); 13extern int shmobile_clk_init(void);
13extern void shmobile_handle_irq_intc(struct pt_regs *); 14extern void shmobile_handle_irq_intc(struct pt_regs *);
@@ -33,23 +34,23 @@ extern int sh7372_do_idle_sysc(unsigned long sleep_mode);
33extern struct clk sh7372_extal1_clk; 34extern struct clk sh7372_extal1_clk;
34extern struct clk sh7372_extal2_clk; 35extern struct clk sh7372_extal2_clk;
35 36
37extern void sh73a0_init_delay(void);
36extern void sh73a0_init_irq(void); 38extern void sh73a0_init_irq(void);
37extern void sh73a0_init_irq_dt(void); 39extern void sh73a0_init_irq_dt(void);
38extern void sh73a0_map_io(void); 40extern void sh73a0_map_io(void);
39extern void sh73a0_earlytimer_init(void); 41extern void sh73a0_earlytimer_init(void);
40extern void sh73a0_add_early_devices(void); 42extern void sh73a0_add_early_devices(void);
41extern void sh73a0_add_early_devices_dt(void);
42extern void sh73a0_add_standard_devices(void); 43extern void sh73a0_add_standard_devices(void);
43extern void sh73a0_add_standard_devices_dt(void); 44extern void sh73a0_add_standard_devices_dt(void);
44extern void sh73a0_clock_init(void); 45extern void sh73a0_clock_init(void);
45extern void sh73a0_pinmux_init(void); 46extern void sh73a0_pinmux_init(void);
46extern void sh73a0_pm_init(void); 47extern void sh73a0_pm_init(void);
47extern void sh73a0_secondary_vector(void);
48extern struct clk sh73a0_extal1_clk; 48extern struct clk sh73a0_extal1_clk;
49extern struct clk sh73a0_extal2_clk; 49extern struct clk sh73a0_extal2_clk;
50extern struct clk sh73a0_extcki_clk; 50extern struct clk sh73a0_extcki_clk;
51extern struct clk sh73a0_extalr_clk; 51extern struct clk sh73a0_extalr_clk;
52 52
53extern void r8a7740_meram_workaround(void);
53extern void r8a7740_init_irq(void); 54extern void r8a7740_init_irq(void);
54extern void r8a7740_map_io(void); 55extern void r8a7740_map_io(void);
55extern void r8a7740_add_early_devices(void); 56extern void r8a7740_add_early_devices(void);
@@ -58,16 +59,18 @@ extern void r8a7740_clock_init(u8 md_ck);
58extern void r8a7740_pinmux_init(void); 59extern void r8a7740_pinmux_init(void);
59extern void r8a7740_pm_init(void); 60extern void r8a7740_pm_init(void);
60 61
62extern void r8a7779_init_delay(void);
61extern void r8a7779_init_irq(void); 63extern void r8a7779_init_irq(void);
64extern void r8a7779_init_irq_extpin(int irlm);
65extern void r8a7779_init_irq_dt(void);
62extern void r8a7779_map_io(void); 66extern void r8a7779_map_io(void);
63extern void r8a7779_earlytimer_init(void); 67extern void r8a7779_earlytimer_init(void);
64extern void r8a7779_add_early_devices(void); 68extern void r8a7779_add_early_devices(void);
65extern void r8a7779_add_standard_devices(void); 69extern void r8a7779_add_standard_devices(void);
70extern void r8a7779_add_standard_devices_dt(void);
66extern void r8a7779_clock_init(void); 71extern void r8a7779_clock_init(void);
67extern void r8a7779_pinmux_init(void); 72extern void r8a7779_pinmux_init(void);
68extern void r8a7779_pm_init(void); 73extern void r8a7779_pm_init(void);
69extern void r8a7740_meram_workaround(void);
70
71extern void r8a7779_register_twd(void); 74extern void r8a7779_register_twd(void);
72 75
73#ifdef CONFIG_SUSPEND 76#ifdef CONFIG_SUSPEND
@@ -82,16 +85,7 @@ int shmobile_cpuidle_init(void);
82static inline int shmobile_cpuidle_init(void) { return 0; } 85static inline int shmobile_cpuidle_init(void) { return 0; }
83#endif 86#endif
84 87
85extern void shmobile_cpu_die(unsigned int cpu); 88extern void __iomem *shmobile_scu_base;
86extern int shmobile_cpu_disable(unsigned int cpu);
87extern int shmobile_cpu_disable_any(unsigned int cpu);
88
89#ifdef CONFIG_HOTPLUG_CPU
90extern int shmobile_cpu_is_dead(unsigned int cpu);
91#else
92static inline int shmobile_cpu_is_dead(unsigned int cpu) { return 1; }
93#endif
94
95extern void shmobile_smp_init_cpus(unsigned int ncores); 89extern void shmobile_smp_init_cpus(unsigned int ncores);
96 90
97static inline void __init shmobile_init_late(void) 91static inline void __init shmobile_init_late(void)
diff --git a/arch/arm/mach-shmobile/include/mach/irqs.h b/arch/arm/mach-shmobile/include/mach/irqs.h
index 06a5da3c3050..b2074e2acb15 100644
--- a/arch/arm/mach-shmobile/include/mach/irqs.h
+++ b/arch/arm/mach-shmobile/include/mach/irqs.h
@@ -5,10 +5,15 @@
5 5
6/* GIC */ 6/* GIC */
7#define gic_spi(nr) ((nr) + 32) 7#define gic_spi(nr) ((nr) + 32)
8#define gic_iid(nr) (nr) /* ICCIAR / interrupt ID */
8 9
9/* INTCS */ 10/* INTCS */
10#define INTCS_VECT_BASE 0x3400 11#define INTCS_VECT_BASE 0x3400
11#define INTCS_VECT(n, vect) INTC_VECT((n), INTCS_VECT_BASE + (vect)) 12#define INTCS_VECT(n, vect) INTC_VECT((n), INTCS_VECT_BASE + (vect))
12#define intcs_evt2irq(evt) evt2irq(INTCS_VECT_BASE + (evt)) 13#define intcs_evt2irq(evt) evt2irq(INTCS_VECT_BASE + (evt))
13 14
15/* External IRQ pins */
16#define IRQPIN_BASE 2000
17#define irq_pin(nr) ((nr) + IRQPIN_BASE)
18
14#endif /* __ASM_MACH_IRQS_H */ 19#endif /* __ASM_MACH_IRQS_H */
diff --git a/arch/arm/mach-shmobile/intc-r8a7779.c b/arch/arm/mach-shmobile/intc-r8a7779.c
index 8807c27f71f9..b86dc8908724 100644
--- a/arch/arm/mach-shmobile/intc-r8a7779.c
+++ b/arch/arm/mach-shmobile/intc-r8a7779.c
@@ -19,12 +19,16 @@
19 */ 19 */
20#include <linux/kernel.h> 20#include <linux/kernel.h>
21#include <linux/init.h> 21#include <linux/init.h>
22#include <linux/platform_device.h>
22#include <linux/interrupt.h> 23#include <linux/interrupt.h>
23#include <linux/irq.h> 24#include <linux/irq.h>
24#include <linux/io.h> 25#include <linux/io.h>
25#include <linux/irqchip/arm-gic.h> 26#include <linux/irqchip/arm-gic.h>
27#include <linux/platform_data/irq-renesas-intc-irqpin.h>
28#include <linux/irqchip.h>
26#include <mach/common.h> 29#include <mach/common.h>
27#include <mach/intc.h> 30#include <mach/intc.h>
31#include <mach/irqs.h>
28#include <mach/r8a7779.h> 32#include <mach/r8a7779.h>
29#include <asm/mach-types.h> 33#include <asm/mach-types.h>
30#include <asm/mach/arch.h> 34#include <asm/mach/arch.h>
@@ -38,18 +42,61 @@
38#define INT2NTSR0 IOMEM(0xfe700060) 42#define INT2NTSR0 IOMEM(0xfe700060)
39#define INT2NTSR1 IOMEM(0xfe700064) 43#define INT2NTSR1 IOMEM(0xfe700064)
40 44
45static struct renesas_intc_irqpin_config irqpin0_platform_data = {
46 .irq_base = irq_pin(0), /* IRQ0 -> IRQ3 */
47 .sense_bitfield_width = 2,
48};
49
50static struct resource irqpin0_resources[] = {
51 DEFINE_RES_MEM(0xfe78001c, 4), /* ICR1 */
52 DEFINE_RES_MEM(0xfe780010, 4), /* INTPRI */
53 DEFINE_RES_MEM(0xfe780024, 4), /* INTREQ */
54 DEFINE_RES_MEM(0xfe780044, 4), /* INTMSK0 */
55 DEFINE_RES_MEM(0xfe780064, 4), /* INTMSKCLR0 */
56 DEFINE_RES_IRQ(gic_spi(27)), /* IRQ0 */
57 DEFINE_RES_IRQ(gic_spi(28)), /* IRQ1 */
58 DEFINE_RES_IRQ(gic_spi(29)), /* IRQ2 */
59 DEFINE_RES_IRQ(gic_spi(30)), /* IRQ3 */
60};
61
62static struct platform_device irqpin0_device = {
63 .name = "renesas_intc_irqpin",
64 .id = 0,
65 .resource = irqpin0_resources,
66 .num_resources = ARRAY_SIZE(irqpin0_resources),
67 .dev = {
68 .platform_data = &irqpin0_platform_data,
69 },
70};
71
72void __init r8a7779_init_irq_extpin(int irlm)
73{
74 void __iomem *icr0 = ioremap_nocache(0xfe780000, PAGE_SIZE);
75 unsigned long tmp;
76
77 if (icr0) {
78 tmp = ioread32(icr0);
79 if (irlm)
80 tmp |= 1 << 23; /* IRQ0 -> IRQ3 as individual pins */
81 else
82 tmp &= ~(1 << 23); /* IRL mode - not supported */
83 tmp |= (1 << 21); /* LVLMODE = 1 */
84 iowrite32(tmp, icr0);
85 iounmap(icr0);
86
87 if (irlm)
88 platform_device_register(&irqpin0_device);
89 } else
90 pr_warn("r8a7779: unable to setup external irq pin mode\n");
91}
92
41static int r8a7779_set_wake(struct irq_data *data, unsigned int on) 93static int r8a7779_set_wake(struct irq_data *data, unsigned int on)
42{ 94{
43 return 0; /* always allow wakeup */ 95 return 0; /* always allow wakeup */
44} 96}
45 97
46void __init r8a7779_init_irq(void) 98static void __init r8a7779_init_irq_common(void)
47{ 99{
48 void __iomem *gic_dist_base = IOMEM(0xf0001000);
49 void __iomem *gic_cpu_base = IOMEM(0xf0000100);
50
51 /* use GIC to handle interrupts */
52 gic_init(0, 29, gic_dist_base, gic_cpu_base);
53 gic_arch_extn.irq_set_wake = r8a7779_set_wake; 100 gic_arch_extn.irq_set_wake = r8a7779_set_wake;
54 101
55 /* route all interrupts to ARM */ 102 /* route all interrupts to ARM */
@@ -63,3 +110,22 @@ void __init r8a7779_init_irq(void)
63 __raw_writel(0xbffffffc, INT2SMSKCR3); 110 __raw_writel(0xbffffffc, INT2SMSKCR3);
64 __raw_writel(0x003fee3f, INT2SMSKCR4); 111 __raw_writel(0x003fee3f, INT2SMSKCR4);
65} 112}
113
114void __init r8a7779_init_irq(void)
115{
116 void __iomem *gic_dist_base = IOMEM(0xf0001000);
117 void __iomem *gic_cpu_base = IOMEM(0xf0000100);
118
119 /* use GIC to handle interrupts */
120 gic_init(0, 29, gic_dist_base, gic_cpu_base);
121
122 r8a7779_init_irq_common();
123}
124
125#ifdef CONFIG_OF
126void __init r8a7779_init_irq_dt(void)
127{
128 irqchip_init();
129 r8a7779_init_irq_common();
130}
131#endif
diff --git a/arch/arm/mach-shmobile/intc-sh73a0.c b/arch/arm/mach-shmobile/intc-sh73a0.c
index 91faba666d46..19a26f4579b3 100644
--- a/arch/arm/mach-shmobile/intc-sh73a0.c
+++ b/arch/arm/mach-shmobile/intc-sh73a0.c
@@ -260,108 +260,6 @@ static int sh73a0_set_wake(struct irq_data *data, unsigned int on)
260 return 0; /* always allow wakeup */ 260 return 0; /* always allow wakeup */
261} 261}
262 262
263#define RELOC_BASE 0x1200
264
265/* INTCA IRQ pins at INTCS + RELOC_BASE to make space for GIC+INTC handling */
266#define INTCS_VECT_RELOC(n, vect) INTCS_VECT((n), (vect) + RELOC_BASE)
267
268INTC_IRQ_PINS_32(intca_irq_pins, 0xe6900000,
269 INTCS_VECT_RELOC, "sh73a0-intca-irq-pins");
270
271static int to_gic_irq(struct irq_data *data)
272{
273 unsigned int vect = irq2evt(data->irq) - INTCS_VECT_BASE;
274
275 if (vect >= 0x3200)
276 vect -= 0x3000;
277 else
278 vect -= 0x0200;
279
280 return gic_spi((vect >> 5) + 1);
281}
282
283static int to_intca_reloc_irq(struct irq_data *data)
284{
285 return data->irq + (RELOC_BASE >> 5);
286}
287
288#define irq_cb(cb, irq) irq_get_chip(irq)->cb(irq_get_irq_data(irq))
289#define irq_cbp(cb, irq, p...) irq_get_chip(irq)->cb(irq_get_irq_data(irq), p)
290
291static void intca_gic_enable(struct irq_data *data)
292{
293 irq_cb(irq_unmask, to_intca_reloc_irq(data));
294 irq_cb(irq_unmask, to_gic_irq(data));
295}
296
297static void intca_gic_disable(struct irq_data *data)
298{
299 irq_cb(irq_mask, to_gic_irq(data));
300 irq_cb(irq_mask, to_intca_reloc_irq(data));
301}
302
303static void intca_gic_mask_ack(struct irq_data *data)
304{
305 irq_cb(irq_mask, to_gic_irq(data));
306 irq_cb(irq_mask_ack, to_intca_reloc_irq(data));
307}
308
309static void intca_gic_eoi(struct irq_data *data)
310{
311 irq_cb(irq_eoi, to_gic_irq(data));
312}
313
314static int intca_gic_set_type(struct irq_data *data, unsigned int type)
315{
316 return irq_cbp(irq_set_type, to_intca_reloc_irq(data), type);
317}
318
319#ifdef CONFIG_SMP
320static int intca_gic_set_affinity(struct irq_data *data,
321 const struct cpumask *cpumask,
322 bool force)
323{
324 return irq_cbp(irq_set_affinity, to_gic_irq(data), cpumask, force);
325}
326#endif
327
328struct irq_chip intca_gic_irq_chip = {
329 .name = "INTCA-GIC",
330 .irq_mask = intca_gic_disable,
331 .irq_unmask = intca_gic_enable,
332 .irq_mask_ack = intca_gic_mask_ack,
333 .irq_eoi = intca_gic_eoi,
334 .irq_enable = intca_gic_enable,
335 .irq_disable = intca_gic_disable,
336 .irq_shutdown = intca_gic_disable,
337 .irq_set_type = intca_gic_set_type,
338 .irq_set_wake = sh73a0_set_wake,
339#ifdef CONFIG_SMP
340 .irq_set_affinity = intca_gic_set_affinity,
341#endif
342};
343
344static int to_intc_vect(int irq)
345{
346 unsigned int irq_pin = irq - gic_spi(1);
347 unsigned int offs;
348
349 if (irq_pin < 16)
350 offs = 0x0200;
351 else
352 offs = 0x3000;
353
354 return offs + (irq_pin << 5);
355}
356
357static irqreturn_t sh73a0_irq_pin_demux(int irq, void *dev_id)
358{
359 generic_handle_irq(intcs_evt2irq(to_intc_vect(irq)));
360 return IRQ_HANDLED;
361}
362
363static struct irqaction sh73a0_irq_pin_cascade[32];
364
365#define PINTER0_PHYS 0xe69000a0 263#define PINTER0_PHYS 0xe69000a0
366#define PINTER1_PHYS 0xe69000a4 264#define PINTER1_PHYS 0xe69000a4
367#define PINTER0_VIRT IOMEM(0xe69000a0) 265#define PINTER0_VIRT IOMEM(0xe69000a0)
@@ -422,13 +320,11 @@ void __init sh73a0_init_irq(void)
422 void __iomem *gic_dist_base = IOMEM(0xf0001000); 320 void __iomem *gic_dist_base = IOMEM(0xf0001000);
423 void __iomem *gic_cpu_base = IOMEM(0xf0000100); 321 void __iomem *gic_cpu_base = IOMEM(0xf0000100);
424 void __iomem *intevtsa = ioremap_nocache(0xffd20100, PAGE_SIZE); 322 void __iomem *intevtsa = ioremap_nocache(0xffd20100, PAGE_SIZE);
425 int k, n;
426 323
427 gic_init(0, 29, gic_dist_base, gic_cpu_base); 324 gic_init(0, 29, gic_dist_base, gic_cpu_base);
428 gic_arch_extn.irq_set_wake = sh73a0_set_wake; 325 gic_arch_extn.irq_set_wake = sh73a0_set_wake;
429 326
430 register_intc_controller(&intcs_desc); 327 register_intc_controller(&intcs_desc);
431 register_intc_controller(&intca_irq_pins_desc);
432 register_intc_controller(&intc_pint0_desc); 328 register_intc_controller(&intc_pint0_desc);
433 register_intc_controller(&intc_pint1_desc); 329 register_intc_controller(&intc_pint1_desc);
434 330
@@ -438,19 +334,6 @@ void __init sh73a0_init_irq(void)
438 sh73a0_intcs_cascade.dev_id = intevtsa; 334 sh73a0_intcs_cascade.dev_id = intevtsa;
439 setup_irq(gic_spi(50), &sh73a0_intcs_cascade); 335 setup_irq(gic_spi(50), &sh73a0_intcs_cascade);
440 336
441 /* IRQ pins require special handling through INTCA and GIC */
442 for (k = 0; k < 32; k++) {
443 sh73a0_irq_pin_cascade[k].name = "INTCA-GIC cascade";
444 sh73a0_irq_pin_cascade[k].handler = sh73a0_irq_pin_demux;
445 setup_irq(gic_spi(1 + k), &sh73a0_irq_pin_cascade[k]);
446
447 n = intcs_evt2irq(to_intc_vect(gic_spi(1 + k)));
448 WARN_ON(irq_alloc_desc_at(n, numa_node_id()) != n);
449 irq_set_chip_and_handler_name(n, &intca_gic_irq_chip,
450 handle_level_irq, "level");
451 set_irq_flags(n, IRQF_VALID); /* yuck */
452 }
453
454 /* PINT pins are sanely tied to the GIC as SPI */ 337 /* PINT pins are sanely tied to the GIC as SPI */
455 sh73a0_pint0_cascade.name = "PINT0 cascade"; 338 sh73a0_pint0_cascade.name = "PINT0 cascade";
456 sh73a0_pint0_cascade.handler = sh73a0_pint0_demux; 339 sh73a0_pint0_cascade.handler = sh73a0_pint0_demux;
@@ -460,11 +343,3 @@ void __init sh73a0_init_irq(void)
460 sh73a0_pint1_cascade.handler = sh73a0_pint1_demux; 343 sh73a0_pint1_cascade.handler = sh73a0_pint1_demux;
461 setup_irq(gic_spi(34), &sh73a0_pint1_cascade); 344 setup_irq(gic_spi(34), &sh73a0_pint1_cascade);
462} 345}
463
464#ifdef CONFIG_OF
465void __init sh73a0_init_irq_dt(void)
466{
467 irqchip_init();
468 gic_arch_extn.irq_set_wake = sh73a0_set_wake;
469}
470#endif
diff --git a/arch/arm/mach-shmobile/setup-emev2.c b/arch/arm/mach-shmobile/setup-emev2.c
index 47662a581c0a..899a86c31ec9 100644
--- a/arch/arm/mach-shmobile/setup-emev2.c
+++ b/arch/arm/mach-shmobile/setup-emev2.c
@@ -404,7 +404,7 @@ void __init emev2_add_standard_devices(void)
404 ARRAY_SIZE(emev2_late_devices)); 404 ARRAY_SIZE(emev2_late_devices));
405} 405}
406 406
407void __init emev2_init_delay(void) 407static void __init emev2_init_delay(void)
408{ 408{
409 shmobile_setup_delay(533, 1, 3); /* Cortex-A9 @ 533MHz */ 409 shmobile_setup_delay(533, 1, 3); /* Cortex-A9 @ 533MHz */
410} 410}
@@ -439,7 +439,7 @@ static const struct of_dev_auxdata emev2_auxdata_lookup[] __initconst = {
439 { } 439 { }
440}; 440};
441 441
442void __init emev2_add_standard_devices_dt(void) 442static void __init emev2_add_standard_devices_dt(void)
443{ 443{
444 of_platform_populate(NULL, of_default_bus_match_table, 444 of_platform_populate(NULL, of_default_bus_match_table,
445 emev2_auxdata_lookup, NULL); 445 emev2_auxdata_lookup, NULL);
@@ -456,7 +456,6 @@ DT_MACHINE_START(EMEV2_DT, "Generic Emma Mobile EV2 (Flattened Device Tree)")
456 .nr_irqs = NR_IRQS_LEGACY, 456 .nr_irqs = NR_IRQS_LEGACY,
457 .init_irq = irqchip_init, 457 .init_irq = irqchip_init,
458 .init_machine = emev2_add_standard_devices_dt, 458 .init_machine = emev2_add_standard_devices_dt,
459 .init_time = shmobile_timer_init,
460 .dt_compat = emev2_boards_compat_dt, 459 .dt_compat = emev2_boards_compat_dt,
461MACHINE_END 460MACHINE_END
462 461
diff --git a/arch/arm/mach-shmobile/setup-r8a7740.c b/arch/arm/mach-shmobile/setup-r8a7740.c
index 8b85d4d8fab6..104b474a2ccf 100644
--- a/arch/arm/mach-shmobile/setup-r8a7740.c
+++ b/arch/arm/mach-shmobile/setup-r8a7740.c
@@ -906,7 +906,6 @@ DT_MACHINE_START(R8A7740_DT, "Generic R8A7740 (Flattened Device Tree)")
906 .init_irq = r8a7740_init_irq, 906 .init_irq = r8a7740_init_irq,
907 .handle_irq = shmobile_handle_irq_intc, 907 .handle_irq = shmobile_handle_irq_intc,
908 .init_machine = r8a7740_add_standard_devices_dt, 908 .init_machine = r8a7740_add_standard_devices_dt,
909 .init_time = shmobile_timer_init,
910 .dt_compat = r8a7740_boards_compat_dt, 909 .dt_compat = r8a7740_boards_compat_dt,
911MACHINE_END 910MACHINE_END
912 911
diff --git a/arch/arm/mach-shmobile/setup-r8a7779.c b/arch/arm/mach-shmobile/setup-r8a7779.c
index c54ff9b29fe5..042df35e71a0 100644
--- a/arch/arm/mach-shmobile/setup-r8a7779.c
+++ b/arch/arm/mach-shmobile/setup-r8a7779.c
@@ -21,6 +21,7 @@
21#include <linux/init.h> 21#include <linux/init.h>
22#include <linux/interrupt.h> 22#include <linux/interrupt.h>
23#include <linux/irq.h> 23#include <linux/irq.h>
24#include <linux/of_platform.h>
24#include <linux/platform_device.h> 25#include <linux/platform_device.h>
25#include <linux/delay.h> 26#include <linux/delay.h>
26#include <linux/input.h> 27#include <linux/input.h>
@@ -28,6 +29,7 @@
28#include <linux/serial_sci.h> 29#include <linux/serial_sci.h>
29#include <linux/sh_intc.h> 30#include <linux/sh_intc.h>
30#include <linux/sh_timer.h> 31#include <linux/sh_timer.h>
32#include <linux/dma-mapping.h>
31#include <mach/hardware.h> 33#include <mach/hardware.h>
32#include <mach/irqs.h> 34#include <mach/irqs.h>
33#include <mach/r8a7779.h> 35#include <mach/r8a7779.h>
@@ -91,7 +93,7 @@ static struct plat_sci_port scif0_platform_data = {
91 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1, 93 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1,
92 .scbrr_algo_id = SCBRR_ALGO_2, 94 .scbrr_algo_id = SCBRR_ALGO_2,
93 .type = PORT_SCIF, 95 .type = PORT_SCIF,
94 .irqs = SCIx_IRQ_MUXED(gic_spi(88)), 96 .irqs = SCIx_IRQ_MUXED(gic_iid(0x78)),
95}; 97};
96 98
97static struct platform_device scif0_device = { 99static struct platform_device scif0_device = {
@@ -108,7 +110,7 @@ static struct plat_sci_port scif1_platform_data = {
108 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1, 110 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1,
109 .scbrr_algo_id = SCBRR_ALGO_2, 111 .scbrr_algo_id = SCBRR_ALGO_2,
110 .type = PORT_SCIF, 112 .type = PORT_SCIF,
111 .irqs = SCIx_IRQ_MUXED(gic_spi(89)), 113 .irqs = SCIx_IRQ_MUXED(gic_iid(0x79)),
112}; 114};
113 115
114static struct platform_device scif1_device = { 116static struct platform_device scif1_device = {
@@ -125,7 +127,7 @@ static struct plat_sci_port scif2_platform_data = {
125 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1, 127 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1,
126 .scbrr_algo_id = SCBRR_ALGO_2, 128 .scbrr_algo_id = SCBRR_ALGO_2,
127 .type = PORT_SCIF, 129 .type = PORT_SCIF,
128 .irqs = SCIx_IRQ_MUXED(gic_spi(90)), 130 .irqs = SCIx_IRQ_MUXED(gic_iid(0x7a)),
129}; 131};
130 132
131static struct platform_device scif2_device = { 133static struct platform_device scif2_device = {
@@ -142,7 +144,7 @@ static struct plat_sci_port scif3_platform_data = {
142 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1, 144 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1,
143 .scbrr_algo_id = SCBRR_ALGO_2, 145 .scbrr_algo_id = SCBRR_ALGO_2,
144 .type = PORT_SCIF, 146 .type = PORT_SCIF,
145 .irqs = SCIx_IRQ_MUXED(gic_spi(91)), 147 .irqs = SCIx_IRQ_MUXED(gic_iid(0x7b)),
146}; 148};
147 149
148static struct platform_device scif3_device = { 150static struct platform_device scif3_device = {
@@ -159,7 +161,7 @@ static struct plat_sci_port scif4_platform_data = {
159 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1, 161 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1,
160 .scbrr_algo_id = SCBRR_ALGO_2, 162 .scbrr_algo_id = SCBRR_ALGO_2,
161 .type = PORT_SCIF, 163 .type = PORT_SCIF,
162 .irqs = SCIx_IRQ_MUXED(gic_spi(92)), 164 .irqs = SCIx_IRQ_MUXED(gic_iid(0x7c)),
163}; 165};
164 166
165static struct platform_device scif4_device = { 167static struct platform_device scif4_device = {
@@ -176,7 +178,7 @@ static struct plat_sci_port scif5_platform_data = {
176 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1, 178 .scscr = SCSCR_RE | SCSCR_TE | SCSCR_CKE1,
177 .scbrr_algo_id = SCBRR_ALGO_2, 179 .scbrr_algo_id = SCBRR_ALGO_2,
178 .type = PORT_SCIF, 180 .type = PORT_SCIF,
179 .irqs = SCIx_IRQ_MUXED(gic_spi(93)), 181 .irqs = SCIx_IRQ_MUXED(gic_iid(0x7d)),
180}; 182};
181 183
182static struct platform_device scif5_device = { 184static struct platform_device scif5_device = {
@@ -203,7 +205,7 @@ static struct resource tmu00_resources[] = {
203 .flags = IORESOURCE_MEM, 205 .flags = IORESOURCE_MEM,
204 }, 206 },
205 [1] = { 207 [1] = {
206 .start = gic_spi(32), 208 .start = gic_iid(0x40),
207 .flags = IORESOURCE_IRQ, 209 .flags = IORESOURCE_IRQ,
208 }, 210 },
209}; 211};
@@ -233,7 +235,7 @@ static struct resource tmu01_resources[] = {
233 .flags = IORESOURCE_MEM, 235 .flags = IORESOURCE_MEM,
234 }, 236 },
235 [1] = { 237 [1] = {
236 .start = gic_spi(33), 238 .start = gic_iid(0x41),
237 .flags = IORESOURCE_IRQ, 239 .flags = IORESOURCE_IRQ,
238 }, 240 },
239}; 241};
@@ -255,7 +257,7 @@ static struct resource rcar_i2c0_res[] = {
255 .end = 0xffc70fff, 257 .end = 0xffc70fff,
256 .flags = IORESOURCE_MEM, 258 .flags = IORESOURCE_MEM,
257 }, { 259 }, {
258 .start = gic_spi(79), 260 .start = gic_iid(0x6f),
259 .flags = IORESOURCE_IRQ, 261 .flags = IORESOURCE_IRQ,
260 }, 262 },
261}; 263};
@@ -273,7 +275,7 @@ static struct resource rcar_i2c1_res[] = {
273 .end = 0xffc71fff, 275 .end = 0xffc71fff,
274 .flags = IORESOURCE_MEM, 276 .flags = IORESOURCE_MEM,
275 }, { 277 }, {
276 .start = gic_spi(82), 278 .start = gic_iid(0x72),
277 .flags = IORESOURCE_IRQ, 279 .flags = IORESOURCE_IRQ,
278 }, 280 },
279}; 281};
@@ -291,7 +293,7 @@ static struct resource rcar_i2c2_res[] = {
291 .end = 0xffc72fff, 293 .end = 0xffc72fff,
292 .flags = IORESOURCE_MEM, 294 .flags = IORESOURCE_MEM,
293 }, { 295 }, {
294 .start = gic_spi(80), 296 .start = gic_iid(0x70),
295 .flags = IORESOURCE_IRQ, 297 .flags = IORESOURCE_IRQ,
296 }, 298 },
297}; 299};
@@ -309,7 +311,7 @@ static struct resource rcar_i2c3_res[] = {
309 .end = 0xffc73fff, 311 .end = 0xffc73fff,
310 .flags = IORESOURCE_MEM, 312 .flags = IORESOURCE_MEM,
311 }, { 313 }, {
312 .start = gic_spi(81), 314 .start = gic_iid(0x71),
313 .flags = IORESOURCE_IRQ, 315 .flags = IORESOURCE_IRQ,
314 }, 316 },
315}; 317};
@@ -321,7 +323,31 @@ static struct platform_device i2c3_device = {
321 .num_resources = ARRAY_SIZE(rcar_i2c3_res), 323 .num_resources = ARRAY_SIZE(rcar_i2c3_res),
322}; 324};
323 325
324static struct platform_device *r8a7779_early_devices[] __initdata = { 326static struct resource sata_resources[] = {
327 [0] = {
328 .name = "rcar-sata",
329 .start = 0xfc600000,
330 .end = 0xfc601fff,
331 .flags = IORESOURCE_MEM,
332 },
333 [1] = {
334 .start = gic_iid(0x84),
335 .flags = IORESOURCE_IRQ,
336 },
337};
338
339static struct platform_device sata_device = {
340 .name = "sata_rcar",
341 .id = -1,
342 .resource = sata_resources,
343 .num_resources = ARRAY_SIZE(sata_resources),
344 .dev = {
345 .dma_mask = &sata_device.dev.coherent_dma_mask,
346 .coherent_dma_mask = DMA_BIT_MASK(32),
347 },
348};
349
350static struct platform_device *r8a7779_devices_dt[] __initdata = {
325 &scif0_device, 351 &scif0_device,
326 &scif1_device, 352 &scif1_device,
327 &scif2_device, 353 &scif2_device,
@@ -330,13 +356,14 @@ static struct platform_device *r8a7779_early_devices[] __initdata = {
330 &scif5_device, 356 &scif5_device,
331 &tmu00_device, 357 &tmu00_device,
332 &tmu01_device, 358 &tmu01_device,
359};
360
361static struct platform_device *r8a7779_late_devices[] __initdata = {
333 &i2c0_device, 362 &i2c0_device,
334 &i2c1_device, 363 &i2c1_device,
335 &i2c2_device, 364 &i2c2_device,
336 &i2c3_device, 365 &i2c3_device,
337}; 366 &sata_device,
338
339static struct platform_device *r8a7779_late_devices[] __initdata = {
340}; 367};
341 368
342void __init r8a7779_add_standard_devices(void) 369void __init r8a7779_add_standard_devices(void)
@@ -349,8 +376,8 @@ void __init r8a7779_add_standard_devices(void)
349 376
350 r8a7779_init_pm_domains(); 377 r8a7779_init_pm_domains();
351 378
352 platform_add_devices(r8a7779_early_devices, 379 platform_add_devices(r8a7779_devices_dt,
353 ARRAY_SIZE(r8a7779_early_devices)); 380 ARRAY_SIZE(r8a7779_devices_dt));
354 platform_add_devices(r8a7779_late_devices, 381 platform_add_devices(r8a7779_late_devices,
355 ARRAY_SIZE(r8a7779_late_devices)); 382 ARRAY_SIZE(r8a7779_late_devices));
356} 383}
@@ -367,8 +394,8 @@ void __init r8a7779_earlytimer_init(void)
367 394
368void __init r8a7779_add_early_devices(void) 395void __init r8a7779_add_early_devices(void)
369{ 396{
370 early_platform_add_devices(r8a7779_early_devices, 397 early_platform_add_devices(r8a7779_devices_dt,
371 ARRAY_SIZE(r8a7779_early_devices)); 398 ARRAY_SIZE(r8a7779_devices_dt));
372 399
373 /* Early serial console setup is not included here due to 400 /* Early serial console setup is not included here due to
374 * memory map collisions. The SCIF serial ports in r8a7779 401 * memory map collisions. The SCIF serial ports in r8a7779
@@ -386,3 +413,40 @@ void __init r8a7779_add_early_devices(void)
386 * command line in case of the marzen board. 413 * command line in case of the marzen board.
387 */ 414 */
388} 415}
416
417#ifdef CONFIG_USE_OF
418void __init r8a7779_init_delay(void)
419{
420 shmobile_setup_delay(1000, 2, 4); /* Cortex-A9 @ 1000MHz */
421}
422
423static const struct of_dev_auxdata r8a7779_auxdata_lookup[] __initconst = {
424 {},
425};
426
427void __init r8a7779_add_standard_devices_dt(void)
428{
429 /* clocks are setup late during boot in the case of DT */
430 r8a7779_clock_init();
431
432 platform_add_devices(r8a7779_devices_dt,
433 ARRAY_SIZE(r8a7779_devices_dt));
434 of_platform_populate(NULL, of_default_bus_match_table,
435 r8a7779_auxdata_lookup, NULL);
436}
437
438static const char *r8a7779_compat_dt[] __initdata = {
439 "renesas,r8a7779",
440 NULL,
441};
442
443DT_MACHINE_START(R8A7779_DT, "Generic R8A7779 (Flattened Device Tree)")
444 .map_io = r8a7779_map_io,
445 .init_early = r8a7779_init_delay,
446 .nr_irqs = NR_IRQS_LEGACY,
447 .init_irq = r8a7779_init_irq_dt,
448 .init_machine = r8a7779_add_standard_devices_dt,
449 .init_time = shmobile_timer_init,
450 .dt_compat = r8a7779_compat_dt,
451MACHINE_END
452#endif /* CONFIG_USE_OF */
diff --git a/arch/arm/mach-shmobile/setup-sh7372.c b/arch/arm/mach-shmobile/setup-sh7372.c
index 59c7146bf66f..5502d624aca6 100644
--- a/arch/arm/mach-shmobile/setup-sh7372.c
+++ b/arch/arm/mach-shmobile/setup-sh7372.c
@@ -1175,7 +1175,6 @@ DT_MACHINE_START(SH7372_DT, "Generic SH7372 (Flattened Device Tree)")
1175 .init_irq = sh7372_init_irq, 1175 .init_irq = sh7372_init_irq,
1176 .handle_irq = shmobile_handle_irq_intc, 1176 .handle_irq = shmobile_handle_irq_intc,
1177 .init_machine = sh7372_add_standard_devices_dt, 1177 .init_machine = sh7372_add_standard_devices_dt,
1178 .init_time = shmobile_timer_init,
1179 .dt_compat = sh7372_boards_compat_dt, 1178 .dt_compat = sh7372_boards_compat_dt,
1180MACHINE_END 1179MACHINE_END
1181 1180
diff --git a/arch/arm/mach-shmobile/setup-sh73a0.c b/arch/arm/mach-shmobile/setup-sh73a0.c
index bdab575f88bc..fdf3894b1cc3 100644
--- a/arch/arm/mach-shmobile/setup-sh73a0.c
+++ b/arch/arm/mach-shmobile/setup-sh73a0.c
@@ -22,6 +22,7 @@
22#include <linux/init.h> 22#include <linux/init.h>
23#include <linux/interrupt.h> 23#include <linux/interrupt.h>
24#include <linux/irq.h> 24#include <linux/irq.h>
25#include <linux/irqchip.h>
25#include <linux/platform_device.h> 26#include <linux/platform_device.h>
26#include <linux/of_platform.h> 27#include <linux/of_platform.h>
27#include <linux/delay.h> 28#include <linux/delay.h>
@@ -32,6 +33,7 @@
32#include <linux/sh_intc.h> 33#include <linux/sh_intc.h>
33#include <linux/sh_timer.h> 34#include <linux/sh_timer.h>
34#include <linux/platform_data/sh_ipmmu.h> 35#include <linux/platform_data/sh_ipmmu.h>
36#include <linux/platform_data/irq-renesas-intc-irqpin.h>
35#include <mach/dma-register.h> 37#include <mach/dma-register.h>
36#include <mach/hardware.h> 38#include <mach/hardware.h>
37#include <mach/irqs.h> 39#include <mach/irqs.h>
@@ -810,7 +812,128 @@ static struct platform_device ipmmu_device = {
810 .num_resources = ARRAY_SIZE(ipmmu_resources), 812 .num_resources = ARRAY_SIZE(ipmmu_resources),
811}; 813};
812 814
813static struct platform_device *sh73a0_early_devices_dt[] __initdata = { 815static struct renesas_intc_irqpin_config irqpin0_platform_data = {
816 .irq_base = irq_pin(0), /* IRQ0 -> IRQ7 */
817};
818
819static struct resource irqpin0_resources[] = {
820 DEFINE_RES_MEM(0xe6900000, 4), /* ICR1A */
821 DEFINE_RES_MEM(0xe6900010, 4), /* INTPRI00A */
822 DEFINE_RES_MEM(0xe6900020, 1), /* INTREQ00A */
823 DEFINE_RES_MEM(0xe6900040, 1), /* INTMSK00A */
824 DEFINE_RES_MEM(0xe6900060, 1), /* INTMSKCLR00A */
825 DEFINE_RES_IRQ(gic_spi(1)), /* IRQ0 */
826 DEFINE_RES_IRQ(gic_spi(2)), /* IRQ1 */
827 DEFINE_RES_IRQ(gic_spi(3)), /* IRQ2 */
828 DEFINE_RES_IRQ(gic_spi(4)), /* IRQ3 */
829 DEFINE_RES_IRQ(gic_spi(5)), /* IRQ4 */
830 DEFINE_RES_IRQ(gic_spi(6)), /* IRQ5 */
831 DEFINE_RES_IRQ(gic_spi(7)), /* IRQ6 */
832 DEFINE_RES_IRQ(gic_spi(8)), /* IRQ7 */
833};
834
835static struct platform_device irqpin0_device = {
836 .name = "renesas_intc_irqpin",
837 .id = 0,
838 .resource = irqpin0_resources,
839 .num_resources = ARRAY_SIZE(irqpin0_resources),
840 .dev = {
841 .platform_data = &irqpin0_platform_data,
842 },
843};
844
845static struct renesas_intc_irqpin_config irqpin1_platform_data = {
846 .irq_base = irq_pin(8), /* IRQ8 -> IRQ15 */
847 .control_parent = true, /* Disable spurious IRQ10 */
848};
849
850static struct resource irqpin1_resources[] = {
851 DEFINE_RES_MEM(0xe6900004, 4), /* ICR2A */
852 DEFINE_RES_MEM(0xe6900014, 4), /* INTPRI10A */
853 DEFINE_RES_MEM(0xe6900024, 1), /* INTREQ10A */
854 DEFINE_RES_MEM(0xe6900044, 1), /* INTMSK10A */
855 DEFINE_RES_MEM(0xe6900064, 1), /* INTMSKCLR10A */
856 DEFINE_RES_IRQ(gic_spi(9)), /* IRQ8 */
857 DEFINE_RES_IRQ(gic_spi(10)), /* IRQ9 */
858 DEFINE_RES_IRQ(gic_spi(11)), /* IRQ10 */
859 DEFINE_RES_IRQ(gic_spi(12)), /* IRQ11 */
860 DEFINE_RES_IRQ(gic_spi(13)), /* IRQ12 */
861 DEFINE_RES_IRQ(gic_spi(14)), /* IRQ13 */
862 DEFINE_RES_IRQ(gic_spi(15)), /* IRQ14 */
863 DEFINE_RES_IRQ(gic_spi(16)), /* IRQ15 */
864};
865
866static struct platform_device irqpin1_device = {
867 .name = "renesas_intc_irqpin",
868 .id = 1,
869 .resource = irqpin1_resources,
870 .num_resources = ARRAY_SIZE(irqpin1_resources),
871 .dev = {
872 .platform_data = &irqpin1_platform_data,
873 },
874};
875
876static struct renesas_intc_irqpin_config irqpin2_platform_data = {
877 .irq_base = irq_pin(16), /* IRQ16 -> IRQ23 */
878};
879
880static struct resource irqpin2_resources[] = {
881 DEFINE_RES_MEM(0xe6900008, 4), /* ICR3A */
882 DEFINE_RES_MEM(0xe6900018, 4), /* INTPRI20A */
883 DEFINE_RES_MEM(0xe6900028, 1), /* INTREQ20A */
884 DEFINE_RES_MEM(0xe6900048, 1), /* INTMSK20A */
885 DEFINE_RES_MEM(0xe6900068, 1), /* INTMSKCLR20A */
886 DEFINE_RES_IRQ(gic_spi(17)), /* IRQ16 */
887 DEFINE_RES_IRQ(gic_spi(18)), /* IRQ17 */
888 DEFINE_RES_IRQ(gic_spi(19)), /* IRQ18 */
889 DEFINE_RES_IRQ(gic_spi(20)), /* IRQ19 */
890 DEFINE_RES_IRQ(gic_spi(21)), /* IRQ20 */
891 DEFINE_RES_IRQ(gic_spi(22)), /* IRQ21 */
892 DEFINE_RES_IRQ(gic_spi(23)), /* IRQ22 */
893 DEFINE_RES_IRQ(gic_spi(24)), /* IRQ23 */
894};
895
896static struct platform_device irqpin2_device = {
897 .name = "renesas_intc_irqpin",
898 .id = 2,
899 .resource = irqpin2_resources,
900 .num_resources = ARRAY_SIZE(irqpin2_resources),
901 .dev = {
902 .platform_data = &irqpin2_platform_data,
903 },
904};
905
906static struct renesas_intc_irqpin_config irqpin3_platform_data = {
907 .irq_base = irq_pin(24), /* IRQ24 -> IRQ31 */
908};
909
910static struct resource irqpin3_resources[] = {
911 DEFINE_RES_MEM(0xe690000c, 4), /* ICR4A */
912 DEFINE_RES_MEM(0xe690001c, 4), /* INTPRI30A */
913 DEFINE_RES_MEM(0xe690002c, 1), /* INTREQ30A */
914 DEFINE_RES_MEM(0xe690004c, 1), /* INTMSK30A */
915 DEFINE_RES_MEM(0xe690006c, 1), /* INTMSKCLR30A */
916 DEFINE_RES_IRQ(gic_spi(25)), /* IRQ24 */
917 DEFINE_RES_IRQ(gic_spi(26)), /* IRQ25 */
918 DEFINE_RES_IRQ(gic_spi(27)), /* IRQ26 */
919 DEFINE_RES_IRQ(gic_spi(28)), /* IRQ27 */
920 DEFINE_RES_IRQ(gic_spi(29)), /* IRQ28 */
921 DEFINE_RES_IRQ(gic_spi(30)), /* IRQ29 */
922 DEFINE_RES_IRQ(gic_spi(31)), /* IRQ30 */
923 DEFINE_RES_IRQ(gic_spi(32)), /* IRQ31 */
924};
925
926static struct platform_device irqpin3_device = {
927 .name = "renesas_intc_irqpin",
928 .id = 3,
929 .resource = irqpin3_resources,
930 .num_resources = ARRAY_SIZE(irqpin3_resources),
931 .dev = {
932 .platform_data = &irqpin3_platform_data,
933 },
934};
935
936static struct platform_device *sh73a0_devices_dt[] __initdata = {
814 &scif0_device, 937 &scif0_device,
815 &scif1_device, 938 &scif1_device,
816 &scif2_device, 939 &scif2_device,
@@ -838,6 +961,10 @@ static struct platform_device *sh73a0_late_devices[] __initdata = {
838 &dma0_device, 961 &dma0_device,
839 &mpdma0_device, 962 &mpdma0_device,
840 &pmu_device, 963 &pmu_device,
964 &irqpin0_device,
965 &irqpin1_device,
966 &irqpin2_device,
967 &irqpin3_device,
841}; 968};
842 969
843#define SRCR2 IOMEM(0xe61580b0) 970#define SRCR2 IOMEM(0xe61580b0)
@@ -847,8 +974,8 @@ void __init sh73a0_add_standard_devices(void)
847 /* Clear software reset bit on SY-DMAC module */ 974 /* Clear software reset bit on SY-DMAC module */
848 __raw_writel(__raw_readl(SRCR2) & ~(1 << 18), SRCR2); 975 __raw_writel(__raw_readl(SRCR2) & ~(1 << 18), SRCR2);
849 976
850 platform_add_devices(sh73a0_early_devices_dt, 977 platform_add_devices(sh73a0_devices_dt,
851 ARRAY_SIZE(sh73a0_early_devices_dt)); 978 ARRAY_SIZE(sh73a0_devices_dt));
852 platform_add_devices(sh73a0_early_devices, 979 platform_add_devices(sh73a0_early_devices,
853 ARRAY_SIZE(sh73a0_early_devices)); 980 ARRAY_SIZE(sh73a0_early_devices));
854 platform_add_devices(sh73a0_late_devices, 981 platform_add_devices(sh73a0_late_devices,
@@ -867,8 +994,8 @@ void __init sh73a0_earlytimer_init(void)
867 994
868void __init sh73a0_add_early_devices(void) 995void __init sh73a0_add_early_devices(void)
869{ 996{
870 early_platform_add_devices(sh73a0_early_devices_dt, 997 early_platform_add_devices(sh73a0_devices_dt,
871 ARRAY_SIZE(sh73a0_early_devices_dt)); 998 ARRAY_SIZE(sh73a0_devices_dt));
872 early_platform_add_devices(sh73a0_early_devices, 999 early_platform_add_devices(sh73a0_early_devices,
873 ARRAY_SIZE(sh73a0_early_devices)); 1000 ARRAY_SIZE(sh73a0_early_devices));
874 1001
@@ -878,23 +1005,9 @@ void __init sh73a0_add_early_devices(void)
878 1005
879#ifdef CONFIG_USE_OF 1006#ifdef CONFIG_USE_OF
880 1007
881/* Please note that the clock initialisation shcheme used in 1008void __init sh73a0_init_delay(void)
882 * sh73a0_add_early_devices_dt() and sh73a0_add_standard_devices_dt()
883 * does not work with SMP as there is a yet to be resolved lock-up in
884 * workqueue initialisation.
885 *
886 * CONFIG_SMP should be disabled when using this code.
887 */
888
889void __init sh73a0_add_early_devices_dt(void)
890{ 1009{
891 shmobile_setup_delay(1196, 44, 46); /* Cortex-A9 @ 1196MHz */ 1010 shmobile_setup_delay(1196, 44, 46); /* Cortex-A9 @ 1196MHz */
892
893 early_platform_add_devices(sh73a0_early_devices_dt,
894 ARRAY_SIZE(sh73a0_early_devices_dt));
895
896 /* setup early console here as well */
897 shmobile_setup_console();
898} 1011}
899 1012
900static const struct of_dev_auxdata sh73a0_auxdata_lookup[] __initconst = { 1013static const struct of_dev_auxdata sh73a0_auxdata_lookup[] __initconst = {
@@ -906,8 +1019,8 @@ void __init sh73a0_add_standard_devices_dt(void)
906 /* clocks are setup late during boot in the case of DT */ 1019 /* clocks are setup late during boot in the case of DT */
907 sh73a0_clock_init(); 1020 sh73a0_clock_init();
908 1021
909 platform_add_devices(sh73a0_early_devices_dt, 1022 platform_add_devices(sh73a0_devices_dt,
910 ARRAY_SIZE(sh73a0_early_devices_dt)); 1023 ARRAY_SIZE(sh73a0_devices_dt));
911 of_platform_populate(NULL, of_default_bus_match_table, 1024 of_platform_populate(NULL, of_default_bus_match_table,
912 sh73a0_auxdata_lookup, NULL); 1025 sh73a0_auxdata_lookup, NULL);
913} 1026}
@@ -918,12 +1031,12 @@ static const char *sh73a0_boards_compat_dt[] __initdata = {
918}; 1031};
919 1032
920DT_MACHINE_START(SH73A0_DT, "Generic SH73A0 (Flattened Device Tree)") 1033DT_MACHINE_START(SH73A0_DT, "Generic SH73A0 (Flattened Device Tree)")
1034 .smp = smp_ops(sh73a0_smp_ops),
921 .map_io = sh73a0_map_io, 1035 .map_io = sh73a0_map_io,
922 .init_early = sh73a0_add_early_devices_dt, 1036 .init_early = sh73a0_init_delay,
923 .nr_irqs = NR_IRQS_LEGACY, 1037 .nr_irqs = NR_IRQS_LEGACY,
924 .init_irq = sh73a0_init_irq_dt, 1038 .init_irq = irqchip_init,
925 .init_machine = sh73a0_add_standard_devices_dt, 1039 .init_machine = sh73a0_add_standard_devices_dt,
926 .init_time = shmobile_timer_init,
927 .dt_compat = sh73a0_boards_compat_dt, 1040 .dt_compat = sh73a0_boards_compat_dt,
928MACHINE_END 1041MACHINE_END
929#endif /* CONFIG_USE_OF */ 1042#endif /* CONFIG_USE_OF */
diff --git a/arch/arm/mach-shmobile/smp-emev2.c b/arch/arm/mach-shmobile/smp-emev2.c
index 953eb1f9388d..8225c16b371b 100644
--- a/arch/arm/mach-shmobile/smp-emev2.c
+++ b/arch/arm/mach-shmobile/smp-emev2.c
@@ -28,63 +28,9 @@
28#include <mach/emev2.h> 28#include <mach/emev2.h>
29#include <asm/smp_plat.h> 29#include <asm/smp_plat.h>
30#include <asm/smp_scu.h> 30#include <asm/smp_scu.h>
31#include <asm/cacheflush.h>
32 31
33#define EMEV2_SCU_BASE 0x1e000000 32#define EMEV2_SCU_BASE 0x1e000000
34 33
35static DEFINE_SPINLOCK(scu_lock);
36static void __iomem *scu_base;
37
38static void modify_scu_cpu_psr(unsigned long set, unsigned long clr)
39{
40 unsigned long tmp;
41
42 /* we assume this code is running on a different cpu
43 * than the one that is changing coherency setting */
44 spin_lock(&scu_lock);
45 tmp = readl(scu_base + 8);
46 tmp &= ~clr;
47 tmp |= set;
48 writel(tmp, scu_base + 8);
49 spin_unlock(&scu_lock);
50
51}
52
53static unsigned int __init emev2_get_core_count(void)
54{
55 if (!scu_base) {
56 scu_base = ioremap(EMEV2_SCU_BASE, PAGE_SIZE);
57 emev2_clock_init(); /* need ioremapped SMU */
58 }
59
60 WARN_ON_ONCE(!scu_base);
61
62 return scu_base ? scu_get_core_count(scu_base) : 1;
63}
64
65static int emev2_platform_cpu_kill(unsigned int cpu)
66{
67 return 0; /* not supported yet */
68}
69
70static int __maybe_unused emev2_cpu_kill(unsigned int cpu)
71{
72 int k;
73
74 /* this function is running on another CPU than the offline target,
75 * here we need wait for shutdown code in platform_cpu_die() to
76 * finish before asking SoC-specific code to power off the CPU core.
77 */
78 for (k = 0; k < 1000; k++) {
79 if (shmobile_cpu_is_dead(cpu))
80 return emev2_platform_cpu_kill(cpu);
81 mdelay(1);
82 }
83
84 return 0;
85}
86
87
88static void __cpuinit emev2_secondary_init(unsigned int cpu) 34static void __cpuinit emev2_secondary_init(unsigned int cpu)
89{ 35{
90 gic_secondary_init(0); 36 gic_secondary_init(0);
@@ -92,31 +38,30 @@ static void __cpuinit emev2_secondary_init(unsigned int cpu)
92 38
93static int __cpuinit emev2_boot_secondary(unsigned int cpu, struct task_struct *idle) 39static int __cpuinit emev2_boot_secondary(unsigned int cpu, struct task_struct *idle)
94{ 40{
95 cpu = cpu_logical_map(cpu); 41 arch_send_wakeup_ipi_mask(cpumask_of(cpu_logical_map(cpu)));
96
97 /* enable cache coherency */
98 modify_scu_cpu_psr(0, 3 << (cpu * 8));
99
100 /* Tell ROM loader about our vector (in headsmp.S) */
101 emev2_set_boot_vector(__pa(shmobile_secondary_vector));
102
103 arch_send_wakeup_ipi_mask(cpumask_of(cpu));
104 return 0; 42 return 0;
105} 43}
106 44
107static void __init emev2_smp_prepare_cpus(unsigned int max_cpus) 45static void __init emev2_smp_prepare_cpus(unsigned int max_cpus)
108{ 46{
109 int cpu = cpu_logical_map(0); 47 scu_enable(shmobile_scu_base);
110 48
111 scu_enable(scu_base); 49 /* Tell ROM loader about our vector (in headsmp-scu.S) */
50 emev2_set_boot_vector(__pa(shmobile_secondary_vector_scu));
112 51
113 /* enable cache coherency on CPU0 */ 52 /* enable cache coherency on booting CPU */
114 modify_scu_cpu_psr(0, 3 << (cpu * 8)); 53 scu_power_mode(shmobile_scu_base, SCU_PM_NORMAL);
115} 54}
116 55
117static void __init emev2_smp_init_cpus(void) 56static void __init emev2_smp_init_cpus(void)
118{ 57{
119 unsigned int ncores = emev2_get_core_count(); 58 unsigned int ncores;
59
60 /* setup EMEV2 specific SCU base */
61 shmobile_scu_base = ioremap(EMEV2_SCU_BASE, PAGE_SIZE);
62 emev2_clock_init(); /* need ioremapped SMU */
63
64 ncores = shmobile_scu_base ? scu_get_core_count(shmobile_scu_base) : 1;
120 65
121 shmobile_smp_init_cpus(ncores); 66 shmobile_smp_init_cpus(ncores);
122} 67}
@@ -126,9 +71,4 @@ struct smp_operations emev2_smp_ops __initdata = {
126 .smp_prepare_cpus = emev2_smp_prepare_cpus, 71 .smp_prepare_cpus = emev2_smp_prepare_cpus,
127 .smp_secondary_init = emev2_secondary_init, 72 .smp_secondary_init = emev2_secondary_init,
128 .smp_boot_secondary = emev2_boot_secondary, 73 .smp_boot_secondary = emev2_boot_secondary,
129#ifdef CONFIG_HOTPLUG_CPU
130 .cpu_kill = emev2_cpu_kill,
131 .cpu_die = shmobile_cpu_die,
132 .cpu_disable = shmobile_cpu_disable,
133#endif
134}; 74};
diff --git a/arch/arm/mach-shmobile/smp-r8a7779.c b/arch/arm/mach-shmobile/smp-r8a7779.c
index 3a4acf23edcf..ea4535a5c4e2 100644
--- a/arch/arm/mach-shmobile/smp-r8a7779.c
+++ b/arch/arm/mach-shmobile/smp-r8a7779.c
@@ -26,11 +26,13 @@
26#include <linux/irqchip/arm-gic.h> 26#include <linux/irqchip/arm-gic.h>
27#include <mach/common.h> 27#include <mach/common.h>
28#include <mach/r8a7779.h> 28#include <mach/r8a7779.h>
29#include <asm/cacheflush.h>
29#include <asm/smp_plat.h> 30#include <asm/smp_plat.h>
30#include <asm/smp_scu.h> 31#include <asm/smp_scu.h>
31#include <asm/smp_twd.h> 32#include <asm/smp_twd.h>
32 33
33#define AVECR IOMEM(0xfe700040) 34#define AVECR IOMEM(0xfe700040)
35#define R8A7779_SCU_BASE 0xf0000000
34 36
35static struct r8a7779_pm_ch r8a7779_ch_cpu1 = { 37static struct r8a7779_pm_ch r8a7779_ch_cpu1 = {
36 .chan_offs = 0x40, /* PWRSR0 .. PWRER0 */ 38 .chan_offs = 0x40, /* PWRSR0 .. PWRER0 */
@@ -56,44 +58,14 @@ static struct r8a7779_pm_ch *r8a7779_ch_cpu[4] = {
56 [3] = &r8a7779_ch_cpu3, 58 [3] = &r8a7779_ch_cpu3,
57}; 59};
58 60
59static void __iomem *scu_base_addr(void)
60{
61 return (void __iomem *)0xf0000000;
62}
63
64static DEFINE_SPINLOCK(scu_lock);
65static unsigned long tmp;
66
67#ifdef CONFIG_HAVE_ARM_TWD 61#ifdef CONFIG_HAVE_ARM_TWD
68static DEFINE_TWD_LOCAL_TIMER(twd_local_timer, 0xf0000600, 29); 62static DEFINE_TWD_LOCAL_TIMER(twd_local_timer, R8A7779_SCU_BASE + 0x600, 29);
69
70void __init r8a7779_register_twd(void) 63void __init r8a7779_register_twd(void)
71{ 64{
72 twd_local_timer_register(&twd_local_timer); 65 twd_local_timer_register(&twd_local_timer);
73} 66}
74#endif 67#endif
75 68
76static void modify_scu_cpu_psr(unsigned long set, unsigned long clr)
77{
78 void __iomem *scu_base = scu_base_addr();
79
80 spin_lock(&scu_lock);
81 tmp = __raw_readl(scu_base + 8);
82 tmp &= ~clr;
83 tmp |= set;
84 spin_unlock(&scu_lock);
85
86 /* disable cache coherency after releasing the lock */
87 __raw_writel(tmp, scu_base + 8);
88}
89
90static unsigned int __init r8a7779_get_core_count(void)
91{
92 void __iomem *scu_base = scu_base_addr();
93
94 return scu_get_core_count(scu_base);
95}
96
97static int r8a7779_platform_cpu_kill(unsigned int cpu) 69static int r8a7779_platform_cpu_kill(unsigned int cpu)
98{ 70{
99 struct r8a7779_pm_ch *ch = NULL; 71 struct r8a7779_pm_ch *ch = NULL;
@@ -101,9 +73,6 @@ static int r8a7779_platform_cpu_kill(unsigned int cpu)
101 73
102 cpu = cpu_logical_map(cpu); 74 cpu = cpu_logical_map(cpu);
103 75
104 /* disable cache coherency */
105 modify_scu_cpu_psr(3 << (cpu * 8), 0);
106
107 if (cpu < ARRAY_SIZE(r8a7779_ch_cpu)) 76 if (cpu < ARRAY_SIZE(r8a7779_ch_cpu))
108 ch = r8a7779_ch_cpu[cpu]; 77 ch = r8a7779_ch_cpu[cpu];
109 78
@@ -113,25 +82,6 @@ static int r8a7779_platform_cpu_kill(unsigned int cpu)
113 return ret ? ret : 1; 82 return ret ? ret : 1;
114} 83}
115 84
116static int __maybe_unused r8a7779_cpu_kill(unsigned int cpu)
117{
118 int k;
119
120 /* this function is running on another CPU than the offline target,
121 * here we need wait for shutdown code in platform_cpu_die() to
122 * finish before asking SoC-specific code to power off the CPU core.
123 */
124 for (k = 0; k < 1000; k++) {
125 if (shmobile_cpu_is_dead(cpu))
126 return r8a7779_platform_cpu_kill(cpu);
127
128 mdelay(1);
129 }
130
131 return 0;
132}
133
134
135static void __cpuinit r8a7779_secondary_init(unsigned int cpu) 85static void __cpuinit r8a7779_secondary_init(unsigned int cpu)
136{ 86{
137 gic_secondary_init(0); 87 gic_secondary_init(0);
@@ -144,9 +94,6 @@ static int __cpuinit r8a7779_boot_secondary(unsigned int cpu, struct task_struct
144 94
145 cpu = cpu_logical_map(cpu); 95 cpu = cpu_logical_map(cpu);
146 96
147 /* enable cache coherency */
148 modify_scu_cpu_psr(0, 3 << (cpu * 8));
149
150 if (cpu < ARRAY_SIZE(r8a7779_ch_cpu)) 97 if (cpu < ARRAY_SIZE(r8a7779_ch_cpu))
151 ch = r8a7779_ch_cpu[cpu]; 98 ch = r8a7779_ch_cpu[cpu];
152 99
@@ -158,15 +105,13 @@ static int __cpuinit r8a7779_boot_secondary(unsigned int cpu, struct task_struct
158 105
159static void __init r8a7779_smp_prepare_cpus(unsigned int max_cpus) 106static void __init r8a7779_smp_prepare_cpus(unsigned int max_cpus)
160{ 107{
161 int cpu = cpu_logical_map(0); 108 scu_enable(shmobile_scu_base);
162 109
163 scu_enable(scu_base_addr()); 110 /* Map the reset vector (in headsmp-scu.S) */
111 __raw_writel(__pa(shmobile_secondary_vector_scu), AVECR);
164 112
165 /* Map the reset vector (in headsmp.S) */ 113 /* enable cache coherency on booting CPU */
166 __raw_writel(__pa(shmobile_secondary_vector), AVECR); 114 scu_power_mode(shmobile_scu_base, SCU_PM_NORMAL);
167
168 /* enable cache coherency on CPU0 */
169 modify_scu_cpu_psr(0, 3 << (cpu * 8));
170 115
171 r8a7779_pm_init(); 116 r8a7779_pm_init();
172 117
@@ -178,10 +123,60 @@ static void __init r8a7779_smp_prepare_cpus(unsigned int max_cpus)
178 123
179static void __init r8a7779_smp_init_cpus(void) 124static void __init r8a7779_smp_init_cpus(void)
180{ 125{
181 unsigned int ncores = r8a7779_get_core_count(); 126 /* setup r8a7779 specific SCU base */
127 shmobile_scu_base = IOMEM(R8A7779_SCU_BASE);
128
129 shmobile_smp_init_cpus(scu_get_core_count(shmobile_scu_base));
130}
182 131
183 shmobile_smp_init_cpus(ncores); 132#ifdef CONFIG_HOTPLUG_CPU
133static int r8a7779_scu_psr_core_disabled(int cpu)
134{
135 unsigned long mask = 3 << (cpu * 8);
136
137 if ((__raw_readl(shmobile_scu_base + 8) & mask) == mask)
138 return 1;
139
140 return 0;
141}
142
143static int r8a7779_cpu_kill(unsigned int cpu)
144{
145 int k;
146
147 /* this function is running on another CPU than the offline target,
148 * here we need wait for shutdown code in platform_cpu_die() to
149 * finish before asking SoC-specific code to power off the CPU core.
150 */
151 for (k = 0; k < 1000; k++) {
152 if (r8a7779_scu_psr_core_disabled(cpu))
153 return r8a7779_platform_cpu_kill(cpu);
154
155 mdelay(1);
156 }
157
158 return 0;
159}
160
161static void r8a7779_cpu_die(unsigned int cpu)
162{
163 dsb();
164 flush_cache_all();
165
166 /* disable cache coherency */
167 scu_power_mode(shmobile_scu_base, SCU_PM_POWEROFF);
168
169 /* Endless loop until power off from r8a7779_cpu_kill() */
170 while (1)
171 cpu_do_idle();
172}
173
174static int r8a7779_cpu_disable(unsigned int cpu)
175{
176 /* only CPU1->3 have power domains, do not allow hotplug of CPU0 */
177 return cpu == 0 ? -EPERM : 0;
184} 178}
179#endif /* CONFIG_HOTPLUG_CPU */
185 180
186struct smp_operations r8a7779_smp_ops __initdata = { 181struct smp_operations r8a7779_smp_ops __initdata = {
187 .smp_init_cpus = r8a7779_smp_init_cpus, 182 .smp_init_cpus = r8a7779_smp_init_cpus,
@@ -190,7 +185,7 @@ struct smp_operations r8a7779_smp_ops __initdata = {
190 .smp_boot_secondary = r8a7779_boot_secondary, 185 .smp_boot_secondary = r8a7779_boot_secondary,
191#ifdef CONFIG_HOTPLUG_CPU 186#ifdef CONFIG_HOTPLUG_CPU
192 .cpu_kill = r8a7779_cpu_kill, 187 .cpu_kill = r8a7779_cpu_kill,
193 .cpu_die = shmobile_cpu_die, 188 .cpu_die = r8a7779_cpu_die,
194 .cpu_disable = shmobile_cpu_disable, 189 .cpu_disable = r8a7779_cpu_disable,
195#endif 190#endif
196}; 191};
diff --git a/arch/arm/mach-shmobile/smp-sh73a0.c b/arch/arm/mach-shmobile/smp-sh73a0.c
index acb46a94ccdf..5ae502b16437 100644
--- a/arch/arm/mach-shmobile/smp-sh73a0.c
+++ b/arch/arm/mach-shmobile/smp-sh73a0.c
@@ -39,26 +39,16 @@
39 39
40#define PSTR_SHUTDOWN_MODE 3 40#define PSTR_SHUTDOWN_MODE 3
41 41
42static void __iomem *scu_base_addr(void) 42#define SH73A0_SCU_BASE 0xf0000000
43{
44 return (void __iomem *)0xf0000000;
45}
46 43
47#ifdef CONFIG_HAVE_ARM_TWD 44#ifdef CONFIG_HAVE_ARM_TWD
48static DEFINE_TWD_LOCAL_TIMER(twd_local_timer, 0xf0000600, 29); 45static DEFINE_TWD_LOCAL_TIMER(twd_local_timer, SH73A0_SCU_BASE + 0x600, 29);
49void __init sh73a0_register_twd(void) 46void __init sh73a0_register_twd(void)
50{ 47{
51 twd_local_timer_register(&twd_local_timer); 48 twd_local_timer_register(&twd_local_timer);
52} 49}
53#endif 50#endif
54 51
55static unsigned int __init sh73a0_get_core_count(void)
56{
57 void __iomem *scu_base = scu_base_addr();
58
59 return scu_get_core_count(scu_base);
60}
61
62static void __cpuinit sh73a0_secondary_init(unsigned int cpu) 52static void __cpuinit sh73a0_secondary_init(unsigned int cpu)
63{ 53{
64 gic_secondary_init(0); 54 gic_secondary_init(0);
@@ -78,21 +68,22 @@ static int __cpuinit sh73a0_boot_secondary(unsigned int cpu, struct task_struct
78 68
79static void __init sh73a0_smp_prepare_cpus(unsigned int max_cpus) 69static void __init sh73a0_smp_prepare_cpus(unsigned int max_cpus)
80{ 70{
81 scu_enable(scu_base_addr()); 71 scu_enable(shmobile_scu_base);
82 72
83 /* Map the reset vector (in headsmp-sh73a0.S) */ 73 /* Map the reset vector (in headsmp-scu.S) */
84 __raw_writel(0, APARMBAREA); /* 4k */ 74 __raw_writel(0, APARMBAREA); /* 4k */
85 __raw_writel(__pa(sh73a0_secondary_vector), SBAR); 75 __raw_writel(__pa(shmobile_secondary_vector_scu), SBAR);
86 76
87 /* enable cache coherency on booting CPU */ 77 /* enable cache coherency on booting CPU */
88 scu_power_mode(scu_base_addr(), SCU_PM_NORMAL); 78 scu_power_mode(shmobile_scu_base, SCU_PM_NORMAL);
89} 79}
90 80
91static void __init sh73a0_smp_init_cpus(void) 81static void __init sh73a0_smp_init_cpus(void)
92{ 82{
93 unsigned int ncores = sh73a0_get_core_count(); 83 /* setup sh73a0 specific SCU base */
84 shmobile_scu_base = IOMEM(SH73A0_SCU_BASE);
94 85
95 shmobile_smp_init_cpus(ncores); 86 shmobile_smp_init_cpus(scu_get_core_count(shmobile_scu_base));
96} 87}
97 88
98#ifdef CONFIG_HOTPLUG_CPU 89#ifdef CONFIG_HOTPLUG_CPU
@@ -128,11 +119,16 @@ static void sh73a0_cpu_die(unsigned int cpu)
128 flush_cache_all(); 119 flush_cache_all();
129 120
130 /* Set power off mode. This takes the CPU out of the MP cluster */ 121 /* Set power off mode. This takes the CPU out of the MP cluster */
131 scu_power_mode(scu_base_addr(), SCU_PM_POWEROFF); 122 scu_power_mode(shmobile_scu_base, SCU_PM_POWEROFF);
132 123
133 /* Enter shutdown mode */ 124 /* Enter shutdown mode */
134 cpu_do_idle(); 125 cpu_do_idle();
135} 126}
127
128static int sh73a0_cpu_disable(unsigned int cpu)
129{
130 return 0; /* CPU0 and CPU1 supported */
131}
136#endif /* CONFIG_HOTPLUG_CPU */ 132#endif /* CONFIG_HOTPLUG_CPU */
137 133
138struct smp_operations sh73a0_smp_ops __initdata = { 134struct smp_operations sh73a0_smp_ops __initdata = {
@@ -143,6 +139,6 @@ struct smp_operations sh73a0_smp_ops __initdata = {
143#ifdef CONFIG_HOTPLUG_CPU 139#ifdef CONFIG_HOTPLUG_CPU
144 .cpu_kill = sh73a0_cpu_kill, 140 .cpu_kill = sh73a0_cpu_kill,
145 .cpu_die = sh73a0_cpu_die, 141 .cpu_die = sh73a0_cpu_die,
146 .cpu_disable = shmobile_cpu_disable_any, 142 .cpu_disable = sh73a0_cpu_disable,
147#endif 143#endif
148}; 144};
diff --git a/arch/arm/mach-shmobile/timer.c b/arch/arm/mach-shmobile/timer.c
index 3d16d4dff01b..f321dbeb2379 100644
--- a/arch/arm/mach-shmobile/timer.c
+++ b/arch/arm/mach-shmobile/timer.c
@@ -19,10 +19,8 @@
19 * 19 *
20 */ 20 */
21#include <linux/platform_device.h> 21#include <linux/platform_device.h>
22#include <linux/clocksource.h>
22#include <linux/delay.h> 23#include <linux/delay.h>
23#include <asm/arch_timer.h>
24#include <asm/mach/time.h>
25#include <asm/smp_twd.h>
26 24
27void __init shmobile_setup_delay(unsigned int max_cpu_core_mhz, 25void __init shmobile_setup_delay(unsigned int max_cpu_core_mhz,
28 unsigned int mult, unsigned int div) 26 unsigned int mult, unsigned int div)
@@ -63,6 +61,5 @@ void __init shmobile_earlytimer_init(void)
63 61
64void __init shmobile_timer_init(void) 62void __init shmobile_timer_init(void)
65{ 63{
66 arch_timer_of_register(); 64 clocksource_of_init();
67 arch_timer_sched_clock_init();
68} 65}
diff --git a/arch/arm/mach-spear/spear13xx.c b/arch/arm/mach-spear/spear13xx.c
index 3975916666a0..3621599c38ad 100644
--- a/arch/arm/mach-spear/spear13xx.c
+++ b/arch/arm/mach-spear/spear13xx.c
@@ -15,13 +15,13 @@
15 15
16#include <linux/amba/pl022.h> 16#include <linux/amba/pl022.h>
17#include <linux/clk.h> 17#include <linux/clk.h>
18#include <linux/clocksource.h>
18#include <linux/err.h> 19#include <linux/err.h>
19#include <linux/of.h> 20#include <linux/of.h>
20#include <asm/hardware/cache-l2x0.h> 21#include <asm/hardware/cache-l2x0.h>
21#include <asm/mach/map.h> 22#include <asm/mach/map.h>
22#include <asm/smp_twd.h>
23#include "generic.h"
24#include <mach/spear.h> 23#include <mach/spear.h>
24#include "generic.h"
25 25
26void __init spear13xx_l2x0_init(void) 26void __init spear13xx_l2x0_init(void)
27{ 27{
@@ -122,5 +122,5 @@ void __init spear13xx_timer_init(void)
122 clk_put(pclk); 122 clk_put(pclk);
123 123
124 spear_setup_of_timer(); 124 spear_setup_of_timer();
125 twd_local_timer_of_register(); 125 clocksource_of_init();
126} 126}
diff --git a/arch/arm/mach-tegra/Makefile b/arch/arm/mach-tegra/Makefile
index f6b46ae2b7f8..e40326d0e29f 100644
--- a/arch/arm/mach-tegra/Makefile
+++ b/arch/arm/mach-tegra/Makefile
@@ -10,6 +10,7 @@ obj-y += pm.o
10obj-y += reset.o 10obj-y += reset.o
11obj-y += reset-handler.o 11obj-y += reset-handler.o
12obj-y += sleep.o 12obj-y += sleep.o
13obj-y += tegra.o
13obj-$(CONFIG_CPU_IDLE) += cpuidle.o 14obj-$(CONFIG_CPU_IDLE) += cpuidle.o
14obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += tegra20_speedo.o 15obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += tegra20_speedo.o
15obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += tegra2_emc.o 16obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += tegra2_emc.o
@@ -27,9 +28,7 @@ obj-$(CONFIG_HOTPLUG_CPU) += hotplug.o
27obj-$(CONFIG_CPU_FREQ) += cpu-tegra.o 28obj-$(CONFIG_CPU_FREQ) += cpu-tegra.o
28obj-$(CONFIG_TEGRA_PCI) += pcie.o 29obj-$(CONFIG_TEGRA_PCI) += pcie.o
29 30
30obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += board-dt-tegra20.o 31obj-$(CONFIG_ARCH_TEGRA_114_SOC) += tegra114_speedo.o
31obj-$(CONFIG_ARCH_TEGRA_3x_SOC) += board-dt-tegra30.o
32obj-$(CONFIG_ARCH_TEGRA_114_SOC) += board-dt-tegra114.o
33ifeq ($(CONFIG_CPU_IDLE),y) 32ifeq ($(CONFIG_CPU_IDLE),y)
34obj-$(CONFIG_ARCH_TEGRA_114_SOC) += cpuidle-tegra114.o 33obj-$(CONFIG_ARCH_TEGRA_114_SOC) += cpuidle-tegra114.o
35endif 34endif
diff --git a/arch/arm/mach-tegra/board-dt-tegra114.c b/arch/arm/mach-tegra/board-dt-tegra114.c
deleted file mode 100644
index 085d63637b62..000000000000
--- a/arch/arm/mach-tegra/board-dt-tegra114.c
+++ /dev/null
@@ -1,46 +0,0 @@
1/*
2 * NVIDIA Tegra114 device tree board support
3 *
4 * Copyright (C) 2013 NVIDIA Corporation
5 *
6 * This software is licensed under the terms of the GNU General Public
7 * License version 2, as published by the Free Software Foundation, and
8 * may be copied, distributed, and modified under those terms.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 */
16
17#include <linux/of.h>
18#include <linux/of_platform.h>
19#include <linux/clocksource.h>
20
21#include <asm/mach/arch.h>
22
23#include "board.h"
24#include "common.h"
25
26static void __init tegra114_dt_init(void)
27{
28 of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
29}
30
31static const char * const tegra114_dt_board_compat[] = {
32 "nvidia,tegra114",
33 NULL,
34};
35
36DT_MACHINE_START(TEGRA114_DT, "NVIDIA Tegra114 (Flattened Device Tree)")
37 .smp = smp_ops(tegra_smp_ops),
38 .map_io = tegra_map_common_io,
39 .init_early = tegra114_init_early,
40 .init_irq = tegra_dt_init_irq,
41 .init_time = clocksource_of_init,
42 .init_machine = tegra114_dt_init,
43 .init_late = tegra_init_late,
44 .restart = tegra_assert_system_reset,
45 .dt_compat = tegra114_dt_board_compat,
46MACHINE_END
diff --git a/arch/arm/mach-tegra/board-dt-tegra30.c b/arch/arm/mach-tegra/board-dt-tegra30.c
deleted file mode 100644
index bf68567e549d..000000000000
--- a/arch/arm/mach-tegra/board-dt-tegra30.c
+++ /dev/null
@@ -1,60 +0,0 @@
1/*
2 * arch/arm/mach-tegra/board-dt-tegra30.c
3 *
4 * NVIDIA Tegra30 device tree board support
5 *
6 * Copyright (C) 2011 NVIDIA Corporation
7 *
8 * Derived from:
9 *
10 * arch/arm/mach-tegra/board-dt-tegra20.c
11 *
12 * Copyright (C) 2010 Secret Lab Technologies, Ltd.
13 * Copyright (C) 2010 Google, Inc.
14 *
15 * This software is licensed under the terms of the GNU General Public
16 * License version 2, as published by the Free Software Foundation, and
17 * may be copied, distributed, and modified under those terms.
18 *
19 * This program is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22 * GNU General Public License for more details.
23 *
24 */
25
26#include <linux/clocksource.h>
27#include <linux/kernel.h>
28#include <linux/of.h>
29#include <linux/of_address.h>
30#include <linux/of_fdt.h>
31#include <linux/of_irq.h>
32#include <linux/of_platform.h>
33
34#include <asm/mach/arch.h>
35
36#include "board.h"
37#include "common.h"
38#include "iomap.h"
39
40static void __init tegra30_dt_init(void)
41{
42 of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
43}
44
45static const char *tegra30_dt_board_compat[] = {
46 "nvidia,tegra30",
47 NULL
48};
49
50DT_MACHINE_START(TEGRA30_DT, "NVIDIA Tegra30 (Flattened Device Tree)")
51 .smp = smp_ops(tegra_smp_ops),
52 .map_io = tegra_map_common_io,
53 .init_early = tegra30_init_early,
54 .init_irq = tegra_dt_init_irq,
55 .init_time = clocksource_of_init,
56 .init_machine = tegra30_dt_init,
57 .init_late = tegra_init_late,
58 .restart = tegra_assert_system_reset,
59 .dt_compat = tegra30_dt_board_compat,
60MACHINE_END
diff --git a/arch/arm/mach-tegra/board-harmony-pcie.c b/arch/arm/mach-tegra/board-harmony-pcie.c
index 3cdc1bb8254c..035b240b9e15 100644
--- a/arch/arm/mach-tegra/board-harmony-pcie.c
+++ b/arch/arm/mach-tegra/board-harmony-pcie.c
@@ -56,13 +56,17 @@ int __init harmony_pcie_init(void)
56 gpio_direction_output(en_vdd_1v05, 1); 56 gpio_direction_output(en_vdd_1v05, 1);
57 57
58 regulator = regulator_get(NULL, "vdd_ldo0,vddio_pex_clk"); 58 regulator = regulator_get(NULL, "vdd_ldo0,vddio_pex_clk");
59 if (IS_ERR_OR_NULL(regulator)) { 59 if (IS_ERR(regulator)) {
60 pr_err("%s: regulator_get failed: %d\n", __func__, 60 err = PTR_ERR(regulator);
61 (int)PTR_ERR(regulator)); 61 pr_err("%s: regulator_get failed: %d\n", __func__, err);
62 goto err_reg; 62 goto err_reg;
63 } 63 }
64 64
65 regulator_enable(regulator); 65 err = regulator_enable(regulator);
66 if (err) {
67 pr_err("%s: regulator_enable failed: %d\n", __func__, err);
68 goto err_en;
69 }
66 70
67 err = tegra_pcie_init(true, true); 71 err = tegra_pcie_init(true, true);
68 if (err) { 72 if (err) {
@@ -74,6 +78,7 @@ int __init harmony_pcie_init(void)
74 78
75err_pcie: 79err_pcie:
76 regulator_disable(regulator); 80 regulator_disable(regulator);
81err_en:
77 regulator_put(regulator); 82 regulator_put(regulator);
78err_reg: 83err_reg:
79 gpio_free(en_vdd_1v05); 84 gpio_free(en_vdd_1v05);
diff --git a/arch/arm/mach-tegra/board.h b/arch/arm/mach-tegra/board.h
index 86851c81a350..60431de585ca 100644
--- a/arch/arm/mach-tegra/board.h
+++ b/arch/arm/mach-tegra/board.h
@@ -26,9 +26,7 @@
26 26
27void tegra_assert_system_reset(char mode, const char *cmd); 27void tegra_assert_system_reset(char mode, const char *cmd);
28 28
29void __init tegra20_init_early(void); 29void __init tegra_init_early(void);
30void __init tegra30_init_early(void);
31void __init tegra114_init_early(void);
32void __init tegra_map_common_io(void); 30void __init tegra_map_common_io(void);
33void __init tegra_init_irq(void); 31void __init tegra_init_irq(void);
34void __init tegra_dt_init_irq(void); 32void __init tegra_dt_init_irq(void);
diff --git a/arch/arm/mach-tegra/common.c b/arch/arm/mach-tegra/common.c
index 5449a3f2977b..eb1f3c8c74cc 100644
--- a/arch/arm/mach-tegra/common.c
+++ b/arch/arm/mach-tegra/common.c
@@ -33,6 +33,7 @@
33#include "common.h" 33#include "common.h"
34#include "fuse.h" 34#include "fuse.h"
35#include "iomap.h" 35#include "iomap.h"
36#include "irq.h"
36#include "pmc.h" 37#include "pmc.h"
37#include "apbio.h" 38#include "apbio.h"
38#include "sleep.h" 39#include "sleep.h"
@@ -61,8 +62,10 @@ u32 tegra_uart_config[4] = {
61void __init tegra_dt_init_irq(void) 62void __init tegra_dt_init_irq(void)
62{ 63{
63 tegra_clocks_init(); 64 tegra_clocks_init();
65 tegra_pmc_init();
64 tegra_init_irq(); 66 tegra_init_irq();
65 irqchip_init(); 67 irqchip_init();
68 tegra_legacy_irq_syscore_init();
66} 69}
67#endif 70#endif
68 71
@@ -94,40 +97,18 @@ static void __init tegra_init_cache(void)
94 97
95} 98}
96 99
97static void __init tegra_init_early(void) 100void __init tegra_init_early(void)
98{ 101{
99 tegra_cpu_reset_handler_init(); 102 tegra_cpu_reset_handler_init();
100 tegra_apb_io_init(); 103 tegra_apb_io_init();
101 tegra_init_fuse(); 104 tegra_init_fuse();
102 tegra_init_cache(); 105 tegra_init_cache();
103 tegra_pmc_init();
104 tegra_powergate_init(); 106 tegra_powergate_init();
107 tegra_hotplug_init();
105} 108}
106 109
107#ifdef CONFIG_ARCH_TEGRA_2x_SOC
108void __init tegra20_init_early(void)
109{
110 tegra_init_early();
111 tegra20_hotplug_init();
112}
113#endif
114
115#ifdef CONFIG_ARCH_TEGRA_3x_SOC
116void __init tegra30_init_early(void)
117{
118 tegra_init_early();
119 tegra30_hotplug_init();
120}
121#endif
122
123#ifdef CONFIG_ARCH_TEGRA_114_SOC
124void __init tegra114_init_early(void)
125{
126 tegra_init_early();
127}
128#endif
129
130void __init tegra_init_late(void) 110void __init tegra_init_late(void)
131{ 111{
112 tegra_init_suspend();
132 tegra_powergate_debugfs_init(); 113 tegra_powergate_debugfs_init();
133} 114}
diff --git a/arch/arm/mach-tegra/cpuidle-tegra20.c b/arch/arm/mach-tegra/cpuidle-tegra20.c
index 825ced4f7a40..8bbbdebed882 100644
--- a/arch/arm/mach-tegra/cpuidle-tegra20.c
+++ b/arch/arm/mach-tegra/cpuidle-tegra20.c
@@ -130,10 +130,6 @@ static bool tegra20_cpu_cluster_power_down(struct cpuidle_device *dev,
130 struct cpuidle_driver *drv, 130 struct cpuidle_driver *drv,
131 int index) 131 int index)
132{ 132{
133 struct cpuidle_state *state = &drv->states[index];
134 u32 cpu_on_time = state->exit_latency;
135 u32 cpu_off_time = state->target_residency - state->exit_latency;
136
137 while (tegra20_cpu_is_resettable_soon()) 133 while (tegra20_cpu_is_resettable_soon())
138 cpu_relax(); 134 cpu_relax();
139 135
@@ -142,7 +138,7 @@ static bool tegra20_cpu_cluster_power_down(struct cpuidle_device *dev,
142 138
143 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_ENTER, &dev->cpu); 139 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_ENTER, &dev->cpu);
144 140
145 tegra_idle_lp2_last(cpu_on_time, cpu_off_time); 141 tegra_idle_lp2_last();
146 142
147 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_EXIT, &dev->cpu); 143 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_EXIT, &dev->cpu);
148 144
diff --git a/arch/arm/mach-tegra/cpuidle-tegra30.c b/arch/arm/mach-tegra/cpuidle-tegra30.c
index 8b50cf4ddd6f..c0931c8bb3e5 100644
--- a/arch/arm/mach-tegra/cpuidle-tegra30.c
+++ b/arch/arm/mach-tegra/cpuidle-tegra30.c
@@ -72,10 +72,6 @@ static bool tegra30_cpu_cluster_power_down(struct cpuidle_device *dev,
72 struct cpuidle_driver *drv, 72 struct cpuidle_driver *drv,
73 int index) 73 int index)
74{ 74{
75 struct cpuidle_state *state = &drv->states[index];
76 u32 cpu_on_time = state->exit_latency;
77 u32 cpu_off_time = state->target_residency - state->exit_latency;
78
79 /* All CPUs entering LP2 is not working. 75 /* All CPUs entering LP2 is not working.
80 * Don't let CPU0 enter LP2 when any secondary CPU is online. 76 * Don't let CPU0 enter LP2 when any secondary CPU is online.
81 */ 77 */
@@ -86,7 +82,7 @@ static bool tegra30_cpu_cluster_power_down(struct cpuidle_device *dev,
86 82
87 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_ENTER, &dev->cpu); 83 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_ENTER, &dev->cpu);
88 84
89 tegra_idle_lp2_last(cpu_on_time, cpu_off_time); 85 tegra_idle_lp2_last();
90 86
91 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_EXIT, &dev->cpu); 87 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_EXIT, &dev->cpu);
92 88
@@ -102,12 +98,8 @@ static bool tegra30_cpu_core_power_down(struct cpuidle_device *dev,
102 98
103 smp_wmb(); 99 smp_wmb();
104 100
105 save_cpu_arch_register();
106
107 cpu_suspend(0, tegra30_sleep_cpu_secondary_finish); 101 cpu_suspend(0, tegra30_sleep_cpu_secondary_finish);
108 102
109 restore_cpu_arch_register();
110
111 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_EXIT, &dev->cpu); 103 clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_EXIT, &dev->cpu);
112 104
113 return true; 105 return true;
diff --git a/arch/arm/mach-tegra/fuse.c b/arch/arm/mach-tegra/fuse.c
index f7db0782a6b6..e035cd284a6e 100644
--- a/arch/arm/mach-tegra/fuse.c
+++ b/arch/arm/mach-tegra/fuse.c
@@ -2,6 +2,7 @@
2 * arch/arm/mach-tegra/fuse.c 2 * arch/arm/mach-tegra/fuse.c
3 * 3 *
4 * Copyright (C) 2010 Google, Inc. 4 * Copyright (C) 2010 Google, Inc.
5 * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved.
5 * 6 *
6 * Author: 7 * Author:
7 * Colin Cross <ccross@android.com> 8 * Colin Cross <ccross@android.com>
@@ -137,6 +138,9 @@ void tegra_init_fuse(void)
137 tegra_fuse_spare_bit = TEGRA30_FUSE_SPARE_BIT; 138 tegra_fuse_spare_bit = TEGRA30_FUSE_SPARE_BIT;
138 tegra_init_speedo_data = &tegra30_init_speedo_data; 139 tegra_init_speedo_data = &tegra30_init_speedo_data;
139 break; 140 break;
141 case TEGRA114:
142 tegra_init_speedo_data = &tegra114_init_speedo_data;
143 break;
140 default: 144 default:
141 pr_warn("Tegra: unknown chip id %d\n", tegra_chip_id); 145 pr_warn("Tegra: unknown chip id %d\n", tegra_chip_id);
142 tegra_fuse_spare_bit = TEGRA20_FUSE_SPARE_BIT; 146 tegra_fuse_spare_bit = TEGRA20_FUSE_SPARE_BIT;
diff --git a/arch/arm/mach-tegra/fuse.h b/arch/arm/mach-tegra/fuse.h
index da78434678c7..aacc00d05980 100644
--- a/arch/arm/mach-tegra/fuse.h
+++ b/arch/arm/mach-tegra/fuse.h
@@ -1,5 +1,6 @@
1/* 1/*
2 * Copyright (C) 2010 Google, Inc. 2 * Copyright (C) 2010 Google, Inc.
3 * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved.
3 * 4 *
4 * Author: 5 * Author:
5 * Colin Cross <ccross@android.com> 6 * Colin Cross <ccross@android.com>
@@ -66,4 +67,10 @@ void tegra30_init_speedo_data(void);
66static inline void tegra30_init_speedo_data(void) {} 67static inline void tegra30_init_speedo_data(void) {}
67#endif 68#endif
68 69
70#ifdef CONFIG_ARCH_TEGRA_114_SOC
71void tegra114_init_speedo_data(void);
72#else
73static inline void tegra114_init_speedo_data(void) {}
74#endif
75
69#endif 76#endif
diff --git a/arch/arm/mach-tegra/headsmp.S b/arch/arm/mach-tegra/headsmp.S
index fd473f2b4c3d..045c16f2dd51 100644
--- a/arch/arm/mach-tegra/headsmp.S
+++ b/arch/arm/mach-tegra/headsmp.S
@@ -7,8 +7,5 @@
7 7
8ENTRY(tegra_secondary_startup) 8ENTRY(tegra_secondary_startup)
9 bl v7_invalidate_l1 9 bl v7_invalidate_l1
10 /* Enable coresight */
11 mov32 r0, 0xC5ACCE55
12 mcr p14, 0, r0, c7, c12, 6
13 b secondary_startup 10 b secondary_startup
14ENDPROC(tegra_secondary_startup) 11ENDPROC(tegra_secondary_startup)
diff --git a/arch/arm/mach-tegra/hotplug.c b/arch/arm/mach-tegra/hotplug.c
index a599f6e36dea..8da9f78475da 100644
--- a/arch/arm/mach-tegra/hotplug.c
+++ b/arch/arm/mach-tegra/hotplug.c
@@ -1,8 +1,7 @@
1/* 1/*
2 *
3 * Copyright (C) 2002 ARM Ltd. 2 * Copyright (C) 2002 ARM Ltd.
4 * All Rights Reserved 3 * All Rights Reserved
5 * Copyright (c) 2010, 2012 NVIDIA Corporation. All rights reserved. 4 * Copyright (c) 2010, 2012-2013, NVIDIA Corporation. All rights reserved.
6 * 5 *
7 * This program is free software; you can redistribute it and/or modify 6 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as 7 * it under the terms of the GNU General Public License version 2 as
@@ -15,6 +14,7 @@
15#include <asm/cacheflush.h> 14#include <asm/cacheflush.h>
16#include <asm/smp_plat.h> 15#include <asm/smp_plat.h>
17 16
17#include "fuse.h"
18#include "sleep.h" 18#include "sleep.h"
19 19
20static void (*tegra_hotplug_shutdown)(void); 20static void (*tegra_hotplug_shutdown)(void);
@@ -56,18 +56,13 @@ int tegra_cpu_disable(unsigned int cpu)
56 return cpu == 0 ? -EPERM : 0; 56 return cpu == 0 ? -EPERM : 0;
57} 57}
58 58
59#ifdef CONFIG_ARCH_TEGRA_2x_SOC 59void __init tegra_hotplug_init(void)
60extern void tegra20_hotplug_shutdown(void);
61void __init tegra20_hotplug_init(void)
62{ 60{
63 tegra_hotplug_shutdown = tegra20_hotplug_shutdown; 61 if (!IS_ENABLED(CONFIG_HOTPLUG_CPU))
64} 62 return;
65#endif
66 63
67#ifdef CONFIG_ARCH_TEGRA_3x_SOC 64 if (IS_ENABLED(CONFIG_ARCH_TEGRA_2x_SOC) && tegra_chip_id == TEGRA20)
68extern void tegra30_hotplug_shutdown(void); 65 tegra_hotplug_shutdown = tegra20_hotplug_shutdown;
69void __init tegra30_hotplug_init(void) 66 if (IS_ENABLED(CONFIG_ARCH_TEGRA_3x_SOC) && tegra_chip_id == TEGRA30)
70{ 67 tegra_hotplug_shutdown = tegra30_hotplug_shutdown;
71 tegra_hotplug_shutdown = tegra30_hotplug_shutdown;
72} 68}
73#endif
diff --git a/arch/arm/mach-tegra/irq.c b/arch/arm/mach-tegra/irq.c
index 1952e82797cc..0de4eed1493d 100644
--- a/arch/arm/mach-tegra/irq.c
+++ b/arch/arm/mach-tegra/irq.c
@@ -4,7 +4,7 @@
4 * Author: 4 * Author:
5 * Colin Cross <ccross@android.com> 5 * Colin Cross <ccross@android.com>
6 * 6 *
7 * Copyright (C) 2010, NVIDIA Corporation 7 * Copyright (C) 2010,2013, NVIDIA Corporation
8 * 8 *
9 * This software is licensed under the terms of the GNU General Public 9 * This software is licensed under the terms of the GNU General Public
10 * License version 2, as published by the Free Software Foundation, and 10 * License version 2, as published by the Free Software Foundation, and
@@ -23,6 +23,7 @@
23#include <linux/io.h> 23#include <linux/io.h>
24#include <linux/of.h> 24#include <linux/of.h>
25#include <linux/irqchip/arm-gic.h> 25#include <linux/irqchip/arm-gic.h>
26#include <linux/syscore_ops.h>
26 27
27#include "board.h" 28#include "board.h"
28#include "iomap.h" 29#include "iomap.h"
@@ -43,6 +44,7 @@
43#define ICTLR_COP_IEP_CLASS 0x3c 44#define ICTLR_COP_IEP_CLASS 0x3c
44 45
45#define FIRST_LEGACY_IRQ 32 46#define FIRST_LEGACY_IRQ 32
47#define TEGRA_MAX_NUM_ICTLRS 5
46 48
47#define SGI_MASK 0xFFFF 49#define SGI_MASK 0xFFFF
48 50
@@ -56,6 +58,15 @@ static void __iomem *ictlr_reg_base[] = {
56 IO_ADDRESS(TEGRA_QUINARY_ICTLR_BASE), 58 IO_ADDRESS(TEGRA_QUINARY_ICTLR_BASE),
57}; 59};
58 60
61#ifdef CONFIG_PM_SLEEP
62static u32 cop_ier[TEGRA_MAX_NUM_ICTLRS];
63static u32 cop_iep[TEGRA_MAX_NUM_ICTLRS];
64static u32 cpu_ier[TEGRA_MAX_NUM_ICTLRS];
65static u32 cpu_iep[TEGRA_MAX_NUM_ICTLRS];
66
67static u32 ictlr_wake_mask[TEGRA_MAX_NUM_ICTLRS];
68#endif
69
59bool tegra_pending_sgi(void) 70bool tegra_pending_sgi(void)
60{ 71{
61 u32 pending_set; 72 u32 pending_set;
@@ -125,6 +136,87 @@ static int tegra_retrigger(struct irq_data *d)
125 return 1; 136 return 1;
126} 137}
127 138
139#ifdef CONFIG_PM_SLEEP
140static int tegra_set_wake(struct irq_data *d, unsigned int enable)
141{
142 u32 irq = d->irq;
143 u32 index, mask;
144
145 if (irq < FIRST_LEGACY_IRQ ||
146 irq >= FIRST_LEGACY_IRQ + num_ictlrs * 32)
147 return -EINVAL;
148
149 index = ((irq - FIRST_LEGACY_IRQ) / 32);
150 mask = BIT((irq - FIRST_LEGACY_IRQ) % 32);
151 if (enable)
152 ictlr_wake_mask[index] |= mask;
153 else
154 ictlr_wake_mask[index] &= ~mask;
155
156 return 0;
157}
158
159static int tegra_legacy_irq_suspend(void)
160{
161 unsigned long flags;
162 int i;
163
164 local_irq_save(flags);
165 for (i = 0; i < num_ictlrs; i++) {
166 void __iomem *ictlr = ictlr_reg_base[i];
167 /* Save interrupt state */
168 cpu_ier[i] = readl_relaxed(ictlr + ICTLR_CPU_IER);
169 cpu_iep[i] = readl_relaxed(ictlr + ICTLR_CPU_IEP_CLASS);
170 cop_ier[i] = readl_relaxed(ictlr + ICTLR_COP_IER);
171 cop_iep[i] = readl_relaxed(ictlr + ICTLR_COP_IEP_CLASS);
172
173 /* Disable COP interrupts */
174 writel_relaxed(~0ul, ictlr + ICTLR_COP_IER_CLR);
175
176 /* Disable CPU interrupts */
177 writel_relaxed(~0ul, ictlr + ICTLR_CPU_IER_CLR);
178
179 /* Enable the wakeup sources of ictlr */
180 writel_relaxed(ictlr_wake_mask[i], ictlr + ICTLR_CPU_IER_SET);
181 }
182 local_irq_restore(flags);
183
184 return 0;
185}
186
187static void tegra_legacy_irq_resume(void)
188{
189 unsigned long flags;
190 int i;
191
192 local_irq_save(flags);
193 for (i = 0; i < num_ictlrs; i++) {
194 void __iomem *ictlr = ictlr_reg_base[i];
195 writel_relaxed(cpu_iep[i], ictlr + ICTLR_CPU_IEP_CLASS);
196 writel_relaxed(~0ul, ictlr + ICTLR_CPU_IER_CLR);
197 writel_relaxed(cpu_ier[i], ictlr + ICTLR_CPU_IER_SET);
198 writel_relaxed(cop_iep[i], ictlr + ICTLR_COP_IEP_CLASS);
199 writel_relaxed(~0ul, ictlr + ICTLR_COP_IER_CLR);
200 writel_relaxed(cop_ier[i], ictlr + ICTLR_COP_IER_SET);
201 }
202 local_irq_restore(flags);
203}
204
205static struct syscore_ops tegra_legacy_irq_syscore_ops = {
206 .suspend = tegra_legacy_irq_suspend,
207 .resume = tegra_legacy_irq_resume,
208};
209
210int tegra_legacy_irq_syscore_init(void)
211{
212 register_syscore_ops(&tegra_legacy_irq_syscore_ops);
213
214 return 0;
215}
216#else
217#define tegra_set_wake NULL
218#endif
219
128void __init tegra_init_irq(void) 220void __init tegra_init_irq(void)
129{ 221{
130 int i; 222 int i;
@@ -150,6 +242,8 @@ void __init tegra_init_irq(void)
150 gic_arch_extn.irq_mask = tegra_mask; 242 gic_arch_extn.irq_mask = tegra_mask;
151 gic_arch_extn.irq_unmask = tegra_unmask; 243 gic_arch_extn.irq_unmask = tegra_unmask;
152 gic_arch_extn.irq_retrigger = tegra_retrigger; 244 gic_arch_extn.irq_retrigger = tegra_retrigger;
245 gic_arch_extn.irq_set_wake = tegra_set_wake;
246 gic_arch_extn.flags = IRQCHIP_MASK_ON_SUSPEND;
153 247
154 /* 248 /*
155 * Check if there is a devicetree present, since the GIC will be 249 * Check if there is a devicetree present, since the GIC will be
diff --git a/arch/arm/mach-tegra/irq.h b/arch/arm/mach-tegra/irq.h
index 5142649bba05..bc05ce5613fb 100644
--- a/arch/arm/mach-tegra/irq.h
+++ b/arch/arm/mach-tegra/irq.h
@@ -19,4 +19,10 @@
19 19
20bool tegra_pending_sgi(void); 20bool tegra_pending_sgi(void);
21 21
22#ifdef CONFIG_PM_SLEEP
23int tegra_legacy_irq_syscore_init(void);
24#else
25static inline int tegra_legacy_irq_syscore_init(void) { return 0; }
26#endif
27
22#endif 28#endif
diff --git a/arch/arm/mach-tegra/platsmp.c b/arch/arm/mach-tegra/platsmp.c
index 2c6b3d55213b..516aab28fe34 100644
--- a/arch/arm/mach-tegra/platsmp.c
+++ b/arch/arm/mach-tegra/platsmp.c
@@ -26,22 +26,16 @@
26#include <asm/smp_scu.h> 26#include <asm/smp_scu.h>
27#include <asm/smp_plat.h> 27#include <asm/smp_plat.h>
28 28
29#include <mach/powergate.h>
30
31#include "fuse.h" 29#include "fuse.h"
32#include "flowctrl.h" 30#include "flowctrl.h"
33#include "reset.h" 31#include "reset.h"
32#include "pmc.h"
34 33
35#include "common.h" 34#include "common.h"
36#include "iomap.h" 35#include "iomap.h"
37 36
38extern void tegra_secondary_startup(void);
39
40static cpumask_t tegra_cpu_init_mask; 37static cpumask_t tegra_cpu_init_mask;
41 38
42#define EVP_CPU_RESET_VECTOR \
43 (IO_ADDRESS(TEGRA_EXCEPTION_VECTORS_BASE) + 0x100)
44
45static void __cpuinit tegra_secondary_init(unsigned int cpu) 39static void __cpuinit tegra_secondary_init(unsigned int cpu)
46{ 40{
47 /* 41 /*
@@ -54,25 +48,43 @@ static void __cpuinit tegra_secondary_init(unsigned int cpu)
54 cpumask_set_cpu(cpu, &tegra_cpu_init_mask); 48 cpumask_set_cpu(cpu, &tegra_cpu_init_mask);
55} 49}
56 50
57static int tegra20_power_up_cpu(unsigned int cpu) 51
52static int tegra20_boot_secondary(unsigned int cpu, struct task_struct *idle)
58{ 53{
59 /* Enable the CPU clock. */ 54 cpu = cpu_logical_map(cpu);
60 tegra_enable_cpu_clock(cpu); 55
56 /*
57 * Force the CPU into reset. The CPU must remain in reset when
58 * the flow controller state is cleared (which will cause the
59 * flow controller to stop driving reset if the CPU has been
60 * power-gated via the flow controller). This will have no
61 * effect on first boot of the CPU since it should already be
62 * in reset.
63 */
64 tegra_put_cpu_in_reset(cpu);
61 65
62 /* Clear flow controller CSR. */ 66 /*
63 flowctrl_write_cpu_csr(cpu, 0); 67 * Unhalt the CPU. If the flow controller was used to
68 * power-gate the CPU this will cause the flow controller to
69 * stop driving reset. The CPU will remain in reset because the
70 * clock and reset block is now driving reset.
71 */
72 flowctrl_write_cpu_halt(cpu, 0);
64 73
74 tegra_enable_cpu_clock(cpu);
75 flowctrl_write_cpu_csr(cpu, 0); /* Clear flow controller CSR. */
76 tegra_cpu_out_of_reset(cpu);
65 return 0; 77 return 0;
66} 78}
67 79
68static int tegra30_power_up_cpu(unsigned int cpu) 80static int tegra30_boot_secondary(unsigned int cpu, struct task_struct *idle)
69{ 81{
70 int ret, pwrgateid; 82 int ret;
71 unsigned long timeout; 83 unsigned long timeout;
72 84
73 pwrgateid = tegra_cpu_powergate_id(cpu); 85 cpu = cpu_logical_map(cpu);
74 if (pwrgateid < 0) 86 tegra_put_cpu_in_reset(cpu);
75 return pwrgateid; 87 flowctrl_write_cpu_halt(cpu, 0);
76 88
77 /* 89 /*
78 * The power up sequence of cold boot CPU and warm boot CPU 90 * The power up sequence of cold boot CPU and warm boot CPU
@@ -85,13 +97,13 @@ static int tegra30_power_up_cpu(unsigned int cpu)
85 * the IO clamps. 97 * the IO clamps.
86 * For cold boot CPU, do not wait. After the cold boot CPU be 98 * For cold boot CPU, do not wait. After the cold boot CPU be
87 * booted, it will run to tegra_secondary_init() and set 99 * booted, it will run to tegra_secondary_init() and set
88 * tegra_cpu_init_mask which influences what tegra30_power_up_cpu() 100 * tegra_cpu_init_mask which influences what tegra30_boot_secondary()
89 * next time around. 101 * next time around.
90 */ 102 */
91 if (cpumask_test_cpu(cpu, &tegra_cpu_init_mask)) { 103 if (cpumask_test_cpu(cpu, &tegra_cpu_init_mask)) {
92 timeout = jiffies + msecs_to_jiffies(50); 104 timeout = jiffies + msecs_to_jiffies(50);
93 do { 105 do {
94 if (!tegra_powergate_is_powered(pwrgateid)) 106 if (tegra_pmc_cpu_is_powered(cpu))
95 goto remove_clamps; 107 goto remove_clamps;
96 udelay(10); 108 udelay(10);
97 } while (time_before(jiffies, timeout)); 109 } while (time_before(jiffies, timeout));
@@ -103,14 +115,14 @@ static int tegra30_power_up_cpu(unsigned int cpu)
103 * be un-gated by un-toggling the power gate register 115 * be un-gated by un-toggling the power gate register
104 * manually. 116 * manually.
105 */ 117 */
106 if (!tegra_powergate_is_powered(pwrgateid)) { 118 if (!tegra_pmc_cpu_is_powered(cpu)) {
107 ret = tegra_powergate_power_on(pwrgateid); 119 ret = tegra_pmc_cpu_power_on(cpu);
108 if (ret) 120 if (ret)
109 return ret; 121 return ret;
110 122
111 /* Wait for the power to come up. */ 123 /* Wait for the power to come up. */
112 timeout = jiffies + msecs_to_jiffies(100); 124 timeout = jiffies + msecs_to_jiffies(100);
113 while (tegra_powergate_is_powered(pwrgateid)) { 125 while (tegra_pmc_cpu_is_powered(cpu)) {
114 if (time_after(jiffies, timeout)) 126 if (time_after(jiffies, timeout))
115 return -ETIMEDOUT; 127 return -ETIMEDOUT;
116 udelay(10); 128 udelay(10);
@@ -123,57 +135,34 @@ remove_clamps:
123 udelay(10); 135 udelay(10);
124 136
125 /* Remove I/O clamps. */ 137 /* Remove I/O clamps. */
126 ret = tegra_powergate_remove_clamping(pwrgateid); 138 ret = tegra_pmc_cpu_remove_clamping(cpu);
127 udelay(10); 139 if (ret)
140 return ret;
128 141
129 /* Clear flow controller CSR. */ 142 udelay(10);
130 flowctrl_write_cpu_csr(cpu, 0);
131 143
144 flowctrl_write_cpu_csr(cpu, 0); /* Clear flow controller CSR. */
145 tegra_cpu_out_of_reset(cpu);
132 return 0; 146 return 0;
133} 147}
134 148
135static int __cpuinit tegra_boot_secondary(unsigned int cpu, struct task_struct *idle) 149static int tegra114_boot_secondary(unsigned int cpu, struct task_struct *idle)
136{ 150{
137 int status;
138
139 cpu = cpu_logical_map(cpu); 151 cpu = cpu_logical_map(cpu);
152 return tegra_pmc_cpu_power_on(cpu);
153}
140 154
141 /* 155static int __cpuinit tegra_boot_secondary(unsigned int cpu,
142 * Force the CPU into reset. The CPU must remain in reset when the 156 struct task_struct *idle)
143 * flow controller state is cleared (which will cause the flow 157{
144 * controller to stop driving reset if the CPU has been power-gated 158 if (IS_ENABLED(CONFIG_ARCH_TEGRA_2x_SOC) && tegra_chip_id == TEGRA20)
145 * via the flow controller). This will have no effect on first boot 159 return tegra20_boot_secondary(cpu, idle);
146 * of the CPU since it should already be in reset. 160 if (IS_ENABLED(CONFIG_ARCH_TEGRA_3x_SOC) && tegra_chip_id == TEGRA30)
147 */ 161 return tegra30_boot_secondary(cpu, idle);
148 tegra_put_cpu_in_reset(cpu); 162 if (IS_ENABLED(CONFIG_ARCH_TEGRA_114_SOC) && tegra_chip_id == TEGRA114)
149 163 return tegra114_boot_secondary(cpu, idle);
150 /* 164
151 * Unhalt the CPU. If the flow controller was used to power-gate the 165 return -EINVAL;
152 * CPU this will cause the flow controller to stop driving reset.
153 * The CPU will remain in reset because the clock and reset block
154 * is now driving reset.
155 */
156 flowctrl_write_cpu_halt(cpu, 0);
157
158 switch (tegra_chip_id) {
159 case TEGRA20:
160 status = tegra20_power_up_cpu(cpu);
161 break;
162 case TEGRA30:
163 status = tegra30_power_up_cpu(cpu);
164 break;
165 default:
166 status = -EINVAL;
167 break;
168 }
169
170 if (status)
171 goto done;
172
173 /* Take the CPU out of reset. */
174 tegra_cpu_out_of_reset(cpu);
175done:
176 return status;
177} 166}
178 167
179static void __init tegra_smp_prepare_cpus(unsigned int max_cpus) 168static void __init tegra_smp_prepare_cpus(unsigned int max_cpus)
diff --git a/arch/arm/mach-tegra/pm.c b/arch/arm/mach-tegra/pm.c
index 523604de666f..d0b7400e4606 100644
--- a/arch/arm/mach-tegra/pm.c
+++ b/arch/arm/mach-tegra/pm.c
@@ -22,7 +22,7 @@
22#include <linux/cpumask.h> 22#include <linux/cpumask.h>
23#include <linux/delay.h> 23#include <linux/delay.h>
24#include <linux/cpu_pm.h> 24#include <linux/cpu_pm.h>
25#include <linux/clk.h> 25#include <linux/suspend.h>
26#include <linux/err.h> 26#include <linux/err.h>
27#include <linux/clk/tegra.h> 27#include <linux/clk/tegra.h>
28 28
@@ -37,67 +37,13 @@
37#include "reset.h" 37#include "reset.h"
38#include "flowctrl.h" 38#include "flowctrl.h"
39#include "fuse.h" 39#include "fuse.h"
40#include "pmc.h"
40#include "sleep.h" 41#include "sleep.h"
41 42
42#define TEGRA_POWER_CPU_PWRREQ_OE (1 << 16) /* CPU pwr req enable */
43
44#define PMC_CTRL 0x0
45#define PMC_CPUPWRGOOD_TIMER 0xc8
46#define PMC_CPUPWROFF_TIMER 0xcc
47
48#ifdef CONFIG_PM_SLEEP 43#ifdef CONFIG_PM_SLEEP
49static unsigned int g_diag_reg;
50static DEFINE_SPINLOCK(tegra_lp2_lock); 44static DEFINE_SPINLOCK(tegra_lp2_lock);
51static void __iomem *pmc = IO_ADDRESS(TEGRA_PMC_BASE);
52static struct clk *tegra_pclk;
53void (*tegra_tear_down_cpu)(void); 45void (*tegra_tear_down_cpu)(void);
54 46
55void save_cpu_arch_register(void)
56{
57 /* read diagnostic register */
58 asm("mrc p15, 0, %0, c15, c0, 1" : "=r"(g_diag_reg) : : "cc");
59 return;
60}
61
62void restore_cpu_arch_register(void)
63{
64 /* write diagnostic register */
65 asm("mcr p15, 0, %0, c15, c0, 1" : : "r"(g_diag_reg) : "cc");
66 return;
67}
68
69static void set_power_timers(unsigned long us_on, unsigned long us_off)
70{
71 unsigned long long ticks;
72 unsigned long long pclk;
73 unsigned long rate;
74 static unsigned long tegra_last_pclk;
75
76 if (tegra_pclk == NULL) {
77 tegra_pclk = clk_get_sys(NULL, "pclk");
78 WARN_ON(IS_ERR(tegra_pclk));
79 }
80
81 rate = clk_get_rate(tegra_pclk);
82
83 if (WARN_ON_ONCE(rate <= 0))
84 pclk = 100000000;
85 else
86 pclk = rate;
87
88 if ((rate != tegra_last_pclk)) {
89 ticks = (us_on * pclk) + 999999ull;
90 do_div(ticks, 1000000);
91 writel((unsigned long)ticks, pmc + PMC_CPUPWRGOOD_TIMER);
92
93 ticks = (us_off * pclk) + 999999ull;
94 do_div(ticks, 1000000);
95 writel((unsigned long)ticks, pmc + PMC_CPUPWROFF_TIMER);
96 wmb();
97 }
98 tegra_last_pclk = pclk;
99}
100
101/* 47/*
102 * restore_cpu_complex 48 * restore_cpu_complex
103 * 49 *
@@ -119,8 +65,6 @@ static void restore_cpu_complex(void)
119 tegra_cpu_clock_resume(); 65 tegra_cpu_clock_resume();
120 66
121 flowctrl_cpu_suspend_exit(cpu); 67 flowctrl_cpu_suspend_exit(cpu);
122
123 restore_cpu_arch_register();
124} 68}
125 69
126/* 70/*
@@ -145,8 +89,6 @@ static void suspend_cpu_complex(void)
145 tegra_cpu_clock_suspend(); 89 tegra_cpu_clock_suspend();
146 90
147 flowctrl_cpu_suspend_enter(cpu); 91 flowctrl_cpu_suspend_enter(cpu);
148
149 save_cpu_arch_register();
150} 92}
151 93
152void tegra_clear_cpu_in_lp2(int phy_cpu_id) 94void tegra_clear_cpu_in_lp2(int phy_cpu_id)
@@ -197,16 +139,9 @@ static int tegra_sleep_cpu(unsigned long v2p)
197 return 0; 139 return 0;
198} 140}
199 141
200void tegra_idle_lp2_last(u32 cpu_on_time, u32 cpu_off_time) 142void tegra_idle_lp2_last(void)
201{ 143{
202 u32 mode; 144 tegra_pmc_pm_set(TEGRA_SUSPEND_LP2);
203
204 /* Only the last cpu down does the final suspend steps */
205 mode = readl(pmc + PMC_CTRL);
206 mode |= TEGRA_POWER_CPU_PWRREQ_OE;
207 writel(mode, pmc + PMC_CTRL);
208
209 set_power_timers(cpu_on_time, cpu_off_time);
210 145
211 cpu_cluster_pm_enter(); 146 cpu_cluster_pm_enter();
212 suspend_cpu_complex(); 147 suspend_cpu_complex();
@@ -216,4 +151,81 @@ void tegra_idle_lp2_last(u32 cpu_on_time, u32 cpu_off_time)
216 restore_cpu_complex(); 151 restore_cpu_complex();
217 cpu_cluster_pm_exit(); 152 cpu_cluster_pm_exit();
218} 153}
154
155enum tegra_suspend_mode tegra_pm_validate_suspend_mode(
156 enum tegra_suspend_mode mode)
157{
158 /* Tegra114 didn't support any suspending mode yet. */
159 if (tegra_chip_id == TEGRA114)
160 return TEGRA_SUSPEND_NONE;
161
162 /*
163 * The Tegra devices only support suspending to LP2 currently.
164 */
165 if (mode > TEGRA_SUSPEND_LP2)
166 return TEGRA_SUSPEND_LP2;
167
168 return mode;
169}
170
171static const char *lp_state[TEGRA_MAX_SUSPEND_MODE] = {
172 [TEGRA_SUSPEND_NONE] = "none",
173 [TEGRA_SUSPEND_LP2] = "LP2",
174 [TEGRA_SUSPEND_LP1] = "LP1",
175 [TEGRA_SUSPEND_LP0] = "LP0",
176};
177
178static int __cpuinit tegra_suspend_enter(suspend_state_t state)
179{
180 enum tegra_suspend_mode mode = tegra_pmc_get_suspend_mode();
181
182 if (WARN_ON(mode < TEGRA_SUSPEND_NONE ||
183 mode >= TEGRA_MAX_SUSPEND_MODE))
184 return -EINVAL;
185
186 pr_info("Entering suspend state %s\n", lp_state[mode]);
187
188 tegra_pmc_pm_set(mode);
189
190 local_fiq_disable();
191
192 suspend_cpu_complex();
193 switch (mode) {
194 case TEGRA_SUSPEND_LP2:
195 tegra_set_cpu_in_lp2(0);
196 break;
197 default:
198 break;
199 }
200
201 cpu_suspend(PHYS_OFFSET - PAGE_OFFSET, &tegra_sleep_cpu);
202
203 switch (mode) {
204 case TEGRA_SUSPEND_LP2:
205 tegra_clear_cpu_in_lp2(0);
206 break;
207 default:
208 break;
209 }
210 restore_cpu_complex();
211
212 local_fiq_enable();
213
214 return 0;
215}
216
217static const struct platform_suspend_ops tegra_suspend_ops = {
218 .valid = suspend_valid_only_mem,
219 .enter = tegra_suspend_enter,
220};
221
222void __init tegra_init_suspend(void)
223{
224 if (tegra_pmc_get_suspend_mode() == TEGRA_SUSPEND_NONE)
225 return;
226
227 tegra_pmc_suspend_init();
228
229 suspend_set_ops(&tegra_suspend_ops);
230}
219#endif 231#endif
diff --git a/arch/arm/mach-tegra/pm.h b/arch/arm/mach-tegra/pm.h
index 787335cc964c..9d2d038bf12e 100644
--- a/arch/arm/mach-tegra/pm.h
+++ b/arch/arm/mach-tegra/pm.h
@@ -21,6 +21,8 @@
21#ifndef _MACH_TEGRA_PM_H_ 21#ifndef _MACH_TEGRA_PM_H_
22#define _MACH_TEGRA_PM_H_ 22#define _MACH_TEGRA_PM_H_
23 23
24#include "pmc.h"
25
24extern unsigned long l2x0_saved_regs_addr; 26extern unsigned long l2x0_saved_regs_addr;
25 27
26void save_cpu_arch_register(void); 28void save_cpu_arch_register(void);
@@ -29,7 +31,20 @@ void restore_cpu_arch_register(void);
29void tegra_clear_cpu_in_lp2(int phy_cpu_id); 31void tegra_clear_cpu_in_lp2(int phy_cpu_id);
30bool tegra_set_cpu_in_lp2(int phy_cpu_id); 32bool tegra_set_cpu_in_lp2(int phy_cpu_id);
31 33
32void tegra_idle_lp2_last(u32 cpu_on_time, u32 cpu_off_time); 34void tegra_idle_lp2_last(void);
33extern void (*tegra_tear_down_cpu)(void); 35extern void (*tegra_tear_down_cpu)(void);
34 36
37#ifdef CONFIG_PM_SLEEP
38enum tegra_suspend_mode tegra_pm_validate_suspend_mode(
39 enum tegra_suspend_mode mode);
40void tegra_init_suspend(void);
41#else
42enum tegra_suspend_mode tegra_pm_validate_suspend_mode(
43 enum tegra_suspend_mode mode)
44{
45 return TEGRA_SUSPEND_NONE;
46}
47static inline void tegra_init_suspend(void) {}
48#endif
49
35#endif /* _MACH_TEGRA_PM_H_ */ 50#endif /* _MACH_TEGRA_PM_H_ */
diff --git a/arch/arm/mach-tegra/pmc.c b/arch/arm/mach-tegra/pmc.c
index d4fdb5fcec20..32360e540ce6 100644
--- a/arch/arm/mach-tegra/pmc.c
+++ b/arch/arm/mach-tegra/pmc.c
@@ -1,5 +1,5 @@
1/* 1/*
2 * Copyright (C) 2012 NVIDIA CORPORATION. All rights reserved. 2 * Copyright (C) 2012,2013 NVIDIA CORPORATION. All rights reserved.
3 * 3 *
4 * This program is free software; you can redistribute it and/or modify it 4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License, 5 * under the terms and conditions of the GNU General Public License,
@@ -16,59 +16,313 @@
16 */ 16 */
17 17
18#include <linux/kernel.h> 18#include <linux/kernel.h>
19#include <linux/clk.h>
19#include <linux/io.h> 20#include <linux/io.h>
20#include <linux/of.h> 21#include <linux/of.h>
22#include <linux/of_address.h>
21 23
22#include "iomap.h" 24#include "fuse.h"
25#include "pm.h"
26#include "pmc.h"
27#include "sleep.h"
23 28
24#define PMC_CTRL 0x0 29#define TEGRA_POWER_EFFECT_LP0 (1 << 14) /* LP0 when CPU pwr gated */
25#define PMC_CTRL_INTR_LOW (1 << 17) 30#define TEGRA_POWER_CPU_PWRREQ_POLARITY (1 << 15) /* CPU pwr req polarity */
31#define TEGRA_POWER_CPU_PWRREQ_OE (1 << 16) /* CPU pwr req enable */
32
33#define PMC_CTRL 0x0
34#define PMC_CTRL_INTR_LOW (1 << 17)
35#define PMC_PWRGATE_TOGGLE 0x30
36#define PMC_PWRGATE_TOGGLE_START (1 << 8)
37#define PMC_REMOVE_CLAMPING 0x34
38#define PMC_PWRGATE_STATUS 0x38
39
40#define PMC_CPUPWRGOOD_TIMER 0xc8
41#define PMC_CPUPWROFF_TIMER 0xcc
42
43#define TEGRA_POWERGATE_PCIE 3
44#define TEGRA_POWERGATE_VDEC 4
45#define TEGRA_POWERGATE_CPU1 9
46#define TEGRA_POWERGATE_CPU2 10
47#define TEGRA_POWERGATE_CPU3 11
48
49static u8 tegra_cpu_domains[] = {
50 0xFF, /* not available for CPU0 */
51 TEGRA_POWERGATE_CPU1,
52 TEGRA_POWERGATE_CPU2,
53 TEGRA_POWERGATE_CPU3,
54};
55static DEFINE_SPINLOCK(tegra_powergate_lock);
56
57static void __iomem *tegra_pmc_base;
58static bool tegra_pmc_invert_interrupt;
59static struct clk *tegra_pclk;
60
61struct pmc_pm_data {
62 u32 cpu_good_time; /* CPU power good time in uS */
63 u32 cpu_off_time; /* CPU power off time in uS */
64 u32 core_osc_time; /* Core power good osc time in uS */
65 u32 core_pmu_time; /* Core power good pmu time in uS */
66 u32 core_off_time; /* Core power off time in uS */
67 bool corereq_high; /* Core power request active-high */
68 bool sysclkreq_high; /* System clock request active-high */
69 bool combined_req; /* Combined pwr req for CPU & Core */
70 bool cpu_pwr_good_en; /* CPU power good signal is enabled */
71 u32 lp0_vec_phy_addr; /* The phy addr of LP0 warm boot code */
72 u32 lp0_vec_size; /* The size of LP0 warm boot code */
73 enum tegra_suspend_mode suspend_mode;
74};
75static struct pmc_pm_data pmc_pm_data;
26 76
27static inline u32 tegra_pmc_readl(u32 reg) 77static inline u32 tegra_pmc_readl(u32 reg)
28{ 78{
29 return readl(IO_ADDRESS(TEGRA_PMC_BASE + reg)); 79 return readl(tegra_pmc_base + reg);
30} 80}
31 81
32static inline void tegra_pmc_writel(u32 val, u32 reg) 82static inline void tegra_pmc_writel(u32 val, u32 reg)
33{ 83{
34 writel(val, IO_ADDRESS(TEGRA_PMC_BASE + reg)); 84 writel(val, tegra_pmc_base + reg);
85}
86
87static int tegra_pmc_get_cpu_powerdomain_id(int cpuid)
88{
89 if (cpuid <= 0 || cpuid >= num_possible_cpus())
90 return -EINVAL;
91 return tegra_cpu_domains[cpuid];
92}
93
94static bool tegra_pmc_powergate_is_powered(int id)
95{
96 return (tegra_pmc_readl(PMC_PWRGATE_STATUS) >> id) & 1;
97}
98
99static int tegra_pmc_powergate_set(int id, bool new_state)
100{
101 bool old_state;
102 unsigned long flags;
103
104 spin_lock_irqsave(&tegra_powergate_lock, flags);
105
106 old_state = tegra_pmc_powergate_is_powered(id);
107 WARN_ON(old_state == new_state);
108
109 tegra_pmc_writel(PMC_PWRGATE_TOGGLE_START | id, PMC_PWRGATE_TOGGLE);
110
111 spin_unlock_irqrestore(&tegra_powergate_lock, flags);
112
113 return 0;
114}
115
116static int tegra_pmc_powergate_remove_clamping(int id)
117{
118 u32 mask;
119
120 /*
121 * Tegra has a bug where PCIE and VDE clamping masks are
122 * swapped relatively to the partition ids.
123 */
124 if (id == TEGRA_POWERGATE_VDEC)
125 mask = (1 << TEGRA_POWERGATE_PCIE);
126 else if (id == TEGRA_POWERGATE_PCIE)
127 mask = (1 << TEGRA_POWERGATE_VDEC);
128 else
129 mask = (1 << id);
130
131 tegra_pmc_writel(mask, PMC_REMOVE_CLAMPING);
132
133 return 0;
134}
135
136bool tegra_pmc_cpu_is_powered(int cpuid)
137{
138 int id;
139
140 id = tegra_pmc_get_cpu_powerdomain_id(cpuid);
141 if (id < 0)
142 return false;
143 return tegra_pmc_powergate_is_powered(id);
35} 144}
36 145
37#ifdef CONFIG_OF 146int tegra_pmc_cpu_power_on(int cpuid)
147{
148 int id;
149
150 id = tegra_pmc_get_cpu_powerdomain_id(cpuid);
151 if (id < 0)
152 return id;
153 return tegra_pmc_powergate_set(id, true);
154}
155
156int tegra_pmc_cpu_remove_clamping(int cpuid)
157{
158 int id;
159
160 id = tegra_pmc_get_cpu_powerdomain_id(cpuid);
161 if (id < 0)
162 return id;
163 return tegra_pmc_powergate_remove_clamping(id);
164}
165
166#ifdef CONFIG_PM_SLEEP
167static void set_power_timers(u32 us_on, u32 us_off, unsigned long rate)
168{
169 unsigned long long ticks;
170 unsigned long long pclk;
171 static unsigned long tegra_last_pclk;
172
173 if (WARN_ON_ONCE(rate <= 0))
174 pclk = 100000000;
175 else
176 pclk = rate;
177
178 if ((rate != tegra_last_pclk)) {
179 ticks = (us_on * pclk) + 999999ull;
180 do_div(ticks, 1000000);
181 tegra_pmc_writel((unsigned long)ticks, PMC_CPUPWRGOOD_TIMER);
182
183 ticks = (us_off * pclk) + 999999ull;
184 do_div(ticks, 1000000);
185 tegra_pmc_writel((unsigned long)ticks, PMC_CPUPWROFF_TIMER);
186 wmb();
187 }
188 tegra_last_pclk = pclk;
189}
190
191enum tegra_suspend_mode tegra_pmc_get_suspend_mode(void)
192{
193 return pmc_pm_data.suspend_mode;
194}
195
196void tegra_pmc_pm_set(enum tegra_suspend_mode mode)
197{
198 u32 reg;
199 unsigned long rate = 0;
200
201 reg = tegra_pmc_readl(PMC_CTRL);
202 reg |= TEGRA_POWER_CPU_PWRREQ_OE;
203 reg &= ~TEGRA_POWER_EFFECT_LP0;
204
205 switch (mode) {
206 case TEGRA_SUSPEND_LP2:
207 rate = clk_get_rate(tegra_pclk);
208 break;
209 default:
210 break;
211 }
212
213 set_power_timers(pmc_pm_data.cpu_good_time, pmc_pm_data.cpu_off_time,
214 rate);
215
216 tegra_pmc_writel(reg, PMC_CTRL);
217}
218
219void tegra_pmc_suspend_init(void)
220{
221 u32 reg;
222
223 /* Always enable CPU power request */
224 reg = tegra_pmc_readl(PMC_CTRL);
225 reg |= TEGRA_POWER_CPU_PWRREQ_OE;
226 tegra_pmc_writel(reg, PMC_CTRL);
227}
228#endif
229
38static const struct of_device_id matches[] __initconst = { 230static const struct of_device_id matches[] __initconst = {
231 { .compatible = "nvidia,tegra114-pmc" },
232 { .compatible = "nvidia,tegra30-pmc" },
39 { .compatible = "nvidia,tegra20-pmc" }, 233 { .compatible = "nvidia,tegra20-pmc" },
40 { } 234 { }
41}; 235};
42#endif
43 236
44void __init tegra_pmc_init(void) 237static void tegra_pmc_parse_dt(void)
45{ 238{
46 /* 239 struct device_node *np;
47 * For now, Harmony is the only board that uses the PMC, and it wants 240 u32 prop;
48 * the signal inverted. Seaboard would too if it used the PMC. 241 enum tegra_suspend_mode suspend_mode;
49 * Hopefully by the time other boards want to use the PMC, everything 242 u32 core_good_time[2] = {0, 0};
50 * will be device-tree, or they also want it inverted. 243 u32 lp0_vec[2] = {0, 0};
51 */
52 bool invert_interrupt = true;
53 u32 val;
54 244
55#ifdef CONFIG_OF 245 np = of_find_matching_node(NULL, matches);
56 if (of_have_populated_dt()) { 246 BUG_ON(!np);
57 struct device_node *np;
58 247
59 invert_interrupt = false; 248 tegra_pmc_base = of_iomap(np, 0);
60 249
61 np = of_find_matching_node(NULL, matches); 250 tegra_pmc_invert_interrupt = of_property_read_bool(np,
62 if (np) { 251 "nvidia,invert-interrupt");
63 if (of_find_property(np, "nvidia,invert-interrupt", 252 tegra_pclk = of_clk_get_by_name(np, "pclk");
64 NULL)) 253 WARN_ON(IS_ERR(tegra_pclk));
65 invert_interrupt = true; 254
255 /* Grabbing the power management configurations */
256 if (of_property_read_u32(np, "nvidia,suspend-mode", &prop)) {
257 suspend_mode = TEGRA_SUSPEND_NONE;
258 } else {
259 switch (prop) {
260 case 0:
261 suspend_mode = TEGRA_SUSPEND_LP0;
262 break;
263 case 1:
264 suspend_mode = TEGRA_SUSPEND_LP1;
265 break;
266 case 2:
267 suspend_mode = TEGRA_SUSPEND_LP2;
268 break;
269 default:
270 suspend_mode = TEGRA_SUSPEND_NONE;
271 break;
66 } 272 }
67 } 273 }
68#endif 274 suspend_mode = tegra_pm_validate_suspend_mode(suspend_mode);
275
276 if (of_property_read_u32(np, "nvidia,cpu-pwr-good-time", &prop))
277 suspend_mode = TEGRA_SUSPEND_NONE;
278 pmc_pm_data.cpu_good_time = prop;
279
280 if (of_property_read_u32(np, "nvidia,cpu-pwr-off-time", &prop))
281 suspend_mode = TEGRA_SUSPEND_NONE;
282 pmc_pm_data.cpu_off_time = prop;
283
284 if (of_property_read_u32_array(np, "nvidia,core-pwr-good-time",
285 core_good_time, ARRAY_SIZE(core_good_time)))
286 suspend_mode = TEGRA_SUSPEND_NONE;
287 pmc_pm_data.core_osc_time = core_good_time[0];
288 pmc_pm_data.core_pmu_time = core_good_time[1];
289
290 if (of_property_read_u32(np, "nvidia,core-pwr-off-time",
291 &prop))
292 suspend_mode = TEGRA_SUSPEND_NONE;
293 pmc_pm_data.core_off_time = prop;
294
295 pmc_pm_data.corereq_high = of_property_read_bool(np,
296 "nvidia,core-power-req-active-high");
297
298 pmc_pm_data.sysclkreq_high = of_property_read_bool(np,
299 "nvidia,sys-clock-req-active-high");
300
301 pmc_pm_data.combined_req = of_property_read_bool(np,
302 "nvidia,combined-power-req");
303
304 pmc_pm_data.cpu_pwr_good_en = of_property_read_bool(np,
305 "nvidia,cpu-pwr-good-en");
306
307 if (of_property_read_u32_array(np, "nvidia,lp0-vec", lp0_vec,
308 ARRAY_SIZE(lp0_vec)))
309 if (suspend_mode == TEGRA_SUSPEND_LP0)
310 suspend_mode = TEGRA_SUSPEND_LP1;
311
312 pmc_pm_data.lp0_vec_phy_addr = lp0_vec[0];
313 pmc_pm_data.lp0_vec_size = lp0_vec[1];
314
315 pmc_pm_data.suspend_mode = suspend_mode;
316}
317
318void __init tegra_pmc_init(void)
319{
320 u32 val;
321
322 tegra_pmc_parse_dt();
69 323
70 val = tegra_pmc_readl(PMC_CTRL); 324 val = tegra_pmc_readl(PMC_CTRL);
71 if (invert_interrupt) 325 if (tegra_pmc_invert_interrupt)
72 val |= PMC_CTRL_INTR_LOW; 326 val |= PMC_CTRL_INTR_LOW;
73 else 327 else
74 val &= ~PMC_CTRL_INTR_LOW; 328 val &= ~PMC_CTRL_INTR_LOW;
diff --git a/arch/arm/mach-tegra/pmc.h b/arch/arm/mach-tegra/pmc.h
index 8995ee4a8768..e1c2df272f7d 100644
--- a/arch/arm/mach-tegra/pmc.h
+++ b/arch/arm/mach-tegra/pmc.h
@@ -18,6 +18,24 @@
18#ifndef __MACH_TEGRA_PMC_H 18#ifndef __MACH_TEGRA_PMC_H
19#define __MACH_TEGRA_PMC_H 19#define __MACH_TEGRA_PMC_H
20 20
21enum tegra_suspend_mode {
22 TEGRA_SUSPEND_NONE = 0,
23 TEGRA_SUSPEND_LP2, /* CPU voltage off */
24 TEGRA_SUSPEND_LP1, /* CPU voltage off, DRAM self-refresh */
25 TEGRA_SUSPEND_LP0, /* CPU + core voltage off, DRAM self-refresh */
26 TEGRA_MAX_SUSPEND_MODE,
27};
28
29#ifdef CONFIG_PM_SLEEP
30enum tegra_suspend_mode tegra_pmc_get_suspend_mode(void);
31void tegra_pmc_pm_set(enum tegra_suspend_mode mode);
32void tegra_pmc_suspend_init(void);
33#endif
34
35bool tegra_pmc_cpu_is_powered(int cpuid);
36int tegra_pmc_cpu_power_on(int cpuid);
37int tegra_pmc_cpu_remove_clamping(int cpuid);
38
21void tegra_pmc_init(void); 39void tegra_pmc_init(void);
22 40
23#endif 41#endif
diff --git a/arch/arm/mach-tegra/reset-handler.S b/arch/arm/mach-tegra/reset-handler.S
index 54382ceade4a..1676aba5e7b8 100644
--- a/arch/arm/mach-tegra/reset-handler.S
+++ b/arch/arm/mach-tegra/reset-handler.S
@@ -41,9 +41,6 @@
41 */ 41 */
42ENTRY(tegra_resume) 42ENTRY(tegra_resume)
43 bl v7_invalidate_l1 43 bl v7_invalidate_l1
44 /* Enable coresight */
45 mov32 r0, 0xC5ACCE55
46 mcr p14, 0, r0, c7, c12, 6
47 44
48 cpu_id r0 45 cpu_id r0
49 cmp r0, #0 @ CPU0? 46 cmp r0, #0 @ CPU0?
@@ -99,6 +96,8 @@ ENTRY(__tegra_cpu_reset_handler_start)
99 * 96 *
100 * Register usage within the reset handler: 97 * Register usage within the reset handler:
101 * 98 *
99 * Others: scratch
100 * R6 = SoC ID << 8
102 * R7 = CPU present (to the OS) mask 101 * R7 = CPU present (to the OS) mask
103 * R8 = CPU in LP1 state mask 102 * R8 = CPU in LP1 state mask
104 * R9 = CPU in LP2 state mask 103 * R9 = CPU in LP2 state mask
@@ -114,6 +113,40 @@ ENTRY(__tegra_cpu_reset_handler_start)
114ENTRY(__tegra_cpu_reset_handler) 113ENTRY(__tegra_cpu_reset_handler)
115 114
116 cpsid aif, 0x13 @ SVC mode, interrupts disabled 115 cpsid aif, 0x13 @ SVC mode, interrupts disabled
116
117 mov32 r6, TEGRA_APB_MISC_BASE
118 ldr r6, [r6, #APB_MISC_GP_HIDREV]
119 and r6, r6, #0xff00
120#ifdef CONFIG_ARCH_TEGRA_2x_SOC
121t20_check:
122 cmp r6, #(0x20 << 8)
123 bne after_t20_check
124t20_errata:
125 # Tegra20 is a Cortex-A9 r1p1
126 mrc p15, 0, r0, c1, c0, 0 @ read system control register
127 orr r0, r0, #1 << 14 @ erratum 716044
128 mcr p15, 0, r0, c1, c0, 0 @ write system control register
129 mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register
130 orr r0, r0, #1 << 4 @ erratum 742230
131 orr r0, r0, #1 << 11 @ erratum 751472
132 mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register
133 b after_errata
134after_t20_check:
135#endif
136#ifdef CONFIG_ARCH_TEGRA_3x_SOC
137t30_check:
138 cmp r6, #(0x30 << 8)
139 bne after_t30_check
140t30_errata:
141 # Tegra30 is a Cortex-A9 r2p9
142 mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register
143 orr r0, r0, #1 << 6 @ erratum 743622
144 orr r0, r0, #1 << 11 @ erratum 751472
145 mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register
146 b after_errata
147after_t30_check:
148#endif
149after_errata:
117 mrc p15, 0, r10, c0, c0, 5 @ MPIDR 150 mrc p15, 0, r10, c0, c0, 5 @ MPIDR
118 and r10, r10, #0x3 @ R10 = CPU number 151 and r10, r10, #0x3 @ R10 = CPU number
119 mov r11, #1 152 mov r11, #1
@@ -129,16 +162,13 @@ ENTRY(__tegra_cpu_reset_handler)
129 162
130#ifdef CONFIG_ARCH_TEGRA_2x_SOC 163#ifdef CONFIG_ARCH_TEGRA_2x_SOC
131 /* Are we on Tegra20? */ 164 /* Are we on Tegra20? */
132 mov32 r6, TEGRA_APB_MISC_BASE 165 cmp r6, #(0x20 << 8)
133 ldr r0, [r6, #APB_MISC_GP_HIDREV]
134 and r0, r0, #0xff00
135 cmp r0, #(0x20 << 8)
136 bne 1f 166 bne 1f
137 /* If not CPU0, don't let CPU0 reset CPU1 now that CPU1 is coming up. */ 167 /* If not CPU0, don't let CPU0 reset CPU1 now that CPU1 is coming up. */
138 mov32 r6, TEGRA_PMC_BASE 168 mov32 r5, TEGRA_PMC_BASE
139 mov r0, #0 169 mov r0, #0
140 cmp r10, #0 170 cmp r10, #0
141 strne r0, [r6, #PMC_SCRATCH41] 171 strne r0, [r5, #PMC_SCRATCH41]
1421: 1721:
143#endif 173#endif
144 174
diff --git a/arch/arm/mach-tegra/sleep.h b/arch/arm/mach-tegra/sleep.h
index 4ffae541726e..970ebd5138b9 100644
--- a/arch/arm/mach-tegra/sleep.h
+++ b/arch/arm/mach-tegra/sleep.h
@@ -1,5 +1,5 @@
1/* 1/*
2 * Copyright (c) 2010-2012, NVIDIA Corporation. All rights reserved. 2 * Copyright (c) 2010-2013, NVIDIA Corporation. All rights reserved.
3 * 3 *
4 * This program is free software; you can redistribute it and/or modify it 4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License, 5 * under the terms and conditions of the GNU General Public License,
@@ -124,11 +124,11 @@ int tegra_sleep_cpu_finish(unsigned long);
124void tegra_disable_clean_inv_dcache(void); 124void tegra_disable_clean_inv_dcache(void);
125 125
126#ifdef CONFIG_HOTPLUG_CPU 126#ifdef CONFIG_HOTPLUG_CPU
127void tegra20_hotplug_init(void); 127void tegra20_hotplug_shutdown(void);
128void tegra30_hotplug_init(void); 128void tegra30_hotplug_shutdown(void);
129void tegra_hotplug_init(void);
129#else 130#else
130static inline void tegra20_hotplug_init(void) {} 131static inline void tegra_hotplug_init(void) {}
131static inline void tegra30_hotplug_init(void) {}
132#endif 132#endif
133 133
134void tegra20_cpu_shutdown(int cpu); 134void tegra20_cpu_shutdown(int cpu);
diff --git a/arch/arm/mach-tegra/board-dt-tegra20.c b/arch/arm/mach-tegra/tegra.c
index a0edf2510280..61749e2d8111 100644
--- a/arch/arm/mach-tegra/board-dt-tegra20.c
+++ b/arch/arm/mach-tegra/tegra.c
@@ -1,6 +1,7 @@
1/* 1/*
2 * nVidia Tegra device tree board support 2 * NVIDIA Tegra SoC device tree board support
3 * 3 *
4 * Copyright (C) 2011, 2013, NVIDIA Corporation
4 * Copyright (C) 2010 Secret Lab Technologies, Ltd. 5 * Copyright (C) 2010 Secret Lab Technologies, Ltd.
5 * Copyright (C) 2010 Google, Inc. 6 * Copyright (C) 2010 Google, Inc.
6 * 7 *
@@ -32,7 +33,10 @@
32#include <linux/io.h> 33#include <linux/io.h>
33#include <linux/i2c.h> 34#include <linux/i2c.h>
34#include <linux/i2c-tegra.h> 35#include <linux/i2c-tegra.h>
36#include <linux/slab.h>
37#include <linux/sys_soc.h>
35#include <linux/usb/tegra_usb_phy.h> 38#include <linux/usb/tegra_usb_phy.h>
39#include <linux/clk/tegra.h>
36 40
37#include <asm/mach-types.h> 41#include <asm/mach-types.h>
38#include <asm/mach/arch.h> 42#include <asm/mach/arch.h>
@@ -41,6 +45,7 @@
41 45
42#include "board.h" 46#include "board.h"
43#include "common.h" 47#include "common.h"
48#include "fuse.h"
44#include "iomap.h" 49#include "iomap.h"
45 50
46static struct tegra_ehci_platform_data tegra_ehci1_pdata = { 51static struct tegra_ehci_platform_data tegra_ehci1_pdata = {
@@ -79,12 +84,38 @@ static struct of_dev_auxdata tegra20_auxdata_lookup[] __initdata = {
79 84
80static void __init tegra_dt_init(void) 85static void __init tegra_dt_init(void)
81{ 86{
87 struct soc_device_attribute *soc_dev_attr;
88 struct soc_device *soc_dev;
89 struct device *parent = NULL;
90
91 tegra_clocks_apply_init_table();
92
93 soc_dev_attr = kzalloc(sizeof(*soc_dev_attr), GFP_KERNEL);
94 if (!soc_dev_attr)
95 goto out;
96
97 soc_dev_attr->family = kasprintf(GFP_KERNEL, "Tegra");
98 soc_dev_attr->revision = kasprintf(GFP_KERNEL, "%d", tegra_revision);
99 soc_dev_attr->soc_id = kasprintf(GFP_KERNEL, "%d", tegra_chip_id);
100
101 soc_dev = soc_device_register(soc_dev_attr);
102 if (IS_ERR(soc_dev)) {
103 kfree(soc_dev_attr->family);
104 kfree(soc_dev_attr->revision);
105 kfree(soc_dev_attr->soc_id);
106 kfree(soc_dev_attr);
107 goto out;
108 }
109
110 parent = soc_device_to_device(soc_dev);
111
82 /* 112 /*
83 * Finished with the static registrations now; fill in the missing 113 * Finished with the static registrations now; fill in the missing
84 * devices 114 * devices
85 */ 115 */
116out:
86 of_platform_populate(NULL, of_default_bus_match_table, 117 of_platform_populate(NULL, of_default_bus_match_table,
87 tegra20_auxdata_lookup, NULL); 118 tegra20_auxdata_lookup, parent);
88} 119}
89 120
90static void __init trimslice_init(void) 121static void __init trimslice_init(void)
@@ -111,7 +142,8 @@ static void __init harmony_init(void)
111 142
112static void __init paz00_init(void) 143static void __init paz00_init(void)
113{ 144{
114 tegra_paz00_wifikill_init(); 145 if (IS_ENABLED(CONFIG_ARCH_TEGRA_2x_SOC))
146 tegra_paz00_wifikill_init();
115} 147}
116 148
117static struct { 149static struct {
@@ -137,19 +169,21 @@ static void __init tegra_dt_init_late(void)
137 } 169 }
138} 170}
139 171
140static const char *tegra20_dt_board_compat[] = { 172static const char * const tegra_dt_board_compat[] = {
173 "nvidia,tegra114",
174 "nvidia,tegra30",
141 "nvidia,tegra20", 175 "nvidia,tegra20",
142 NULL 176 NULL
143}; 177};
144 178
145DT_MACHINE_START(TEGRA_DT, "nVidia Tegra20 (Flattened Device Tree)") 179DT_MACHINE_START(TEGRA_DT, "NVIDIA Tegra SoC (Flattened Device Tree)")
146 .map_io = tegra_map_common_io, 180 .map_io = tegra_map_common_io,
147 .smp = smp_ops(tegra_smp_ops), 181 .smp = smp_ops(tegra_smp_ops),
148 .init_early = tegra20_init_early, 182 .init_early = tegra_init_early,
149 .init_irq = tegra_dt_init_irq, 183 .init_irq = tegra_dt_init_irq,
150 .init_time = clocksource_of_init, 184 .init_time = clocksource_of_init,
151 .init_machine = tegra_dt_init, 185 .init_machine = tegra_dt_init,
152 .init_late = tegra_dt_init_late, 186 .init_late = tegra_dt_init_late,
153 .restart = tegra_assert_system_reset, 187 .restart = tegra_assert_system_reset,
154 .dt_compat = tegra20_dt_board_compat, 188 .dt_compat = tegra_dt_board_compat,
155MACHINE_END 189MACHINE_END
diff --git a/arch/arm/mach-tegra/tegra114_speedo.c b/arch/arm/mach-tegra/tegra114_speedo.c
new file mode 100644
index 000000000000..5218d4853cd3
--- /dev/null
+++ b/arch/arm/mach-tegra/tegra114_speedo.c
@@ -0,0 +1,104 @@
1/*
2 * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved.
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 */
16
17#include <linux/kernel.h>
18#include <linux/bug.h>
19
20#include "fuse.h"
21
22#define CORE_PROCESS_CORNERS_NUM 2
23#define CPU_PROCESS_CORNERS_NUM 2
24
25enum {
26 THRESHOLD_INDEX_0,
27 THRESHOLD_INDEX_1,
28 THRESHOLD_INDEX_COUNT,
29};
30
31static const u32 core_process_speedos[][CORE_PROCESS_CORNERS_NUM] = {
32 {1123, UINT_MAX},
33 {0, UINT_MAX},
34};
35
36static const u32 cpu_process_speedos[][CPU_PROCESS_CORNERS_NUM] = {
37 {1695, UINT_MAX},
38 {0, UINT_MAX},
39};
40
41static void rev_sku_to_speedo_ids(int rev, int sku, int *threshold)
42{
43 u32 tmp;
44
45 switch (sku) {
46 case 0x00:
47 case 0x10:
48 case 0x05:
49 case 0x06:
50 tegra_cpu_speedo_id = 1;
51 tegra_soc_speedo_id = 0;
52 *threshold = THRESHOLD_INDEX_0;
53 break;
54
55 case 0x03:
56 case 0x04:
57 tegra_cpu_speedo_id = 2;
58 tegra_soc_speedo_id = 1;
59 *threshold = THRESHOLD_INDEX_1;
60 break;
61
62 default:
63 pr_err("Tegra114 Unknown SKU %d\n", sku);
64 tegra_cpu_speedo_id = 0;
65 tegra_soc_speedo_id = 0;
66 *threshold = THRESHOLD_INDEX_0;
67 break;
68 }
69
70 if (rev == TEGRA_REVISION_A01) {
71 tmp = tegra_fuse_readl(0x270) << 1;
72 tmp |= tegra_fuse_readl(0x26c);
73 if (!tmp)
74 tegra_cpu_speedo_id = 0;
75 }
76}
77
78void tegra114_init_speedo_data(void)
79{
80 u32 cpu_speedo_val;
81 u32 core_speedo_val;
82 int threshold;
83 int i;
84
85 BUILD_BUG_ON(ARRAY_SIZE(cpu_process_speedos) !=
86 THRESHOLD_INDEX_COUNT);
87 BUILD_BUG_ON(ARRAY_SIZE(core_process_speedos) !=
88 THRESHOLD_INDEX_COUNT);
89
90 rev_sku_to_speedo_ids(tegra_revision, tegra_sku_id, &threshold);
91
92 cpu_speedo_val = tegra_fuse_readl(0x12c) + 1024;
93 core_speedo_val = tegra_fuse_readl(0x134);
94
95 for (i = 0; i < CPU_PROCESS_CORNERS_NUM; i++)
96 if (cpu_speedo_val < cpu_process_speedos[threshold][i])
97 break;
98 tegra_cpu_process_id = i;
99
100 for (i = 0; i < CORE_PROCESS_CORNERS_NUM; i++)
101 if (core_speedo_val < core_process_speedos[threshold][i])
102 break;
103 tegra_core_process_id = i;
104}
diff --git a/arch/arm/mach-tegra/tegra2_emc.c b/arch/arm/mach-tegra/tegra2_emc.c
index ce7ce42a1ac9..9e8bdfa2b369 100644
--- a/arch/arm/mach-tegra/tegra2_emc.c
+++ b/arch/arm/mach-tegra/tegra2_emc.c
@@ -276,7 +276,7 @@ static struct tegra_emc_pdata *tegra_emc_fill_pdata(struct platform_device *pdev
276 int i; 276 int i;
277 277
278 WARN_ON(pdev->dev.platform_data); 278 WARN_ON(pdev->dev.platform_data);
279 BUG_ON(IS_ERR_OR_NULL(c)); 279 BUG_ON(IS_ERR(c));
280 280
281 pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL); 281 pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL);
282 pdata->tables = devm_kzalloc(&pdev->dev, sizeof(*pdata->tables), 282 pdata->tables = devm_kzalloc(&pdev->dev, sizeof(*pdata->tables),
diff --git a/arch/arm/mach-ux500/board-mop500-pins.c b/arch/arm/mach-ux500/board-mop500-pins.c
index 0a3f30df1eb8..152ae38cd18c 100644
--- a/arch/arm/mach-ux500/board-mop500-pins.c
+++ b/arch/arm/mach-ux500/board-mop500-pins.c
@@ -48,8 +48,12 @@ BIAS(slpm_in_nopull_wkup, PIN_SLEEPMODE_ENABLED|
48 PIN_SLPM_DIR_INPUT|PIN_SLPM_PULL_NONE|PIN_SLPM_WAKEUP_ENABLE); 48 PIN_SLPM_DIR_INPUT|PIN_SLPM_PULL_NONE|PIN_SLPM_WAKEUP_ENABLE);
49BIAS(slpm_in_wkup_pdis, PIN_SLEEPMODE_ENABLED| 49BIAS(slpm_in_wkup_pdis, PIN_SLEEPMODE_ENABLED|
50 PIN_SLPM_DIR_INPUT|PIN_SLPM_WAKEUP_ENABLE|PIN_SLPM_PDIS_DISABLED); 50 PIN_SLPM_DIR_INPUT|PIN_SLPM_WAKEUP_ENABLE|PIN_SLPM_PDIS_DISABLED);
51BIAS(slpm_in_wkup_pdis_en, PIN_SLEEPMODE_ENABLED|
52 PIN_SLPM_DIR_INPUT|PIN_SLPM_WAKEUP_ENABLE|PIN_SLPM_PDIS_ENABLED);
51BIAS(slpm_wkup_pdis, PIN_SLEEPMODE_ENABLED| 53BIAS(slpm_wkup_pdis, PIN_SLEEPMODE_ENABLED|
52 PIN_SLPM_WAKEUP_ENABLE|PIN_SLPM_PDIS_DISABLED); 54 PIN_SLPM_WAKEUP_ENABLE|PIN_SLPM_PDIS_DISABLED);
55BIAS(slpm_wkup_pdis_en, PIN_SLEEPMODE_ENABLED|
56 PIN_SLPM_WAKEUP_ENABLE|PIN_SLPM_PDIS_ENABLED);
53BIAS(slpm_out_lo_pdis, PIN_SLEEPMODE_ENABLED| 57BIAS(slpm_out_lo_pdis, PIN_SLEEPMODE_ENABLED|
54 PIN_SLPM_OUTPUT_LOW|PIN_SLPM_WAKEUP_DISABLE|PIN_SLPM_PDIS_DISABLED); 58 PIN_SLPM_OUTPUT_LOW|PIN_SLPM_WAKEUP_DISABLE|PIN_SLPM_PDIS_DISABLED);
55BIAS(slpm_out_lo_wkup, PIN_SLEEPMODE_ENABLED| 59BIAS(slpm_out_lo_wkup, PIN_SLEEPMODE_ENABLED|
@@ -78,9 +82,6 @@ BIAS(out_wkup_pdis, PIN_SLPM_DIR_OUTPUT|PIN_SLPM_WAKEUP_ENABLE|
78 PIN_MAP_MUX_GROUP_HOG_DEFAULT("pinctrl-db8500", group, func) 82 PIN_MAP_MUX_GROUP_HOG_DEFAULT("pinctrl-db8500", group, func)
79#define DB8500_PIN_HOG(pin,conf) \ 83#define DB8500_PIN_HOG(pin,conf) \
80 PIN_MAP_CONFIGS_PIN_HOG_DEFAULT("pinctrl-db8500", pin, conf) 84 PIN_MAP_CONFIGS_PIN_HOG_DEFAULT("pinctrl-db8500", pin, conf)
81#define DB8500_PIN_SLEEP(pin, conf, dev) \
82 PIN_MAP_CONFIGS_PIN(dev, PINCTRL_STATE_SLEEP, "pinctrl-db8500", \
83 pin, conf)
84 85
85/* These are default states associated with device and changed runtime */ 86/* These are default states associated with device and changed runtime */
86#define DB8500_MUX(group,func,dev) \ 87#define DB8500_MUX(group,func,dev) \
@@ -309,8 +310,23 @@ static struct pinctrl_map __initdata mop500_family_pinmap[] = {
309 DB8500_PIN_SLEEP("GPIO207_AJ23", slpm_in_wkup_pdis, "sdi4"), /* DAT4 */ 310 DB8500_PIN_SLEEP("GPIO207_AJ23", slpm_in_wkup_pdis, "sdi4"), /* DAT4 */
310 311
311 /* Mux in USB pins, drive STP high */ 312 /* Mux in USB pins, drive STP high */
312 DB8500_MUX("usb_a_1", "usb", "musb-ux500.0"), 313 /* USB default state */
313 DB8500_PIN("GPIO257_AE29", out_hi, "musb-ux500.0"), /* STP */ 314 DB8500_MUX("usb_a_1", "usb", "ab8500-usb.0"),
315 DB8500_PIN("GPIO257_AE29", out_hi, "ab8500-usb.0"), /* STP */
316 /* USB sleep state */
317 DB8500_PIN_SLEEP("GPIO256_AF28", slpm_wkup_pdis_en, "ab8500-usb.0"), /* NXT */
318 DB8500_PIN_SLEEP("GPIO257_AE29", slpm_out_hi_wkup_pdis, "ab8500-usb.0"), /* STP */
319 DB8500_PIN_SLEEP("GPIO258_AD29", slpm_wkup_pdis_en, "ab8500-usb.0"), /* XCLK */
320 DB8500_PIN_SLEEP("GPIO259_AC29", slpm_wkup_pdis_en, "ab8500-usb.0"), /* DIR */
321 DB8500_PIN_SLEEP("GPIO260_AD28", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT7 */
322 DB8500_PIN_SLEEP("GPIO261_AD26", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT6 */
323 DB8500_PIN_SLEEP("GPIO262_AE26", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT5 */
324 DB8500_PIN_SLEEP("GPIO263_AG29", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT4 */
325 DB8500_PIN_SLEEP("GPIO264_AE27", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT3 */
326 DB8500_PIN_SLEEP("GPIO265_AD27", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT2 */
327 DB8500_PIN_SLEEP("GPIO266_AC28", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT1 */
328 DB8500_PIN_SLEEP("GPIO267_AC27", slpm_in_wkup_pdis_en, "ab8500-usb.0"), /* DAT0 */
329
314 /* Mux in SPI2 pins on the "other C1" altfunction */ 330 /* Mux in SPI2 pins on the "other C1" altfunction */
315 DB8500_MUX("spi2_oc1_2", "spi2", "spi2"), 331 DB8500_MUX("spi2_oc1_2", "spi2", "spi2"),
316 DB8500_PIN("GPIO216_AG12", gpio_out_hi, "spi2"), /* FRM */ 332 DB8500_PIN("GPIO216_AG12", gpio_out_hi, "spi2"), /* FRM */
@@ -318,9 +334,9 @@ static struct pinctrl_map __initdata mop500_family_pinmap[] = {
318 DB8500_PIN("GPIO215_AH13", out_lo, "spi2"), /* TXD */ 334 DB8500_PIN("GPIO215_AH13", out_lo, "spi2"), /* TXD */
319 DB8500_PIN("GPIO217_AH12", out_lo, "spi2"), /* CLK */ 335 DB8500_PIN("GPIO217_AH12", out_lo, "spi2"), /* CLK */
320 /* SPI2 idle state */ 336 /* SPI2 idle state */
321 DB8500_PIN_SLEEP("GPIO218_AH11", slpm_in_wkup_pdis, "spi2"), /* RXD */ 337 DB8500_PIN_IDLE("GPIO218_AH11", slpm_in_wkup_pdis, "spi2"), /* RXD */
322 DB8500_PIN_SLEEP("GPIO215_AH13", slpm_out_lo_wkup_pdis, "spi2"), /* TXD */ 338 DB8500_PIN_IDLE("GPIO215_AH13", slpm_out_lo_wkup_pdis, "spi2"), /* TXD */
323 DB8500_PIN_SLEEP("GPIO217_AH12", slpm_wkup_pdis, "spi2"), /* CLK */ 339 DB8500_PIN_IDLE("GPIO217_AH12", slpm_wkup_pdis, "spi2"), /* CLK */
324 /* SPI2 sleep state */ 340 /* SPI2 sleep state */
325 DB8500_PIN_SLEEP("GPIO216_AG12", slpm_in_wkup_pdis, "spi2"), /* FRM */ 341 DB8500_PIN_SLEEP("GPIO216_AG12", slpm_in_wkup_pdis, "spi2"), /* FRM */
326 DB8500_PIN_SLEEP("GPIO218_AH11", slpm_in_wkup_pdis, "spi2"), /* RXD */ 342 DB8500_PIN_SLEEP("GPIO218_AH11", slpm_in_wkup_pdis, "spi2"), /* RXD */
@@ -747,6 +763,8 @@ static struct pinctrl_map __initdata snowball_pinmap[] = {
747 DB8500_PIN_HOG("GPIO21_AB3", out_hi), 763 DB8500_PIN_HOG("GPIO21_AB3", out_hi),
748 /* Mux in "SM" which is used for the SMSC911x Ethernet adapter */ 764 /* Mux in "SM" which is used for the SMSC911x Ethernet adapter */
749 DB8500_MUX_HOG("sm_b_1", "sm"), 765 DB8500_MUX_HOG("sm_b_1", "sm"),
766 /* User LED */
767 DB8500_PIN_HOG("GPIO142_C11", gpio_out_hi),
750 /* Drive RSTn_LAN high */ 768 /* Drive RSTn_LAN high */
751 DB8500_PIN_HOG("GPIO141_C12", gpio_out_hi), 769 DB8500_PIN_HOG("GPIO141_C12", gpio_out_hi),
752 /* Accelerometer/Magnetometer */ 770 /* Accelerometer/Magnetometer */
diff --git a/arch/arm/mach-ux500/cpu.c b/arch/arm/mach-ux500/cpu.c
index 537870d3fea8..002da9a369d5 100644
--- a/arch/arm/mach-ux500/cpu.c
+++ b/arch/arm/mach-ux500/cpu.c
@@ -140,14 +140,13 @@ struct device * __init ux500_soc_device_init(const char *soc_id)
140 soc_info_populate(soc_dev_attr, soc_id); 140 soc_info_populate(soc_dev_attr, soc_id);
141 141
142 soc_dev = soc_device_register(soc_dev_attr); 142 soc_dev = soc_device_register(soc_dev_attr);
143 if (IS_ERR_OR_NULL(soc_dev)) { 143 if (IS_ERR(soc_dev)) {
144 kfree(soc_dev_attr); 144 kfree(soc_dev_attr);
145 return NULL; 145 return NULL;
146 } 146 }
147 147
148 parent = soc_device_to_device(soc_dev); 148 parent = soc_device_to_device(soc_dev);
149 if (!IS_ERR_OR_NULL(parent)) 149 device_create_file(parent, &ux500_soc_attr);
150 device_create_file(parent, &ux500_soc_attr);
151 150
152 return parent; 151 return parent;
153} 152}
diff --git a/arch/arm/mach-ux500/timer.c b/arch/arm/mach-ux500/timer.c
index a6af0b8732ba..d07bbe7f04a6 100644
--- a/arch/arm/mach-ux500/timer.c
+++ b/arch/arm/mach-ux500/timer.c
@@ -7,6 +7,7 @@
7#include <linux/io.h> 7#include <linux/io.h>
8#include <linux/errno.h> 8#include <linux/errno.h>
9#include <linux/clksrc-dbx500-prcmu.h> 9#include <linux/clksrc-dbx500-prcmu.h>
10#include <linux/clocksource.h>
10#include <linux/of.h> 11#include <linux/of.h>
11#include <linux/of_address.h> 12#include <linux/of_address.h>
12#include <linux/platform_data/clocksource-nomadik-mtu.h> 13#include <linux/platform_data/clocksource-nomadik-mtu.h>
@@ -32,7 +33,7 @@ static void __init ux500_twd_init(void)
32 twd_local_timer = &u8500_twd_local_timer; 33 twd_local_timer = &u8500_twd_local_timer;
33 34
34 if (of_have_populated_dt()) 35 if (of_have_populated_dt())
35 twd_local_timer_of_register(); 36 clocksource_of_init();
36 else { 37 else {
37 err = twd_local_timer_register(twd_local_timer); 38 err = twd_local_timer_register(twd_local_timer);
38 if (err) 39 if (err)
diff --git a/arch/arm/mach-versatile/core.c b/arch/arm/mach-versatile/core.c
index 25160aeaa3b7..54bb80b012ac 100644
--- a/arch/arm/mach-versatile/core.c
+++ b/arch/arm/mach-versatile/core.c
@@ -749,12 +749,25 @@ void versatile_restart(char mode, const char *cmd)
749/* Early initializations */ 749/* Early initializations */
750void __init versatile_init_early(void) 750void __init versatile_init_early(void)
751{ 751{
752 u32 val;
752 void __iomem *sys = __io_address(VERSATILE_SYS_BASE); 753 void __iomem *sys = __io_address(VERSATILE_SYS_BASE);
753 754
754 osc4_clk.vcoreg = sys + VERSATILE_SYS_OSCCLCD_OFFSET; 755 osc4_clk.vcoreg = sys + VERSATILE_SYS_OSCCLCD_OFFSET;
755 clkdev_add_table(lookups, ARRAY_SIZE(lookups)); 756 clkdev_add_table(lookups, ARRAY_SIZE(lookups));
756 757
757 versatile_sched_clock_init(sys + VERSATILE_SYS_24MHz_OFFSET, 24000000); 758 versatile_sched_clock_init(sys + VERSATILE_SYS_24MHz_OFFSET, 24000000);
759
760 /*
761 * set clock frequency:
762 * VERSATILE_REFCLK is 32KHz
763 * VERSATILE_TIMCLK is 1MHz
764 */
765 val = readl(__io_address(VERSATILE_SCTL_BASE));
766 writel((VERSATILE_TIMCLK << VERSATILE_TIMER1_EnSel) |
767 (VERSATILE_TIMCLK << VERSATILE_TIMER2_EnSel) |
768 (VERSATILE_TIMCLK << VERSATILE_TIMER3_EnSel) |
769 (VERSATILE_TIMCLK << VERSATILE_TIMER4_EnSel) | val,
770 __io_address(VERSATILE_SCTL_BASE));
758} 771}
759 772
760void __init versatile_init(void) 773void __init versatile_init(void)
@@ -785,19 +798,6 @@ void __init versatile_init(void)
785 */ 798 */
786void __init versatile_timer_init(void) 799void __init versatile_timer_init(void)
787{ 800{
788 u32 val;
789
790 /*
791 * set clock frequency:
792 * VERSATILE_REFCLK is 32KHz
793 * VERSATILE_TIMCLK is 1MHz
794 */
795 val = readl(__io_address(VERSATILE_SCTL_BASE));
796 writel((VERSATILE_TIMCLK << VERSATILE_TIMER1_EnSel) |
797 (VERSATILE_TIMCLK << VERSATILE_TIMER2_EnSel) |
798 (VERSATILE_TIMCLK << VERSATILE_TIMER3_EnSel) |
799 (VERSATILE_TIMCLK << VERSATILE_TIMER4_EnSel) | val,
800 __io_address(VERSATILE_SCTL_BASE));
801 801
802 /* 802 /*
803 * Initialise to a known state (all timers off) 803 * Initialise to a known state (all timers off)
diff --git a/arch/arm/mach-versatile/versatile_dt.c b/arch/arm/mach-versatile/versatile_dt.c
index 2558f2e957c3..3621b000a0f6 100644
--- a/arch/arm/mach-versatile/versatile_dt.c
+++ b/arch/arm/mach-versatile/versatile_dt.c
@@ -45,7 +45,6 @@ DT_MACHINE_START(VERSATILE_PB, "ARM-Versatile (Device Tree Support)")
45 .map_io = versatile_map_io, 45 .map_io = versatile_map_io,
46 .init_early = versatile_init_early, 46 .init_early = versatile_init_early,
47 .init_irq = versatile_init_irq, 47 .init_irq = versatile_init_irq,
48 .init_time = versatile_timer_init,
49 .init_machine = versatile_dt_init, 48 .init_machine = versatile_dt_init,
50 .dt_compat = versatile_dt_match, 49 .dt_compat = versatile_dt_match,
51 .restart = versatile_restart, 50 .restart = versatile_restart,
diff --git a/arch/arm/mach-vexpress/v2m.c b/arch/arm/mach-vexpress/v2m.c
index 915683cb67d6..09e571ddc984 100644
--- a/arch/arm/mach-vexpress/v2m.c
+++ b/arch/arm/mach-vexpress/v2m.c
@@ -1,10 +1,12 @@
1/* 1/*
2 * Versatile Express V2M Motherboard Support 2 * Versatile Express V2M Motherboard Support
3 */ 3 */
4#include <linux/clocksource.h>
4#include <linux/device.h> 5#include <linux/device.h>
5#include <linux/amba/bus.h> 6#include <linux/amba/bus.h>
6#include <linux/amba/mmci.h> 7#include <linux/amba/mmci.h>
7#include <linux/io.h> 8#include <linux/io.h>
9#include <linux/clocksource.h>
8#include <linux/smp.h> 10#include <linux/smp.h>
9#include <linux/init.h> 11#include <linux/init.h>
10#include <linux/irqchip.h> 12#include <linux/irqchip.h>
@@ -22,10 +24,8 @@
22#include <linux/regulator/machine.h> 24#include <linux/regulator/machine.h>
23#include <linux/vexpress.h> 25#include <linux/vexpress.h>
24 26
25#include <asm/arch_timer.h>
26#include <asm/mach-types.h> 27#include <asm/mach-types.h>
27#include <asm/sizes.h> 28#include <asm/sizes.h>
28#include <asm/smp_twd.h>
29#include <asm/mach/arch.h> 29#include <asm/mach/arch.h>
30#include <asm/mach/map.h> 30#include <asm/mach/map.h>
31#include <asm/mach/time.h> 31#include <asm/mach/time.h>
@@ -61,9 +61,6 @@ static void __init v2m_sp804_init(void __iomem *base, unsigned int irq)
61 if (WARN_ON(!base || irq == NO_IRQ)) 61 if (WARN_ON(!base || irq == NO_IRQ))
62 return; 62 return;
63 63
64 writel(0, base + TIMER_1_BASE + TIMER_CTRL);
65 writel(0, base + TIMER_2_BASE + TIMER_CTRL);
66
67 sp804_clocksource_init(base + TIMER_2_BASE, "v2m-timer1"); 64 sp804_clocksource_init(base + TIMER_2_BASE, "v2m-timer1");
68 sp804_clockevents_init(base + TIMER_1_BASE, irq, "v2m-timer0"); 65 sp804_clockevents_init(base + TIMER_1_BASE, irq, "v2m-timer0");
69} 66}
@@ -431,25 +428,11 @@ void __init v2m_dt_init_early(void)
431 428
432static void __init v2m_dt_timer_init(void) 429static void __init v2m_dt_timer_init(void)
433{ 430{
434 struct device_node *node = NULL;
435
436 vexpress_clk_of_init(); 431 vexpress_clk_of_init();
437 432
438 do { 433 clocksource_of_init();
439 node = of_find_compatible_node(node, NULL, "arm,sp804");
440 } while (node && vexpress_get_site_by_node(node) != VEXPRESS_SITE_MB);
441 if (node) {
442 pr_info("Using SP804 '%s' as a clock & events source\n",
443 node->full_name);
444 v2m_sp804_init(of_iomap(node, 0),
445 irq_of_parse_and_map(node, 0));
446 }
447
448 if (arch_timer_of_register() != 0)
449 twd_local_timer_of_register();
450 434
451 if (arch_timer_sched_clock_init() != 0) 435 versatile_sched_clock_init(vexpress_get_24mhz_clock_base(),
452 versatile_sched_clock_init(vexpress_get_24mhz_clock_base(),
453 24000000); 436 24000000);
454} 437}
455 438
diff --git a/arch/arm/mach-virt/virt.c b/arch/arm/mach-virt/virt.c
index 31666f6b4373..adc0945255ae 100644
--- a/arch/arm/mach-virt/virt.c
+++ b/arch/arm/mach-virt/virt.c
@@ -23,21 +23,13 @@
23#include <linux/of_platform.h> 23#include <linux/of_platform.h>
24#include <linux/smp.h> 24#include <linux/smp.h>
25 25
26#include <asm/arch_timer.h>
27#include <asm/mach/arch.h> 26#include <asm/mach/arch.h>
28#include <asm/mach/time.h>
29 27
30static void __init virt_init(void) 28static void __init virt_init(void)
31{ 29{
32 of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL); 30 of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
33} 31}
34 32
35static void __init virt_timer_init(void)
36{
37 WARN_ON(arch_timer_of_register() != 0);
38 WARN_ON(arch_timer_sched_clock_init() != 0);
39}
40
41static const char *virt_dt_match[] = { 33static const char *virt_dt_match[] = {
42 "linux,dummy-virt", 34 "linux,dummy-virt",
43 NULL 35 NULL
@@ -47,7 +39,6 @@ extern struct smp_operations virt_smp_ops;
47 39
48DT_MACHINE_START(VIRT, "Dummy Virtual Machine") 40DT_MACHINE_START(VIRT, "Dummy Virtual Machine")
49 .init_irq = irqchip_init, 41 .init_irq = irqchip_init,
50 .init_time = virt_timer_init,
51 .init_machine = virt_init, 42 .init_machine = virt_init,
52 .smp = smp_ops(virt_smp_ops), 43 .smp = smp_ops(virt_smp_ops),
53 .dt_compat = virt_dt_match, 44 .dt_compat = virt_dt_match,
diff --git a/arch/arm/mach-vt8500/Kconfig b/arch/arm/mach-vt8500/Kconfig
index e3e94b2fa145..9b252934b206 100644
--- a/arch/arm/mach-vt8500/Kconfig
+++ b/arch/arm/mach-vt8500/Kconfig
@@ -7,6 +7,7 @@ config ARCH_VT8500
7 select GENERIC_CLOCKEVENTS 7 select GENERIC_CLOCKEVENTS
8 select HAVE_CLK 8 select HAVE_CLK
9 select VT8500_TIMER 9 select VT8500_TIMER
10 select PINCTRL
10 help 11 help
11 Support for VIA/WonderMedia VT8500/WM85xx System-on-Chip. 12 Support for VIA/WonderMedia VT8500/WM85xx System-on-Chip.
12 13
diff --git a/arch/arm/mach-zynq/Kconfig b/arch/arm/mach-zynq/Kconfig
index adb6c0ea0e53..d70651e8b705 100644
--- a/arch/arm/mach-zynq/Kconfig
+++ b/arch/arm/mach-zynq/Kconfig
@@ -9,5 +9,6 @@ config ARCH_ZYNQ
9 select MIGHT_HAVE_CACHE_L2X0 9 select MIGHT_HAVE_CACHE_L2X0
10 select USE_OF 10 select USE_OF
11 select SPARSE_IRQ 11 select SPARSE_IRQ
12 select CADENCE_TTC_TIMER
12 help 13 help
13 Support for Xilinx Zynq ARM Cortex A9 Platform 14 Support for Xilinx Zynq ARM Cortex A9 Platform
diff --git a/arch/arm/mach-zynq/Makefile b/arch/arm/mach-zynq/Makefile
index 397268c1b250..320faedeb484 100644
--- a/arch/arm/mach-zynq/Makefile
+++ b/arch/arm/mach-zynq/Makefile
@@ -3,4 +3,4 @@
3# 3#
4 4
5# Common support 5# Common support
6obj-y := common.o timer.o 6obj-y := common.o
diff --git a/arch/arm/mach-zynq/common.c b/arch/arm/mach-zynq/common.c
index 5c8983218183..68e0907de5d0 100644
--- a/arch/arm/mach-zynq/common.c
+++ b/arch/arm/mach-zynq/common.c
@@ -20,6 +20,7 @@
20#include <linux/platform_device.h> 20#include <linux/platform_device.h>
21#include <linux/clk.h> 21#include <linux/clk.h>
22#include <linux/clk/zynq.h> 22#include <linux/clk/zynq.h>
23#include <linux/clocksource.h>
23#include <linux/of_address.h> 24#include <linux/of_address.h>
24#include <linux/of_irq.h> 25#include <linux/of_irq.h>
25#include <linux/of_platform.h> 26#include <linux/of_platform.h>
@@ -77,7 +78,7 @@ static void __init xilinx_zynq_timer_init(void)
77 78
78 xilinx_zynq_clocks_init(slcr); 79 xilinx_zynq_clocks_init(slcr);
79 80
80 xttcps_timer_init(); 81 clocksource_of_init();
81} 82}
82 83
83/** 84/**
diff --git a/arch/arm/mach-zynq/common.h b/arch/arm/mach-zynq/common.h
index 8b4dbbaa01cf..5050bb10bb12 100644
--- a/arch/arm/mach-zynq/common.h
+++ b/arch/arm/mach-zynq/common.h
@@ -17,6 +17,4 @@
17#ifndef __MACH_ZYNQ_COMMON_H__ 17#ifndef __MACH_ZYNQ_COMMON_H__
18#define __MACH_ZYNQ_COMMON_H__ 18#define __MACH_ZYNQ_COMMON_H__
19 19
20void __init xttcps_timer_init(void);
21
22#endif 20#endif
diff --git a/arch/arm/mach-zynq/timer.c b/arch/arm/mach-zynq/timer.c
deleted file mode 100644
index f9fbc9c1e7a6..000000000000
--- a/arch/arm/mach-zynq/timer.c
+++ /dev/null
@@ -1,324 +0,0 @@
1/*
2 * This file contains driver for the Xilinx PS Timer Counter IP.
3 *
4 * Copyright (C) 2011 Xilinx
5 *
6 * based on arch/mips/kernel/time.c timer driver
7 *
8 * This software is licensed under the terms of the GNU General Public
9 * License version 2, as published by the Free Software Foundation, and
10 * may be copied, distributed, and modified under those terms.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 */
17
18#include <linux/interrupt.h>
19#include <linux/clockchips.h>
20#include <linux/of_address.h>
21#include <linux/of_irq.h>
22#include <linux/slab.h>
23#include <linux/clk-provider.h>
24#include "common.h"
25
26/*
27 * Timer Register Offset Definitions of Timer 1, Increment base address by 4
28 * and use same offsets for Timer 2
29 */
30#define XTTCPS_CLK_CNTRL_OFFSET 0x00 /* Clock Control Reg, RW */
31#define XTTCPS_CNT_CNTRL_OFFSET 0x0C /* Counter Control Reg, RW */
32#define XTTCPS_COUNT_VAL_OFFSET 0x18 /* Counter Value Reg, RO */
33#define XTTCPS_INTR_VAL_OFFSET 0x24 /* Interval Count Reg, RW */
34#define XTTCPS_ISR_OFFSET 0x54 /* Interrupt Status Reg, RO */
35#define XTTCPS_IER_OFFSET 0x60 /* Interrupt Enable Reg, RW */
36
37#define XTTCPS_CNT_CNTRL_DISABLE_MASK 0x1
38
39/*
40 * Setup the timers to use pre-scaling, using a fixed value for now that will
41 * work across most input frequency, but it may need to be more dynamic
42 */
43#define PRESCALE_EXPONENT 11 /* 2 ^ PRESCALE_EXPONENT = PRESCALE */
44#define PRESCALE 2048 /* The exponent must match this */
45#define CLK_CNTRL_PRESCALE ((PRESCALE_EXPONENT - 1) << 1)
46#define CLK_CNTRL_PRESCALE_EN 1
47#define CNT_CNTRL_RESET (1<<4)
48
49/**
50 * struct xttcps_timer - This definition defines local timer structure
51 *
52 * @base_addr: Base address of timer
53 **/
54struct xttcps_timer {
55 void __iomem *base_addr;
56};
57
58struct xttcps_timer_clocksource {
59 struct xttcps_timer xttc;
60 struct clocksource cs;
61};
62
63#define to_xttcps_timer_clksrc(x) \
64 container_of(x, struct xttcps_timer_clocksource, cs)
65
66struct xttcps_timer_clockevent {
67 struct xttcps_timer xttc;
68 struct clock_event_device ce;
69 struct clk *clk;
70};
71
72#define to_xttcps_timer_clkevent(x) \
73 container_of(x, struct xttcps_timer_clockevent, ce)
74
75/**
76 * xttcps_set_interval - Set the timer interval value
77 *
78 * @timer: Pointer to the timer instance
79 * @cycles: Timer interval ticks
80 **/
81static void xttcps_set_interval(struct xttcps_timer *timer,
82 unsigned long cycles)
83{
84 u32 ctrl_reg;
85
86 /* Disable the counter, set the counter value and re-enable counter */
87 ctrl_reg = __raw_readl(timer->base_addr + XTTCPS_CNT_CNTRL_OFFSET);
88 ctrl_reg |= XTTCPS_CNT_CNTRL_DISABLE_MASK;
89 __raw_writel(ctrl_reg, timer->base_addr + XTTCPS_CNT_CNTRL_OFFSET);
90
91 __raw_writel(cycles, timer->base_addr + XTTCPS_INTR_VAL_OFFSET);
92
93 /*
94 * Reset the counter (0x10) so that it starts from 0, one-shot
95 * mode makes this needed for timing to be right.
96 */
97 ctrl_reg |= CNT_CNTRL_RESET;
98 ctrl_reg &= ~XTTCPS_CNT_CNTRL_DISABLE_MASK;
99 __raw_writel(ctrl_reg, timer->base_addr + XTTCPS_CNT_CNTRL_OFFSET);
100}
101
102/**
103 * xttcps_clock_event_interrupt - Clock event timer interrupt handler
104 *
105 * @irq: IRQ number of the Timer
106 * @dev_id: void pointer to the xttcps_timer instance
107 *
108 * returns: Always IRQ_HANDLED - success
109 **/
110static irqreturn_t xttcps_clock_event_interrupt(int irq, void *dev_id)
111{
112 struct xttcps_timer_clockevent *xttce = dev_id;
113 struct xttcps_timer *timer = &xttce->xttc;
114
115 /* Acknowledge the interrupt and call event handler */
116 __raw_readl(timer->base_addr + XTTCPS_ISR_OFFSET);
117
118 xttce->ce.event_handler(&xttce->ce);
119
120 return IRQ_HANDLED;
121}
122
123/**
124 * __xttc_clocksource_read - Reads the timer counter register
125 *
126 * returns: Current timer counter register value
127 **/
128static cycle_t __xttc_clocksource_read(struct clocksource *cs)
129{
130 struct xttcps_timer *timer = &to_xttcps_timer_clksrc(cs)->xttc;
131
132 return (cycle_t)__raw_readl(timer->base_addr +
133 XTTCPS_COUNT_VAL_OFFSET);
134}
135
136/**
137 * xttcps_set_next_event - Sets the time interval for next event
138 *
139 * @cycles: Timer interval ticks
140 * @evt: Address of clock event instance
141 *
142 * returns: Always 0 - success
143 **/
144static int xttcps_set_next_event(unsigned long cycles,
145 struct clock_event_device *evt)
146{
147 struct xttcps_timer_clockevent *xttce = to_xttcps_timer_clkevent(evt);
148 struct xttcps_timer *timer = &xttce->xttc;
149
150 xttcps_set_interval(timer, cycles);
151 return 0;
152}
153
154/**
155 * xttcps_set_mode - Sets the mode of timer
156 *
157 * @mode: Mode to be set
158 * @evt: Address of clock event instance
159 **/
160static void xttcps_set_mode(enum clock_event_mode mode,
161 struct clock_event_device *evt)
162{
163 struct xttcps_timer_clockevent *xttce = to_xttcps_timer_clkevent(evt);
164 struct xttcps_timer *timer = &xttce->xttc;
165 u32 ctrl_reg;
166
167 switch (mode) {
168 case CLOCK_EVT_MODE_PERIODIC:
169 xttcps_set_interval(timer,
170 DIV_ROUND_CLOSEST(clk_get_rate(xttce->clk),
171 PRESCALE * HZ));
172 break;
173 case CLOCK_EVT_MODE_ONESHOT:
174 case CLOCK_EVT_MODE_UNUSED:
175 case CLOCK_EVT_MODE_SHUTDOWN:
176 ctrl_reg = __raw_readl(timer->base_addr +
177 XTTCPS_CNT_CNTRL_OFFSET);
178 ctrl_reg |= XTTCPS_CNT_CNTRL_DISABLE_MASK;
179 __raw_writel(ctrl_reg,
180 timer->base_addr + XTTCPS_CNT_CNTRL_OFFSET);
181 break;
182 case CLOCK_EVT_MODE_RESUME:
183 ctrl_reg = __raw_readl(timer->base_addr +
184 XTTCPS_CNT_CNTRL_OFFSET);
185 ctrl_reg &= ~XTTCPS_CNT_CNTRL_DISABLE_MASK;
186 __raw_writel(ctrl_reg,
187 timer->base_addr + XTTCPS_CNT_CNTRL_OFFSET);
188 break;
189 }
190}
191
192static void __init zynq_ttc_setup_clocksource(struct device_node *np,
193 void __iomem *base)
194{
195 struct xttcps_timer_clocksource *ttccs;
196 struct clk *clk;
197 int err;
198 u32 reg;
199
200 ttccs = kzalloc(sizeof(*ttccs), GFP_KERNEL);
201 if (WARN_ON(!ttccs))
202 return;
203
204 err = of_property_read_u32(np, "reg", &reg);
205 if (WARN_ON(err))
206 return;
207
208 clk = of_clk_get_by_name(np, "cpu_1x");
209 if (WARN_ON(IS_ERR(clk)))
210 return;
211
212 err = clk_prepare_enable(clk);
213 if (WARN_ON(err))
214 return;
215
216 ttccs->xttc.base_addr = base + reg * 4;
217
218 ttccs->cs.name = np->name;
219 ttccs->cs.rating = 200;
220 ttccs->cs.read = __xttc_clocksource_read;
221 ttccs->cs.mask = CLOCKSOURCE_MASK(16);
222 ttccs->cs.flags = CLOCK_SOURCE_IS_CONTINUOUS;
223
224 __raw_writel(0x0, ttccs->xttc.base_addr + XTTCPS_IER_OFFSET);
225 __raw_writel(CLK_CNTRL_PRESCALE | CLK_CNTRL_PRESCALE_EN,
226 ttccs->xttc.base_addr + XTTCPS_CLK_CNTRL_OFFSET);
227 __raw_writel(CNT_CNTRL_RESET,
228 ttccs->xttc.base_addr + XTTCPS_CNT_CNTRL_OFFSET);
229
230 err = clocksource_register_hz(&ttccs->cs, clk_get_rate(clk) / PRESCALE);
231 if (WARN_ON(err))
232 return;
233}
234
235static void __init zynq_ttc_setup_clockevent(struct device_node *np,
236 void __iomem *base)
237{
238 struct xttcps_timer_clockevent *ttcce;
239 int err, irq;
240 u32 reg;
241
242 ttcce = kzalloc(sizeof(*ttcce), GFP_KERNEL);
243 if (WARN_ON(!ttcce))
244 return;
245
246 err = of_property_read_u32(np, "reg", &reg);
247 if (WARN_ON(err))
248 return;
249
250 ttcce->xttc.base_addr = base + reg * 4;
251
252 ttcce->clk = of_clk_get_by_name(np, "cpu_1x");
253 if (WARN_ON(IS_ERR(ttcce->clk)))
254 return;
255
256 err = clk_prepare_enable(ttcce->clk);
257 if (WARN_ON(err))
258 return;
259
260 irq = irq_of_parse_and_map(np, 0);
261 if (WARN_ON(!irq))
262 return;
263
264 ttcce->ce.name = np->name;
265 ttcce->ce.features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT;
266 ttcce->ce.set_next_event = xttcps_set_next_event;
267 ttcce->ce.set_mode = xttcps_set_mode;
268 ttcce->ce.rating = 200;
269 ttcce->ce.irq = irq;
270 ttcce->ce.cpumask = cpu_possible_mask;
271
272 __raw_writel(0x23, ttcce->xttc.base_addr + XTTCPS_CNT_CNTRL_OFFSET);
273 __raw_writel(CLK_CNTRL_PRESCALE | CLK_CNTRL_PRESCALE_EN,
274 ttcce->xttc.base_addr + XTTCPS_CLK_CNTRL_OFFSET);
275 __raw_writel(0x1, ttcce->xttc.base_addr + XTTCPS_IER_OFFSET);
276
277 err = request_irq(irq, xttcps_clock_event_interrupt, IRQF_TIMER,
278 np->name, ttcce);
279 if (WARN_ON(err))
280 return;
281
282 clockevents_config_and_register(&ttcce->ce,
283 clk_get_rate(ttcce->clk) / PRESCALE,
284 1, 0xfffe);
285}
286
287static const __initconst struct of_device_id zynq_ttc_match[] = {
288 { .compatible = "xlnx,ttc-counter-clocksource",
289 .data = zynq_ttc_setup_clocksource, },
290 { .compatible = "xlnx,ttc-counter-clockevent",
291 .data = zynq_ttc_setup_clockevent, },
292 {}
293};
294
295/**
296 * xttcps_timer_init - Initialize the timer
297 *
298 * Initializes the timer hardware and register the clock source and clock event
299 * timers with Linux kernal timer framework
300 **/
301void __init xttcps_timer_init(void)
302{
303 struct device_node *np;
304
305 for_each_compatible_node(np, NULL, "xlnx,ttc") {
306 struct device_node *np_chld;
307 void __iomem *base;
308
309 base = of_iomap(np, 0);
310 if (WARN_ON(!base))
311 return;
312
313 for_each_available_child_of_node(np, np_chld) {
314 int (*cb)(struct device_node *np, void __iomem *base);
315 const struct of_device_id *match;
316
317 match = of_match_node(zynq_ttc_match, np_chld);
318 if (match) {
319 cb = match->data;
320 cb(np_chld, base);
321 }
322 }
323 }
324}
diff --git a/arch/arm/plat-omap/dmtimer.c b/arch/arm/plat-omap/dmtimer.c
index a0daa2fb5de6..e6dbc8dbe6a6 100644
--- a/arch/arm/plat-omap/dmtimer.c
+++ b/arch/arm/plat-omap/dmtimer.c
@@ -140,8 +140,7 @@ static int omap_dm_timer_prepare(struct omap_dm_timer *timer)
140 */ 140 */
141 if (!(timer->capability & OMAP_TIMER_NEEDS_RESET)) { 141 if (!(timer->capability & OMAP_TIMER_NEEDS_RESET)) {
142 timer->fclk = clk_get(&timer->pdev->dev, "fck"); 142 timer->fclk = clk_get(&timer->pdev->dev, "fck");
143 if (WARN_ON_ONCE(IS_ERR_OR_NULL(timer->fclk))) { 143 if (WARN_ON_ONCE(IS_ERR(timer->fclk))) {
144 timer->fclk = NULL;
145 dev_err(&timer->pdev->dev, ": No fclk handle.\n"); 144 dev_err(&timer->pdev->dev, ": No fclk handle.\n");
146 return -EINVAL; 145 return -EINVAL;
147 } 146 }
@@ -373,7 +372,7 @@ EXPORT_SYMBOL_GPL(omap_dm_timer_modify_idlect_mask);
373 372
374struct clk *omap_dm_timer_get_fclk(struct omap_dm_timer *timer) 373struct clk *omap_dm_timer_get_fclk(struct omap_dm_timer *timer)
375{ 374{
376 if (timer) 375 if (timer && !IS_ERR(timer->fclk))
377 return timer->fclk; 376 return timer->fclk;
378 return NULL; 377 return NULL;
379} 378}
@@ -482,7 +481,7 @@ int omap_dm_timer_set_source(struct omap_dm_timer *timer, int source)
482 if (pdata && pdata->set_timer_src) 481 if (pdata && pdata->set_timer_src)
483 return pdata->set_timer_src(timer->pdev, source); 482 return pdata->set_timer_src(timer->pdev, source);
484 483
485 if (!timer->fclk) 484 if (IS_ERR(timer->fclk))
486 return -EINVAL; 485 return -EINVAL;
487 486
488 switch (source) { 487 switch (source) {
@@ -500,13 +499,13 @@ int omap_dm_timer_set_source(struct omap_dm_timer *timer, int source)
500 } 499 }
501 500
502 parent = clk_get(&timer->pdev->dev, parent_name); 501 parent = clk_get(&timer->pdev->dev, parent_name);
503 if (IS_ERR_OR_NULL(parent)) { 502 if (IS_ERR(parent)) {
504 pr_err("%s: %s not found\n", __func__, parent_name); 503 pr_err("%s: %s not found\n", __func__, parent_name);
505 return -EINVAL; 504 return -EINVAL;
506 } 505 }
507 506
508 ret = clk_set_parent(timer->fclk, parent); 507 ret = clk_set_parent(timer->fclk, parent);
509 if (IS_ERR_VALUE(ret)) 508 if (ret < 0)
510 pr_err("%s: failed to set %s as parent\n", __func__, 509 pr_err("%s: failed to set %s as parent\n", __func__,
511 parent_name); 510 parent_name);
512 511
@@ -808,6 +807,7 @@ static int omap_dm_timer_probe(struct platform_device *pdev)
808 return -ENOMEM; 807 return -ENOMEM;
809 } 808 }
810 809
810 timer->fclk = ERR_PTR(-ENODEV);
811 timer->io_base = devm_ioremap_resource(dev, mem); 811 timer->io_base = devm_ioremap_resource(dev, mem);
812 if (IS_ERR(timer->io_base)) 812 if (IS_ERR(timer->io_base))
813 return PTR_ERR(timer->io_base); 813 return PTR_ERR(timer->io_base);
diff --git a/arch/arm/plat-samsung/Kconfig b/arch/arm/plat-samsung/Kconfig
index a9d52167e16e..b708b3e56d27 100644
--- a/arch/arm/plat-samsung/Kconfig
+++ b/arch/arm/plat-samsung/Kconfig
@@ -70,7 +70,7 @@ config S3C_LOWLEVEL_UART_PORT
70 70
71# timer options 71# timer options
72 72
73config S5P_HRT 73config SAMSUNG_HRT
74 bool 74 bool
75 select SAMSUNG_DEV_PWM 75 select SAMSUNG_DEV_PWM
76 help 76 help
diff --git a/arch/arm/plat-samsung/Makefile b/arch/arm/plat-samsung/Makefile
index 3a7c64d1814a..a23c460299a1 100644
--- a/arch/arm/plat-samsung/Makefile
+++ b/arch/arm/plat-samsung/Makefile
@@ -12,8 +12,7 @@ obj- :=
12# Objects we always build independent of SoC choice 12# Objects we always build independent of SoC choice
13 13
14obj-y += init.o cpu.o 14obj-y += init.o cpu.o
15obj-$(CONFIG_ARCH_USES_GETTIMEOFFSET) += time.o 15obj-$(CONFIG_SAMSUNG_HRT) += samsung-time.o
16obj-$(CONFIG_S5P_HRT) += s5p-time.o
17 16
18obj-$(CONFIG_SAMSUNG_CLOCK) += clock.o 17obj-$(CONFIG_SAMSUNG_CLOCK) += clock.o
19obj-$(CONFIG_SAMSUNG_CLOCK) += pwm-clock.o 18obj-$(CONFIG_SAMSUNG_CLOCK) += pwm-clock.o
diff --git a/arch/arm/plat-samsung/include/plat/cpu.h b/arch/arm/plat-samsung/include/plat/cpu.h
index 37703ef6dfc7..989fefe18be6 100644
--- a/arch/arm/plat-samsung/include/plat/cpu.h
+++ b/arch/arm/plat-samsung/include/plat/cpu.h
@@ -23,6 +23,9 @@ extern unsigned long samsung_cpu_id;
23#define S3C24XX_CPU_ID 0x32400000 23#define S3C24XX_CPU_ID 0x32400000
24#define S3C24XX_CPU_MASK 0xFFF00000 24#define S3C24XX_CPU_MASK 0xFFF00000
25 25
26#define S3C2412_CPU_ID 0x32412000
27#define S3C2412_CPU_MASK 0xFFFFF000
28
26#define S3C6400_CPU_ID 0x36400000 29#define S3C6400_CPU_ID 0x36400000
27#define S3C6410_CPU_ID 0x36410000 30#define S3C6410_CPU_ID 0x36410000
28#define S3C64XX_CPU_MASK 0xFFFFF000 31#define S3C64XX_CPU_MASK 0xFFFFF000
@@ -53,6 +56,7 @@ static inline int is_samsung_##name(void) \
53} 56}
54 57
55IS_SAMSUNG_CPU(s3c24xx, S3C24XX_CPU_ID, S3C24XX_CPU_MASK) 58IS_SAMSUNG_CPU(s3c24xx, S3C24XX_CPU_ID, S3C24XX_CPU_MASK)
59IS_SAMSUNG_CPU(s3c2412, S3C2412_CPU_ID, S3C2412_CPU_MASK)
56IS_SAMSUNG_CPU(s3c6400, S3C6400_CPU_ID, S3C64XX_CPU_MASK) 60IS_SAMSUNG_CPU(s3c6400, S3C6400_CPU_ID, S3C64XX_CPU_MASK)
57IS_SAMSUNG_CPU(s3c6410, S3C6410_CPU_ID, S3C64XX_CPU_MASK) 61IS_SAMSUNG_CPU(s3c6410, S3C6410_CPU_ID, S3C64XX_CPU_MASK)
58IS_SAMSUNG_CPU(s5p6440, S5P6440_CPU_ID, S5P64XX_CPU_MASK) 62IS_SAMSUNG_CPU(s5p6440, S5P6440_CPU_ID, S5P64XX_CPU_MASK)
@@ -74,6 +78,12 @@ IS_SAMSUNG_CPU(exynos5440, EXYNOS5440_SOC_ID, EXYNOS5_SOC_MASK)
74# define soc_is_s3c24xx() 0 78# define soc_is_s3c24xx() 0
75#endif 79#endif
76 80
81#if defined(CONFIG_CPU_S3C2412)
82# define soc_is_s3c2412() is_samsung_s3c2412()
83#else
84# define soc_is_s3c2412() 0
85#endif
86
77#if defined(CONFIG_CPU_S3C6400) || defined(CONFIG_CPU_S3C6410) 87#if defined(CONFIG_CPU_S3C6400) || defined(CONFIG_CPU_S3C6410)
78# define soc_is_s3c64xx() (is_samsung_s3c6400() || is_samsung_s3c6410()) 88# define soc_is_s3c64xx() (is_samsung_s3c6400() || is_samsung_s3c6410())
79#else 89#else
@@ -173,7 +183,6 @@ extern void s3c_init_cpu(unsigned long idcode,
173 183
174/* core initialisation functions */ 184/* core initialisation functions */
175 185
176extern void s3c24xx_init_irq(void);
177extern void s5p_init_irq(u32 *vic, u32 num_vic); 186extern void s5p_init_irq(u32 *vic, u32 num_vic);
178 187
179extern void s3c24xx_init_io(struct map_desc *mach_desc, int size); 188extern void s3c24xx_init_io(struct map_desc *mach_desc, int size);
@@ -192,10 +201,6 @@ extern void s3c24xx_init_uartdevs(char *name,
192 struct s3c24xx_uart_resources *res, 201 struct s3c24xx_uart_resources *res,
193 struct s3c2410_uartcfg *cfg, int no); 202 struct s3c2410_uartcfg *cfg, int no);
194 203
195/* timer for 2410/2440 */
196
197extern void s3c24xx_timer_init(void);
198
199extern struct syscore_ops s3c2410_pm_syscore_ops; 204extern struct syscore_ops s3c2410_pm_syscore_ops;
200extern struct syscore_ops s3c2412_pm_syscore_ops; 205extern struct syscore_ops s3c2412_pm_syscore_ops;
201extern struct syscore_ops s3c2416_pm_syscore_ops; 206extern struct syscore_ops s3c2416_pm_syscore_ops;
diff --git a/arch/arm/plat-samsung/include/plat/irq.h b/arch/arm/plat-samsung/include/plat/irq.h
deleted file mode 100644
index e21a89bc26c9..000000000000
--- a/arch/arm/plat-samsung/include/plat/irq.h
+++ /dev/null
@@ -1,116 +0,0 @@
1/* linux/arch/arm/plat-samsung/include/plat/irq.h
2 *
3 * Copyright (c) 2004-2005 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * Header file for S3C24XX CPU IRQ support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#include <linux/io.h>
14
15#include <mach/hardware.h>
16#include <mach/regs-irq.h>
17#include <mach/regs-gpio.h>
18
19#define irqdbf(x...)
20#define irqdbf2(x...)
21
22#define EXTINT_OFF (IRQ_EINT4 - 4)
23
24/* these are exported for arch/arm/mach-* usage */
25extern struct irq_chip s3c_irq_level_chip;
26extern struct irq_chip s3c_irq_chip;
27
28static inline void s3c_irqsub_mask(unsigned int irqno,
29 unsigned int parentbit,
30 int subcheck)
31{
32 unsigned long mask;
33 unsigned long submask;
34
35 submask = __raw_readl(S3C2410_INTSUBMSK);
36 mask = __raw_readl(S3C2410_INTMSK);
37
38 submask |= (1UL << (irqno - IRQ_S3CUART_RX0));
39
40 /* check to see if we need to mask the parent IRQ */
41
42 if ((submask & subcheck) == subcheck)
43 __raw_writel(mask | parentbit, S3C2410_INTMSK);
44
45 /* write back masks */
46 __raw_writel(submask, S3C2410_INTSUBMSK);
47
48}
49
50static inline void s3c_irqsub_unmask(unsigned int irqno,
51 unsigned int parentbit)
52{
53 unsigned long mask;
54 unsigned long submask;
55
56 submask = __raw_readl(S3C2410_INTSUBMSK);
57 mask = __raw_readl(S3C2410_INTMSK);
58
59 submask &= ~(1UL << (irqno - IRQ_S3CUART_RX0));
60 mask &= ~parentbit;
61
62 /* write back masks */
63 __raw_writel(submask, S3C2410_INTSUBMSK);
64 __raw_writel(mask, S3C2410_INTMSK);
65}
66
67
68static inline void s3c_irqsub_maskack(unsigned int irqno,
69 unsigned int parentmask,
70 unsigned int group)
71{
72 unsigned int bit = 1UL << (irqno - IRQ_S3CUART_RX0);
73
74 s3c_irqsub_mask(irqno, parentmask, group);
75
76 __raw_writel(bit, S3C2410_SUBSRCPND);
77
78 /* only ack parent if we've got all the irqs (seems we must
79 * ack, all and hope that the irq system retriggers ok when
80 * the interrupt goes off again)
81 */
82
83 if (1) {
84 __raw_writel(parentmask, S3C2410_SRCPND);
85 __raw_writel(parentmask, S3C2410_INTPND);
86 }
87}
88
89static inline void s3c_irqsub_ack(unsigned int irqno,
90 unsigned int parentmask,
91 unsigned int group)
92{
93 unsigned int bit = 1UL << (irqno - IRQ_S3CUART_RX0);
94
95 __raw_writel(bit, S3C2410_SUBSRCPND);
96
97 /* only ack parent if we've got all the irqs (seems we must
98 * ack, all and hope that the irq system retriggers ok when
99 * the interrupt goes off again)
100 */
101
102 if (1) {
103 __raw_writel(parentmask, S3C2410_SRCPND);
104 __raw_writel(parentmask, S3C2410_INTPND);
105 }
106}
107
108/* exported for use in arch/arm/mach-s3c2410 */
109
110#ifdef CONFIG_PM
111extern int s3c_irq_wake(struct irq_data *data, unsigned int state);
112#else
113#define s3c_irq_wake NULL
114#endif
115
116extern int s3c_irqext_type(struct irq_data *d, unsigned int type);
diff --git a/arch/arm/plat-samsung/include/plat/s3c2410.h b/arch/arm/plat-samsung/include/plat/s3c2410.h
deleted file mode 100644
index 55b0e5f51e97..000000000000
--- a/arch/arm/plat-samsung/include/plat/s3c2410.h
+++ /dev/null
@@ -1,31 +0,0 @@
1/* linux/arch/arm/plat-samsung/include/plat/s3c2410.h
2 *
3 * Copyright (c) 2004 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * Header file for s3c2410 machine directory
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11 *
12*/
13
14#ifdef CONFIG_CPU_S3C2410
15
16extern int s3c2410_init(void);
17extern int s3c2410a_init(void);
18
19extern void s3c2410_map_io(void);
20
21extern void s3c2410_init_uarts(struct s3c2410_uartcfg *cfg, int no);
22
23extern void s3c2410_init_clocks(int xtal);
24
25#else
26#define s3c2410_init_clocks NULL
27#define s3c2410_init_uarts NULL
28#define s3c2410_map_io NULL
29#define s3c2410_init NULL
30#define s3c2410a_init NULL
31#endif
diff --git a/arch/arm/plat-samsung/include/plat/s3c2412.h b/arch/arm/plat-samsung/include/plat/s3c2412.h
deleted file mode 100644
index cbae50ddacc8..000000000000
--- a/arch/arm/plat-samsung/include/plat/s3c2412.h
+++ /dev/null
@@ -1,32 +0,0 @@
1/* linux/arch/arm/plat-samsung/include/plat/s3c2412.h
2 *
3 * Copyright (c) 2006 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * Header file for s3c2412 cpu support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#ifdef CONFIG_CPU_S3C2412
14
15extern int s3c2412_init(void);
16
17extern void s3c2412_map_io(void);
18
19extern void s3c2412_init_uarts(struct s3c2410_uartcfg *cfg, int no);
20
21extern void s3c2412_init_clocks(int xtal);
22
23extern int s3c2412_baseclk_add(void);
24
25extern void s3c2412_restart(char mode, const char *cmd);
26#else
27#define s3c2412_init_clocks NULL
28#define s3c2412_init_uarts NULL
29#define s3c2412_map_io NULL
30#define s3c2412_init NULL
31#define s3c2412_restart NULL
32#endif
diff --git a/arch/arm/plat-samsung/include/plat/s3c2416.h b/arch/arm/plat-samsung/include/plat/s3c2416.h
deleted file mode 100644
index f27399a3c68d..000000000000
--- a/arch/arm/plat-samsung/include/plat/s3c2416.h
+++ /dev/null
@@ -1,37 +0,0 @@
1/* linux/arch/arm/plat-samsung/include/plat/s3c2416.h
2 *
3 * Copyright (c) 2009 Yauhen Kharuzhy <jekhor@gmail.com>
4 *
5 * Header file for s3c2416 cpu support
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as
9 * published by the Free Software Foundation.
10*/
11
12#ifdef CONFIG_CPU_S3C2416
13
14struct s3c2410_uartcfg;
15
16extern int s3c2416_init(void);
17
18extern void s3c2416_map_io(void);
19
20extern void s3c2416_init_uarts(struct s3c2410_uartcfg *cfg, int no);
21
22extern void s3c2416_init_clocks(int xtal);
23
24extern int s3c2416_baseclk_add(void);
25
26extern void s3c2416_restart(char mode, const char *cmd);
27
28extern void s3c2416_init_irq(void);
29extern struct syscore_ops s3c2416_irq_syscore_ops;
30
31#else
32#define s3c2416_init_clocks NULL
33#define s3c2416_init_uarts NULL
34#define s3c2416_map_io NULL
35#define s3c2416_init NULL
36#define s3c2416_restart NULL
37#endif
diff --git a/arch/arm/plat-samsung/include/plat/s3c2443.h b/arch/arm/plat-samsung/include/plat/s3c2443.h
deleted file mode 100644
index 71b88ec48956..000000000000
--- a/arch/arm/plat-samsung/include/plat/s3c2443.h
+++ /dev/null
@@ -1,36 +0,0 @@
1/* linux/arch/arm/plat-samsung/include/plat/s3c2443.h
2 *
3 * Copyright (c) 2004-2005 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * Header file for s3c2443 cpu support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#ifdef CONFIG_CPU_S3C2443
14
15struct s3c2410_uartcfg;
16
17extern int s3c2443_init(void);
18
19extern void s3c2443_map_io(void);
20
21extern void s3c2443_init_uarts(struct s3c2410_uartcfg *cfg, int no);
22
23extern void s3c2443_init_clocks(int xtal);
24
25extern int s3c2443_baseclk_add(void);
26
27extern void s3c2443_restart(char mode, const char *cmd);
28
29extern void s3c2443_init_irq(void);
30#else
31#define s3c2443_init_clocks NULL
32#define s3c2443_init_uarts NULL
33#define s3c2443_map_io NULL
34#define s3c2443_init NULL
35#define s3c2443_restart NULL
36#endif
diff --git a/arch/arm/plat-samsung/include/plat/s3c244x.h b/arch/arm/plat-samsung/include/plat/s3c244x.h
deleted file mode 100644
index ea0c961b7603..000000000000
--- a/arch/arm/plat-samsung/include/plat/s3c244x.h
+++ /dev/null
@@ -1,42 +0,0 @@
1/* linux/arch/arm/plat-samsung/include/plat/s3c244x.h
2 *
3 * Copyright (c) 2004-2005 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * Header file for S3C2440 and S3C2442 cpu support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#if defined(CONFIG_CPU_S3C2440) || defined(CONFIG_CPU_S3C2442)
14
15extern void s3c244x_map_io(void);
16
17extern void s3c244x_init_uarts(struct s3c2410_uartcfg *cfg, int no);
18
19extern void s3c244x_init_clocks(int xtal);
20
21#else
22#define s3c244x_init_clocks NULL
23#define s3c244x_init_uarts NULL
24#endif
25
26#ifdef CONFIG_CPU_S3C2440
27extern int s3c2440_init(void);
28
29extern void s3c2440_map_io(void);
30#else
31#define s3c2440_init NULL
32#define s3c2440_map_io NULL
33#endif
34
35#ifdef CONFIG_CPU_S3C2442
36extern int s3c2442_init(void);
37
38extern void s3c2442_map_io(void);
39#else
40#define s3c2442_init NULL
41#define s3c2442_map_io NULL
42#endif
diff --git a/arch/arm/plat-samsung/include/plat/s5p-time.h b/arch/arm/plat-samsung/include/plat/s5p-time.h
deleted file mode 100644
index 9c96f3586ce0..000000000000
--- a/arch/arm/plat-samsung/include/plat/s5p-time.h
+++ /dev/null
@@ -1,40 +0,0 @@
1/* linux/arch/arm/plat-samsung/include/plat/s5p-time.h
2 *
3 * Copyright 2011 Samsung Electronics Co., Ltd.
4 * http://www.samsung.com/
5 *
6 * Header file for s5p time support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#ifndef __ASM_PLAT_S5P_TIME_H
14#define __ASM_PLAT_S5P_TIME_H __FILE__
15
16/* S5P HR-Timer Clock mode */
17enum s5p_timer_mode {
18 S5P_PWM0,
19 S5P_PWM1,
20 S5P_PWM2,
21 S5P_PWM3,
22 S5P_PWM4,
23};
24
25struct s5p_timer_source {
26 unsigned int event_id;
27 unsigned int source_id;
28};
29
30/* Be able to sleep for atleast 4 seconds (usually more) */
31#define S5PTIMER_MIN_RANGE 4
32
33#define TCNT_MAX 0xffffffff
34#define NON_PERIODIC 0
35#define PERIODIC 1
36
37extern void __init s5p_set_timer_source(enum s5p_timer_mode event,
38 enum s5p_timer_mode source);
39extern void s5p_timer_init(void);
40#endif /* __ASM_PLAT_S5P_TIME_H */
diff --git a/arch/arm/plat-samsung/include/plat/samsung-time.h b/arch/arm/plat-samsung/include/plat/samsung-time.h
new file mode 100644
index 000000000000..4cc99bb1f176
--- /dev/null
+++ b/arch/arm/plat-samsung/include/plat/samsung-time.h
@@ -0,0 +1,53 @@
1/* linux/arch/arm/plat-samsung/include/plat/samsung-time.h
2 *
3 * Copyright 2011 Samsung Electronics Co., Ltd.
4 * http://www.samsung.com/
5 *
6 * Header file for samsung s3c and s5p time support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11*/
12
13#ifndef __ASM_PLAT_SAMSUNG_TIME_H
14#define __ASM_PLAT_SAMSUNG_TIME_H __FILE__
15
16/* SAMSUNG HR-Timer Clock mode */
17enum samsung_timer_mode {
18 SAMSUNG_PWM0,
19 SAMSUNG_PWM1,
20 SAMSUNG_PWM2,
21 SAMSUNG_PWM3,
22 SAMSUNG_PWM4,
23};
24
25struct samsung_timer_source {
26 unsigned int event_id;
27 unsigned int source_id;
28};
29
30/* Be able to sleep for atleast 4 seconds (usually more) */
31#define SAMSUNG_TIMER_MIN_RANGE 4
32
33#if defined(CONFIG_ARCH_S3C24XX) || defined(CONFIG_ARCH_S5PC100)
34#define TCNT_MAX 0xffff
35#define TSCALER_DIV 25
36#define TDIV 50
37#define TSIZE 16
38#else
39#define TCNT_MAX 0xffffffff
40#define TSCALER_DIV 2
41#define TDIV 2
42#define TSIZE 32
43#endif
44
45#define NON_PERIODIC 0
46#define PERIODIC 1
47
48extern void __init samsung_set_timer_source(enum samsung_timer_mode event,
49 enum samsung_timer_mode source);
50
51extern void __init samsung_timer_init(void);
52
53#endif /* __ASM_PLAT_SAMSUNG_TIME_H */
diff --git a/arch/arm/plat-samsung/s5p-time.c b/arch/arm/plat-samsung/samsung-time.c
index e92510cf82ee..f899cbc9b288 100644
--- a/arch/arm/plat-samsung/s5p-time.c
+++ b/arch/arm/plat-samsung/samsung-time.c
@@ -2,7 +2,7 @@
2 * Copyright (c) 2011 Samsung Electronics Co., Ltd. 2 * Copyright (c) 2011 Samsung Electronics Co., Ltd.
3 * http://www.samsung.com/ 3 * http://www.samsung.com/
4 * 4 *
5 * S5P - Common hr-timer support 5 * samsung - Common hr-timer support (s3c and s5p)
6 * 6 *
7 * This program is free software; you can redistribute it and/or modify 7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as 8 * it under the terms of the GNU General Public License version 2 as
@@ -25,41 +25,41 @@
25#include <mach/map.h> 25#include <mach/map.h>
26#include <plat/devs.h> 26#include <plat/devs.h>
27#include <plat/regs-timer.h> 27#include <plat/regs-timer.h>
28#include <plat/s5p-time.h> 28#include <plat/samsung-time.h>
29 29
30static struct clk *tin_event; 30static struct clk *tin_event;
31static struct clk *tin_source; 31static struct clk *tin_source;
32static struct clk *tdiv_event; 32static struct clk *tdiv_event;
33static struct clk *tdiv_source; 33static struct clk *tdiv_source;
34static struct clk *timerclk; 34static struct clk *timerclk;
35static struct s5p_timer_source timer_source; 35static struct samsung_timer_source timer_source;
36static unsigned long clock_count_per_tick; 36static unsigned long clock_count_per_tick;
37static void s5p_timer_resume(void); 37static void samsung_timer_resume(void);
38 38
39static void s5p_time_stop(enum s5p_timer_mode mode) 39static void samsung_time_stop(enum samsung_timer_mode mode)
40{ 40{
41 unsigned long tcon; 41 unsigned long tcon;
42 42
43 tcon = __raw_readl(S3C2410_TCON); 43 tcon = __raw_readl(S3C2410_TCON);
44 44
45 switch (mode) { 45 switch (mode) {
46 case S5P_PWM0: 46 case SAMSUNG_PWM0:
47 tcon &= ~S3C2410_TCON_T0START; 47 tcon &= ~S3C2410_TCON_T0START;
48 break; 48 break;
49 49
50 case S5P_PWM1: 50 case SAMSUNG_PWM1:
51 tcon &= ~S3C2410_TCON_T1START; 51 tcon &= ~S3C2410_TCON_T1START;
52 break; 52 break;
53 53
54 case S5P_PWM2: 54 case SAMSUNG_PWM2:
55 tcon &= ~S3C2410_TCON_T2START; 55 tcon &= ~S3C2410_TCON_T2START;
56 break; 56 break;
57 57
58 case S5P_PWM3: 58 case SAMSUNG_PWM3:
59 tcon &= ~S3C2410_TCON_T3START; 59 tcon &= ~S3C2410_TCON_T3START;
60 break; 60 break;
61 61
62 case S5P_PWM4: 62 case SAMSUNG_PWM4:
63 tcon &= ~S3C2410_TCON_T4START; 63 tcon &= ~S3C2410_TCON_T4START;
64 break; 64 break;
65 65
@@ -70,7 +70,7 @@ static void s5p_time_stop(enum s5p_timer_mode mode)
70 __raw_writel(tcon, S3C2410_TCON); 70 __raw_writel(tcon, S3C2410_TCON);
71} 71}
72 72
73static void s5p_time_setup(enum s5p_timer_mode mode, unsigned long tcnt) 73static void samsung_time_setup(enum samsung_timer_mode mode, unsigned long tcnt)
74{ 74{
75 unsigned long tcon; 75 unsigned long tcon;
76 76
@@ -79,27 +79,27 @@ static void s5p_time_setup(enum s5p_timer_mode mode, unsigned long tcnt)
79 tcnt--; 79 tcnt--;
80 80
81 switch (mode) { 81 switch (mode) {
82 case S5P_PWM0: 82 case SAMSUNG_PWM0:
83 tcon &= ~(0x0f << 0); 83 tcon &= ~(0x0f << 0);
84 tcon |= S3C2410_TCON_T0MANUALUPD; 84 tcon |= S3C2410_TCON_T0MANUALUPD;
85 break; 85 break;
86 86
87 case S5P_PWM1: 87 case SAMSUNG_PWM1:
88 tcon &= ~(0x0f << 8); 88 tcon &= ~(0x0f << 8);
89 tcon |= S3C2410_TCON_T1MANUALUPD; 89 tcon |= S3C2410_TCON_T1MANUALUPD;
90 break; 90 break;
91 91
92 case S5P_PWM2: 92 case SAMSUNG_PWM2:
93 tcon &= ~(0x0f << 12); 93 tcon &= ~(0x0f << 12);
94 tcon |= S3C2410_TCON_T2MANUALUPD; 94 tcon |= S3C2410_TCON_T2MANUALUPD;
95 break; 95 break;
96 96
97 case S5P_PWM3: 97 case SAMSUNG_PWM3:
98 tcon &= ~(0x0f << 16); 98 tcon &= ~(0x0f << 16);
99 tcon |= S3C2410_TCON_T3MANUALUPD; 99 tcon |= S3C2410_TCON_T3MANUALUPD;
100 break; 100 break;
101 101
102 case S5P_PWM4: 102 case SAMSUNG_PWM4:
103 tcon &= ~(0x07 << 20); 103 tcon &= ~(0x07 << 20);
104 tcon |= S3C2410_TCON_T4MANUALUPD; 104 tcon |= S3C2410_TCON_T4MANUALUPD;
105 break; 105 break;
@@ -114,14 +114,14 @@ static void s5p_time_setup(enum s5p_timer_mode mode, unsigned long tcnt)
114 __raw_writel(tcon, S3C2410_TCON); 114 __raw_writel(tcon, S3C2410_TCON);
115} 115}
116 116
117static void s5p_time_start(enum s5p_timer_mode mode, bool periodic) 117static void samsung_time_start(enum samsung_timer_mode mode, bool periodic)
118{ 118{
119 unsigned long tcon; 119 unsigned long tcon;
120 120
121 tcon = __raw_readl(S3C2410_TCON); 121 tcon = __raw_readl(S3C2410_TCON);
122 122
123 switch (mode) { 123 switch (mode) {
124 case S5P_PWM0: 124 case SAMSUNG_PWM0:
125 tcon |= S3C2410_TCON_T0START; 125 tcon |= S3C2410_TCON_T0START;
126 tcon &= ~S3C2410_TCON_T0MANUALUPD; 126 tcon &= ~S3C2410_TCON_T0MANUALUPD;
127 127
@@ -131,7 +131,7 @@ static void s5p_time_start(enum s5p_timer_mode mode, bool periodic)
131 tcon &= ~S3C2410_TCON_T0RELOAD; 131 tcon &= ~S3C2410_TCON_T0RELOAD;
132 break; 132 break;
133 133
134 case S5P_PWM1: 134 case SAMSUNG_PWM1:
135 tcon |= S3C2410_TCON_T1START; 135 tcon |= S3C2410_TCON_T1START;
136 tcon &= ~S3C2410_TCON_T1MANUALUPD; 136 tcon &= ~S3C2410_TCON_T1MANUALUPD;
137 137
@@ -141,7 +141,7 @@ static void s5p_time_start(enum s5p_timer_mode mode, bool periodic)
141 tcon &= ~S3C2410_TCON_T1RELOAD; 141 tcon &= ~S3C2410_TCON_T1RELOAD;
142 break; 142 break;
143 143
144 case S5P_PWM2: 144 case SAMSUNG_PWM2:
145 tcon |= S3C2410_TCON_T2START; 145 tcon |= S3C2410_TCON_T2START;
146 tcon &= ~S3C2410_TCON_T2MANUALUPD; 146 tcon &= ~S3C2410_TCON_T2MANUALUPD;
147 147
@@ -151,7 +151,7 @@ static void s5p_time_start(enum s5p_timer_mode mode, bool periodic)
151 tcon &= ~S3C2410_TCON_T2RELOAD; 151 tcon &= ~S3C2410_TCON_T2RELOAD;
152 break; 152 break;
153 153
154 case S5P_PWM3: 154 case SAMSUNG_PWM3:
155 tcon |= S3C2410_TCON_T3START; 155 tcon |= S3C2410_TCON_T3START;
156 tcon &= ~S3C2410_TCON_T3MANUALUPD; 156 tcon &= ~S3C2410_TCON_T3MANUALUPD;
157 157
@@ -161,7 +161,7 @@ static void s5p_time_start(enum s5p_timer_mode mode, bool periodic)
161 tcon &= ~S3C2410_TCON_T3RELOAD; 161 tcon &= ~S3C2410_TCON_T3RELOAD;
162 break; 162 break;
163 163
164 case S5P_PWM4: 164 case SAMSUNG_PWM4:
165 tcon |= S3C2410_TCON_T4START; 165 tcon |= S3C2410_TCON_T4START;
166 tcon &= ~S3C2410_TCON_T4MANUALUPD; 166 tcon &= ~S3C2410_TCON_T4MANUALUPD;
167 167
@@ -178,24 +178,24 @@ static void s5p_time_start(enum s5p_timer_mode mode, bool periodic)
178 __raw_writel(tcon, S3C2410_TCON); 178 __raw_writel(tcon, S3C2410_TCON);
179} 179}
180 180
181static int s5p_set_next_event(unsigned long cycles, 181static int samsung_set_next_event(unsigned long cycles,
182 struct clock_event_device *evt) 182 struct clock_event_device *evt)
183{ 183{
184 s5p_time_setup(timer_source.event_id, cycles); 184 samsung_time_setup(timer_source.event_id, cycles);
185 s5p_time_start(timer_source.event_id, NON_PERIODIC); 185 samsung_time_start(timer_source.event_id, NON_PERIODIC);
186 186
187 return 0; 187 return 0;
188} 188}
189 189
190static void s5p_set_mode(enum clock_event_mode mode, 190static void samsung_set_mode(enum clock_event_mode mode,
191 struct clock_event_device *evt) 191 struct clock_event_device *evt)
192{ 192{
193 s5p_time_stop(timer_source.event_id); 193 samsung_time_stop(timer_source.event_id);
194 194
195 switch (mode) { 195 switch (mode) {
196 case CLOCK_EVT_MODE_PERIODIC: 196 case CLOCK_EVT_MODE_PERIODIC:
197 s5p_time_setup(timer_source.event_id, clock_count_per_tick); 197 samsung_time_setup(timer_source.event_id, clock_count_per_tick);
198 s5p_time_start(timer_source.event_id, PERIODIC); 198 samsung_time_start(timer_source.event_id, PERIODIC);
199 break; 199 break;
200 200
201 case CLOCK_EVT_MODE_ONESHOT: 201 case CLOCK_EVT_MODE_ONESHOT:
@@ -206,24 +206,24 @@ static void s5p_set_mode(enum clock_event_mode mode,
206 break; 206 break;
207 207
208 case CLOCK_EVT_MODE_RESUME: 208 case CLOCK_EVT_MODE_RESUME:
209 s5p_timer_resume(); 209 samsung_timer_resume();
210 break; 210 break;
211 } 211 }
212} 212}
213 213
214static void s5p_timer_resume(void) 214static void samsung_timer_resume(void)
215{ 215{
216 /* event timer restart */ 216 /* event timer restart */
217 s5p_time_setup(timer_source.event_id, clock_count_per_tick); 217 samsung_time_setup(timer_source.event_id, clock_count_per_tick);
218 s5p_time_start(timer_source.event_id, PERIODIC); 218 samsung_time_start(timer_source.event_id, PERIODIC);
219 219
220 /* source timer restart */ 220 /* source timer restart */
221 s5p_time_setup(timer_source.source_id, TCNT_MAX); 221 samsung_time_setup(timer_source.source_id, TCNT_MAX);
222 s5p_time_start(timer_source.source_id, PERIODIC); 222 samsung_time_start(timer_source.source_id, PERIODIC);
223} 223}
224 224
225void __init s5p_set_timer_source(enum s5p_timer_mode event, 225void __init samsung_set_timer_source(enum samsung_timer_mode event,
226 enum s5p_timer_mode source) 226 enum samsung_timer_mode source)
227{ 227{
228 s3c_device_timer[event].dev.bus = &platform_bus_type; 228 s3c_device_timer[event].dev.bus = &platform_bus_type;
229 s3c_device_timer[source].dev.bus = &platform_bus_type; 229 s3c_device_timer[source].dev.bus = &platform_bus_type;
@@ -233,14 +233,14 @@ void __init s5p_set_timer_source(enum s5p_timer_mode event,
233} 233}
234 234
235static struct clock_event_device time_event_device = { 235static struct clock_event_device time_event_device = {
236 .name = "s5p_event_timer", 236 .name = "samsung_event_timer",
237 .features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT, 237 .features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT,
238 .rating = 200, 238 .rating = 200,
239 .set_next_event = s5p_set_next_event, 239 .set_next_event = samsung_set_next_event,
240 .set_mode = s5p_set_mode, 240 .set_mode = samsung_set_mode,
241}; 241};
242 242
243static irqreturn_t s5p_clock_event_isr(int irq, void *dev_id) 243static irqreturn_t samsung_clock_event_isr(int irq, void *dev_id)
244{ 244{
245 struct clock_event_device *evt = dev_id; 245 struct clock_event_device *evt = dev_id;
246 246
@@ -249,14 +249,14 @@ static irqreturn_t s5p_clock_event_isr(int irq, void *dev_id)
249 return IRQ_HANDLED; 249 return IRQ_HANDLED;
250} 250}
251 251
252static struct irqaction s5p_clock_event_irq = { 252static struct irqaction samsung_clock_event_irq = {
253 .name = "s5p_time_irq", 253 .name = "samsung_time_irq",
254 .flags = IRQF_DISABLED | IRQF_TIMER | IRQF_IRQPOLL, 254 .flags = IRQF_DISABLED | IRQF_TIMER | IRQF_IRQPOLL,
255 .handler = s5p_clock_event_isr, 255 .handler = samsung_clock_event_isr,
256 .dev_id = &time_event_device, 256 .dev_id = &time_event_device,
257}; 257};
258 258
259static void __init s5p_clockevent_init(void) 259static void __init samsung_clockevent_init(void)
260{ 260{
261 unsigned long pclk; 261 unsigned long pclk;
262 unsigned long clock_rate; 262 unsigned long clock_rate;
@@ -267,8 +267,8 @@ static void __init s5p_clockevent_init(void)
267 267
268 tscaler = clk_get_parent(tdiv_event); 268 tscaler = clk_get_parent(tdiv_event);
269 269
270 clk_set_rate(tscaler, pclk / 2); 270 clk_set_rate(tscaler, pclk / TSCALER_DIV);
271 clk_set_rate(tdiv_event, pclk / 2); 271 clk_set_rate(tdiv_event, pclk / TDIV);
272 clk_set_parent(tin_event, tdiv_event); 272 clk_set_parent(tin_event, tdiv_event);
273 273
274 clock_rate = clk_get_rate(tin_event); 274 clock_rate = clk_get_rate(tin_event);
@@ -278,22 +278,22 @@ static void __init s5p_clockevent_init(void)
278 clockevents_config_and_register(&time_event_device, clock_rate, 1, -1); 278 clockevents_config_and_register(&time_event_device, clock_rate, 1, -1);
279 279
280 irq_number = timer_source.event_id + IRQ_TIMER0; 280 irq_number = timer_source.event_id + IRQ_TIMER0;
281 setup_irq(irq_number, &s5p_clock_event_irq); 281 setup_irq(irq_number, &samsung_clock_event_irq);
282} 282}
283 283
284static void __iomem *s5p_timer_reg(void) 284static void __iomem *samsung_timer_reg(void)
285{ 285{
286 unsigned long offset = 0; 286 unsigned long offset = 0;
287 287
288 switch (timer_source.source_id) { 288 switch (timer_source.source_id) {
289 case S5P_PWM0: 289 case SAMSUNG_PWM0:
290 case S5P_PWM1: 290 case SAMSUNG_PWM1:
291 case S5P_PWM2: 291 case SAMSUNG_PWM2:
292 case S5P_PWM3: 292 case SAMSUNG_PWM3:
293 offset = (timer_source.source_id * 0x0c) + 0x14; 293 offset = (timer_source.source_id * 0x0c) + 0x14;
294 break; 294 break;
295 295
296 case S5P_PWM4: 296 case SAMSUNG_PWM4:
297 offset = 0x40; 297 offset = 0x40;
298 break; 298 break;
299 299
@@ -312,9 +312,9 @@ static void __iomem *s5p_timer_reg(void)
312 * this wraps around for now, since it is just a relative time 312 * this wraps around for now, since it is just a relative time
313 * stamp. (Inspired by U300 implementation.) 313 * stamp. (Inspired by U300 implementation.)
314 */ 314 */
315static u32 notrace s5p_read_sched_clock(void) 315static u32 notrace samsung_read_sched_clock(void)
316{ 316{
317 void __iomem *reg = s5p_timer_reg(); 317 void __iomem *reg = samsung_timer_reg();
318 318
319 if (!reg) 319 if (!reg)
320 return 0; 320 return 0;
@@ -322,29 +322,29 @@ static u32 notrace s5p_read_sched_clock(void)
322 return ~__raw_readl(reg); 322 return ~__raw_readl(reg);
323} 323}
324 324
325static void __init s5p_clocksource_init(void) 325static void __init samsung_clocksource_init(void)
326{ 326{
327 unsigned long pclk; 327 unsigned long pclk;
328 unsigned long clock_rate; 328 unsigned long clock_rate;
329 329
330 pclk = clk_get_rate(timerclk); 330 pclk = clk_get_rate(timerclk);
331 331
332 clk_set_rate(tdiv_source, pclk / 2); 332 clk_set_rate(tdiv_source, pclk / TDIV);
333 clk_set_parent(tin_source, tdiv_source); 333 clk_set_parent(tin_source, tdiv_source);
334 334
335 clock_rate = clk_get_rate(tin_source); 335 clock_rate = clk_get_rate(tin_source);
336 336
337 s5p_time_setup(timer_source.source_id, TCNT_MAX); 337 samsung_time_setup(timer_source.source_id, TCNT_MAX);
338 s5p_time_start(timer_source.source_id, PERIODIC); 338 samsung_time_start(timer_source.source_id, PERIODIC);
339 339
340 setup_sched_clock(s5p_read_sched_clock, 32, clock_rate); 340 setup_sched_clock(samsung_read_sched_clock, TSIZE, clock_rate);
341 341
342 if (clocksource_mmio_init(s5p_timer_reg(), "s5p_clocksource_timer", 342 if (clocksource_mmio_init(samsung_timer_reg(), "samsung_clocksource_timer",
343 clock_rate, 250, 32, clocksource_mmio_readl_down)) 343 clock_rate, 250, TSIZE, clocksource_mmio_readl_down))
344 panic("s5p_clocksource_timer: can't register clocksource\n"); 344 panic("samsung_clocksource_timer: can't register clocksource\n");
345} 345}
346 346
347static void __init s5p_timer_resources(void) 347static void __init samsung_timer_resources(void)
348{ 348{
349 349
350 unsigned long event_id = timer_source.event_id; 350 unsigned long event_id = timer_source.event_id;
@@ -386,9 +386,9 @@ static void __init s5p_timer_resources(void)
386 clk_enable(tin_source); 386 clk_enable(tin_source);
387} 387}
388 388
389void __init s5p_timer_init(void) 389void __init samsung_timer_init(void)
390{ 390{
391 s5p_timer_resources(); 391 samsung_timer_resources();
392 s5p_clockevent_init(); 392 samsung_clockevent_init();
393 s5p_clocksource_init(); 393 samsung_clocksource_init();
394} 394}
diff --git a/arch/arm/plat-samsung/time.c b/arch/arm/plat-samsung/time.c
deleted file mode 100644
index 73defd00c3e4..000000000000
--- a/arch/arm/plat-samsung/time.c
+++ /dev/null
@@ -1,287 +0,0 @@
1/* linux/arch/arm/plat-samsung/time.c
2 *
3 * Copyright (C) 2003-2005 Simtec Electronics
4 * Ben Dooks, <ben@simtec.co.uk>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 */
20
21#include <linux/kernel.h>
22#include <linux/sched.h>
23#include <linux/init.h>
24#include <linux/interrupt.h>
25#include <linux/irq.h>
26#include <linux/err.h>
27#include <linux/clk.h>
28#include <linux/io.h>
29#include <linux/platform_device.h>
30#include <linux/syscore_ops.h>
31
32#include <asm/mach-types.h>
33
34#include <asm/irq.h>
35#include <mach/map.h>
36#include <plat/regs-timer.h>
37#include <mach/regs-irq.h>
38#include <asm/mach/time.h>
39#include <mach/tick.h>
40
41#include <plat/clock.h>
42#include <plat/cpu.h>
43
44static unsigned long timer_startval;
45static unsigned long timer_usec_ticks;
46
47#ifndef TICK_MAX
48#define TICK_MAX (0xffff)
49#endif
50
51#define TIMER_USEC_SHIFT 16
52
53/* we use the shifted arithmetic to work out the ratio of timer ticks
54 * to usecs, as often the peripheral clock is not a nice even multiple
55 * of 1MHz.
56 *
57 * shift of 14 and 15 are too low for the 12MHz, 16 seems to be ok
58 * for the current HZ value of 200 without producing overflows.
59 *
60 * Original patch by Dimitry Andric, updated by Ben Dooks
61*/
62
63
64/* timer_mask_usec_ticks
65 *
66 * given a clock and divisor, make the value to pass into timer_ticks_to_usec
67 * to scale the ticks into usecs
68*/
69
70static inline unsigned long
71timer_mask_usec_ticks(unsigned long scaler, unsigned long pclk)
72{
73 unsigned long den = pclk / 1000;
74
75 return ((1000 << TIMER_USEC_SHIFT) * scaler + (den >> 1)) / den;
76}
77
78/* timer_ticks_to_usec
79 *
80 * convert timer ticks to usec.
81*/
82
83static inline unsigned long timer_ticks_to_usec(unsigned long ticks)
84{
85 unsigned long res;
86
87 res = ticks * timer_usec_ticks;
88 res += 1 << (TIMER_USEC_SHIFT - 4); /* round up slightly */
89
90 return res >> TIMER_USEC_SHIFT;
91}
92
93/***
94 * Returns microsecond since last clock interrupt. Note that interrupts
95 * will have been disabled by do_gettimeoffset()
96 * IRQs are disabled before entering here from do_gettimeofday()
97 */
98
99static u32 s3c2410_gettimeoffset(void)
100{
101 unsigned long tdone;
102 unsigned long tval;
103
104 /* work out how many ticks have gone since last timer interrupt */
105
106 tval = __raw_readl(S3C2410_TCNTO(4));
107 tdone = timer_startval - tval;
108
109 /* check to see if there is an interrupt pending */
110
111 if (s3c24xx_ostimer_pending()) {
112 /* re-read the timer, and try and fix up for the missed
113 * interrupt. Note, the interrupt may go off before the
114 * timer has re-loaded from wrapping.
115 */
116
117 tval = __raw_readl(S3C2410_TCNTO(4));
118 tdone = timer_startval - tval;
119
120 if (tval != 0)
121 tdone += timer_startval;
122 }
123
124 return timer_ticks_to_usec(tdone) * 1000;
125}
126
127
128/*
129 * IRQ handler for the timer
130 */
131static irqreturn_t
132s3c2410_timer_interrupt(int irq, void *dev_id)
133{
134 timer_tick();
135 return IRQ_HANDLED;
136}
137
138static struct irqaction s3c2410_timer_irq = {
139 .name = "S3C2410 Timer Tick",
140 .flags = IRQF_DISABLED | IRQF_TIMER | IRQF_IRQPOLL,
141 .handler = s3c2410_timer_interrupt,
142};
143
144#define use_tclk1_12() ( \
145 machine_is_bast() || \
146 machine_is_vr1000() || \
147 machine_is_anubis() || \
148 machine_is_osiris())
149
150static struct clk *tin;
151static struct clk *tdiv;
152static struct clk *timerclk;
153
154/*
155 * Set up timer interrupt, and return the current time in seconds.
156 *
157 * Currently we only use timer4, as it is the only timer which has no
158 * other function that can be exploited externally
159 */
160static void s3c2410_timer_setup (void)
161{
162 unsigned long tcon;
163 unsigned long tcnt;
164 unsigned long tcfg1;
165 unsigned long tcfg0;
166
167 tcnt = TICK_MAX; /* default value for tcnt */
168
169 /* configure the system for whichever machine is in use */
170
171 if (use_tclk1_12()) {
172 /* timer is at 12MHz, scaler is 1 */
173 timer_usec_ticks = timer_mask_usec_ticks(1, 12000000);
174 tcnt = 12000000 / HZ;
175
176 tcfg1 = __raw_readl(S3C2410_TCFG1);
177 tcfg1 &= ~S3C2410_TCFG1_MUX4_MASK;
178 tcfg1 |= S3C2410_TCFG1_MUX4_TCLK1;
179 __raw_writel(tcfg1, S3C2410_TCFG1);
180 } else {
181 unsigned long pclk;
182 struct clk *tscaler;
183
184 /* for the h1940 (and others), we use the pclk from the core
185 * to generate the timer values. since values around 50 to
186 * 70MHz are not values we can directly generate the timer
187 * value from, we need to pre-scale and divide before using it.
188 *
189 * for instance, using 50.7MHz and dividing by 6 gives 8.45MHz
190 * (8.45 ticks per usec)
191 */
192
193 pclk = clk_get_rate(timerclk);
194
195 /* configure clock tick */
196
197 timer_usec_ticks = timer_mask_usec_ticks(6, pclk);
198
199 tscaler = clk_get_parent(tdiv);
200
201 clk_set_rate(tscaler, pclk / 3);
202 clk_set_rate(tdiv, pclk / 6);
203 clk_set_parent(tin, tdiv);
204
205 tcnt = clk_get_rate(tin) / HZ;
206 }
207
208 tcon = __raw_readl(S3C2410_TCON);
209 tcfg0 = __raw_readl(S3C2410_TCFG0);
210 tcfg1 = __raw_readl(S3C2410_TCFG1);
211
212 /* timers reload after counting zero, so reduce the count by 1 */
213
214 tcnt--;
215
216 printk(KERN_DEBUG "timer tcon=%08lx, tcnt %04lx, tcfg %08lx,%08lx, usec %08lx\n",
217 tcon, tcnt, tcfg0, tcfg1, timer_usec_ticks);
218
219 /* check to see if timer is within 16bit range... */
220 if (tcnt > TICK_MAX) {
221 panic("setup_timer: HZ is too small, cannot configure timer!");
222 return;
223 }
224
225 __raw_writel(tcfg1, S3C2410_TCFG1);
226 __raw_writel(tcfg0, S3C2410_TCFG0);
227
228 timer_startval = tcnt;
229 __raw_writel(tcnt, S3C2410_TCNTB(4));
230
231 /* ensure timer is stopped... */
232
233 tcon &= ~(7<<20);
234 tcon |= S3C2410_TCON_T4RELOAD;
235 tcon |= S3C2410_TCON_T4MANUALUPD;
236
237 __raw_writel(tcon, S3C2410_TCON);
238 __raw_writel(tcnt, S3C2410_TCNTB(4));
239 __raw_writel(tcnt, S3C2410_TCMPB(4));
240
241 /* start the timer running */
242 tcon |= S3C2410_TCON_T4START;
243 tcon &= ~S3C2410_TCON_T4MANUALUPD;
244 __raw_writel(tcon, S3C2410_TCON);
245}
246
247static void __init s3c2410_timer_resources(void)
248{
249 struct platform_device tmpdev;
250
251 tmpdev.dev.bus = &platform_bus_type;
252 tmpdev.id = 4;
253
254 timerclk = clk_get(NULL, "timers");
255 if (IS_ERR(timerclk))
256 panic("failed to get clock for system timer");
257
258 clk_enable(timerclk);
259
260 if (!use_tclk1_12()) {
261 tmpdev.id = 4;
262 tmpdev.dev.init_name = "s3c24xx-pwm.4";
263 tin = clk_get(&tmpdev.dev, "pwm-tin");
264 if (IS_ERR(tin))
265 panic("failed to get pwm-tin clock for system timer");
266
267 tdiv = clk_get(&tmpdev.dev, "pwm-tdiv");
268 if (IS_ERR(tdiv))
269 panic("failed to get pwm-tdiv clock for system timer");
270 }
271
272 clk_enable(tin);
273}
274
275static struct syscore_ops s3c24xx_syscore_ops = {
276 .resume = s3c2410_timer_setup,
277};
278
279void __init s3c24xx_timer_init(void)
280{
281 arch_gettimeoffset = s3c2410_gettimeoffset;
282
283 s3c2410_timer_resources();
284 s3c2410_timer_setup();
285 setup_irq(IRQ_TIMER4, &s3c2410_timer_irq);
286 register_syscore_ops(&s3c24xx_syscore_ops);
287}