diff options
-rw-r--r-- | arch/arm/configs/kirkwood_defconfig | 1 | ||||
-rw-r--r-- | arch/arm/mach-kirkwood/Makefile | 1 | ||||
-rw-r--r-- | arch/arm/mach-kirkwood/board-dt.c | 2 | ||||
-rw-r--r-- | arch/arm/mach-kirkwood/common.c | 23 | ||||
-rw-r--r-- | arch/arm/mach-kirkwood/common.h | 1 | ||||
-rw-r--r-- | arch/arm/mach-kirkwood/include/mach/kirkwood.h | 3 | ||||
-rw-r--r-- | drivers/cpuidle/Kconfig | 6 | ||||
-rw-r--r-- | drivers/cpuidle/Makefile | 1 | ||||
-rw-r--r-- | drivers/cpuidle/cpuidle-kirkwood.c (renamed from arch/arm/mach-kirkwood/cpuidle.c) | 45 |
9 files changed, 75 insertions, 8 deletions
diff --git a/arch/arm/configs/kirkwood_defconfig b/arch/arm/configs/kirkwood_defconfig index 93f3794ba5cb..13482ea58b09 100644 --- a/arch/arm/configs/kirkwood_defconfig +++ b/arch/arm/configs/kirkwood_defconfig @@ -56,6 +56,7 @@ CONFIG_AEABI=y CONFIG_ZBOOT_ROM_TEXT=0x0 CONFIG_ZBOOT_ROM_BSS=0x0 CONFIG_CPU_IDLE=y +CONFIG_CPU_IDLE_KIRKWOOD=y CONFIG_NET=y CONFIG_PACKET=y CONFIG_UNIX=y diff --git a/arch/arm/mach-kirkwood/Makefile b/arch/arm/mach-kirkwood/Makefile index 8d2e5a96247c..d6653095a1eb 100644 --- a/arch/arm/mach-kirkwood/Makefile +++ b/arch/arm/mach-kirkwood/Makefile @@ -19,7 +19,6 @@ obj-$(CONFIG_MACH_NET2BIG_V2) += netxbig_v2-setup.o lacie_v2-common.o obj-$(CONFIG_MACH_NET5BIG_V2) += netxbig_v2-setup.o lacie_v2-common.o obj-$(CONFIG_MACH_T5325) += t5325-setup.o -obj-$(CONFIG_CPU_IDLE) += cpuidle.o obj-$(CONFIG_ARCH_KIRKWOOD_DT) += board-dt.o obj-$(CONFIG_MACH_DREAMPLUG_DT) += board-dreamplug.o obj-$(CONFIG_MACH_ICONNECT_DT) += board-iconnect.o diff --git a/arch/arm/mach-kirkwood/board-dt.c b/arch/arm/mach-kirkwood/board-dt.c index de4fd2bb1e27..f964cdc44b1a 100644 --- a/arch/arm/mach-kirkwood/board-dt.c +++ b/arch/arm/mach-kirkwood/board-dt.c @@ -98,6 +98,8 @@ static void __init kirkwood_dt_init(void) /* Setup root of clk tree */ kirkwood_of_clk_init(); + kirkwood_cpuidle_init(); + #ifdef CONFIG_KEXEC kexec_reinit = kirkwood_enable_pcie; #endif diff --git a/arch/arm/mach-kirkwood/common.c b/arch/arm/mach-kirkwood/common.c index bac21a554c91..5ed1f2e8c5f8 100644 --- a/arch/arm/mach-kirkwood/common.c +++ b/arch/arm/mach-kirkwood/common.c @@ -499,6 +499,28 @@ void __init kirkwood_wdt_init(void) orion_wdt_init(); } +/***************************************************************************** + * CPU idle + ****************************************************************************/ +static struct resource kirkwood_cpuidle_resource[] = { + { + .flags = IORESOURCE_MEM, + .start = DDR_OPERATION_BASE, + .end = DDR_OPERATION_BASE + 3, + }, +}; + +static struct platform_device kirkwood_cpuidle = { + .name = "kirkwood_cpuidle", + .id = -1, + .resource = kirkwood_cpuidle_resource, + .num_resources = 1, +}; + +void __init kirkwood_cpuidle_init(void) +{ + platform_device_register(&kirkwood_cpuidle); +} /***************************************************************************** * Time handling @@ -671,6 +693,7 @@ void __init kirkwood_init(void) kirkwood_xor1_init(); kirkwood_crypto_init(); + kirkwood_cpuidle_init(); #ifdef CONFIG_KEXEC kexec_reinit = kirkwood_enable_pcie; #endif diff --git a/arch/arm/mach-kirkwood/common.h b/arch/arm/mach-kirkwood/common.h index 5ffa57f08c80..320aa61ff505 100644 --- a/arch/arm/mach-kirkwood/common.h +++ b/arch/arm/mach-kirkwood/common.h @@ -50,6 +50,7 @@ void kirkwood_nand_init(struct mtd_partition *parts, int nr_parts, int delay); void kirkwood_nand_init_rnb(struct mtd_partition *parts, int nr_parts, int (*dev_ready)(struct mtd_info *)); void kirkwood_audio_init(void); +void kirkwood_cpuidle_init(void); void kirkwood_restart(char, const char *); void kirkwood_clk_init(void); diff --git a/arch/arm/mach-kirkwood/include/mach/kirkwood.h b/arch/arm/mach-kirkwood/include/mach/kirkwood.h index 041653a04a9c..a05563a31c95 100644 --- a/arch/arm/mach-kirkwood/include/mach/kirkwood.h +++ b/arch/arm/mach-kirkwood/include/mach/kirkwood.h @@ -60,8 +60,9 @@ * Register Map */ #define DDR_VIRT_BASE (KIRKWOOD_REGS_VIRT_BASE + 0x00000) +#define DDR_PHYS_BASE (KIRKWOOD_REGS_PHYS_BASE + 0x00000) #define DDR_WINDOW_CPU_BASE (DDR_VIRT_BASE + 0x1500) -#define DDR_OPERATION_BASE (DDR_VIRT_BASE + 0x1418) +#define DDR_OPERATION_BASE (DDR_PHYS_BASE + 0x1418) #define DEV_BUS_PHYS_BASE (KIRKWOOD_REGS_PHYS_BASE + 0x10000) #define DEV_BUS_VIRT_BASE (KIRKWOOD_REGS_VIRT_BASE + 0x10000) diff --git a/drivers/cpuidle/Kconfig b/drivers/cpuidle/Kconfig index c4cc27e5c8a5..071e2c3eec4f 100644 --- a/drivers/cpuidle/Kconfig +++ b/drivers/cpuidle/Kconfig @@ -39,4 +39,10 @@ config CPU_IDLE_CALXEDA help Select this to enable cpuidle on Calxeda processors. +config CPU_IDLE_KIRKWOOD + bool "CPU Idle Driver for Kirkwood processors" + depends on ARCH_KIRKWOOD + help + Select this to enable cpuidle on Kirkwood processors. + endif diff --git a/drivers/cpuidle/Makefile b/drivers/cpuidle/Makefile index 03ee87482c71..24c6e7d945ed 100644 --- a/drivers/cpuidle/Makefile +++ b/drivers/cpuidle/Makefile @@ -6,3 +6,4 @@ obj-y += cpuidle.o driver.o governor.o sysfs.o governors/ obj-$(CONFIG_ARCH_NEEDS_CPU_IDLE_COUPLED) += coupled.o obj-$(CONFIG_CPU_IDLE_CALXEDA) += cpuidle-calxeda.o +obj-$(CONFIG_CPU_IDLE_KIRKWOOD) += cpuidle-kirkwood.o diff --git a/arch/arm/mach-kirkwood/cpuidle.c b/drivers/cpuidle/cpuidle-kirkwood.c index f7304670f2f8..670aa1e55cd6 100644 --- a/arch/arm/mach-kirkwood/cpuidle.c +++ b/drivers/cpuidle/cpuidle-kirkwood.c @@ -14,6 +14,7 @@ */ #include <linux/kernel.h> +#include <linux/module.h> #include <linux/init.h> #include <linux/platform_device.h> #include <linux/cpuidle.h> @@ -21,16 +22,17 @@ #include <linux/export.h> #include <asm/proc-fns.h> #include <asm/cpuidle.h> -#include <mach/kirkwood.h> #define KIRKWOOD_MAX_STATES 2 +static void __iomem *ddr_operation_base; + /* Actual code that puts the SoC in different idle states */ static int kirkwood_enter_idle(struct cpuidle_device *dev, - struct cpuidle_driver *drv, + struct cpuidle_driver *drv, int index) { - writel(0x7, DDR_OPERATION_BASE); + writel(0x7, ddr_operation_base); cpu_do_idle(); return index; @@ -51,13 +53,22 @@ static struct cpuidle_driver kirkwood_idle_driver = { }, .state_count = KIRKWOOD_MAX_STATES, }; +static struct cpuidle_device *device; static DEFINE_PER_CPU(struct cpuidle_device, kirkwood_cpuidle_device); /* Initialize CPU idle by registering the idle states */ -static int kirkwood_init_cpuidle(void) +static int kirkwood_cpuidle_probe(struct platform_device *pdev) { - struct cpuidle_device *device; + struct resource *res; + + res = platform_get_resource(pdev, IORESOURCE_MEM, 0); + if (res == NULL) + return -EINVAL; + + ddr_operation_base = devm_request_and_ioremap(&pdev->dev, res); + if (!ddr_operation_base) + return -EADDRNOTAVAIL; device = &per_cpu(kirkwood_cpuidle_device, smp_processor_id()); device->state_count = KIRKWOOD_MAX_STATES; @@ -70,4 +81,26 @@ static int kirkwood_init_cpuidle(void) return 0; } -device_initcall(kirkwood_init_cpuidle); +int kirkwood_cpuidle_remove(struct platform_device *pdev) +{ + cpuidle_unregister_device(device); + cpuidle_unregister_driver(&kirkwood_idle_driver); + + return 0; +} + +static struct platform_driver kirkwood_cpuidle_driver = { + .probe = kirkwood_cpuidle_probe, + .remove = kirkwood_cpuidle_remove, + .driver = { + .name = "kirkwood_cpuidle", + .owner = THIS_MODULE, + }, +}; + +module_platform_driver(kirkwood_cpuidle_driver); + +MODULE_AUTHOR("Andrew Lunn <andrew@lunn.ch>"); +MODULE_DESCRIPTION("Kirkwood cpu idle driver"); +MODULE_LICENSE("GPL v2"); +MODULE_ALIAS("platform:kirkwood-cpuidle"); |