aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/cpufreq
diff options
context:
space:
mode:
authorArnd Bergmann <arnd@arndb.de>2014-07-26 06:01:10 -0400
committerArnd Bergmann <arnd@arndb.de>2014-07-26 06:01:27 -0400
commit96bda115ec552ff75319f85828f6c333d101b401 (patch)
treee30895f65413fdf8fd91c026faad1a3fb54b0653 /drivers/cpufreq
parent8e5655cd4f7e140ceb24705f913406e9f56b7d54 (diff)
parentf1ff47454bb2fe0d5644f981679d1bea532816fd (diff)
Merge tag 's5pv210-dt' of git://git.kernel.org/pub/scm/linux/kernel/git/kgene/linux-samsung into next/soc
Merge "Samsung S5PV210 DT support for v3.17" from Kukjin Kim: - support common clock framework for s5pv210 clock - add generic PHY driver on s5pv210 to support it via DT - add dt support for s5pv210-goni, smdkc110, smdkv210 and torbreck boards - remove board files from mach-s5pv210 and unused codes - enable multiplatform for s5pv210 * tag 's5pv210-dt' of git://git.kernel.org/pub/scm/linux/kernel/git/kgene/linux-samsung: clk: samsung: s5pv210: Remove legacy board support ARM: SAMSUNG: Remove remaining legacy code gpio: samsung: Remove legacy support of S5PV210 ARM: S5PV210: Enable multi-platform build support cpufreq: s5pv210: Make the driver multiplatform aware ARM: S5PV210: Register cpufreq platform device ARM: S5PV210: move debug-macro.S into the common space ARM: S5PV210: Untie PM support from legacy code ARM: S5PV210: Remove support for board files ARM: dts: Add Device tree for s5pc110/s5pv210 boards ARM: dts: Add Device tree for s5pv210 SoC ARM: S5PV210: Add board file for boot using Device Tree phy: Add support for S5PV210 to the Exynos USB 2.0 PHY driver clk: samsung: Add S5PV210 Audio Subsystem clock driver ARM: SAMSUNG: Remove legacy clock code serial: samsung: Remove support for legacy clock code cpufreq: s3c24xx: Remove some dead code ARM: S5PV210: Migrate clock handling to Common Clock Framework clk: samsung: Add clock driver for S5PV210 and compatible SoCs Signed-off-by: Arnd Bergmann <arnd@arndb.de>
Diffstat (limited to 'drivers/cpufreq')
-rw-r--r--drivers/cpufreq/s3c2410-cpufreq.c2
-rw-r--r--drivers/cpufreq/s3c2412-cpufreq.c3
-rw-r--r--drivers/cpufreq/s3c2440-cpufreq.c3
-rw-r--r--drivers/cpufreq/s3c24xx-cpufreq.c1
-rw-r--r--drivers/cpufreq/s5pv210-cpufreq.c131
5 files changed, 122 insertions, 18 deletions
diff --git a/drivers/cpufreq/s3c2410-cpufreq.c b/drivers/cpufreq/s3c2410-cpufreq.c
index cfa0dd8723ec..b8e5da8e188b 100644
--- a/drivers/cpufreq/s3c2410-cpufreq.c
+++ b/drivers/cpufreq/s3c2410-cpufreq.c
@@ -26,7 +26,6 @@
26#include <mach/regs-clock.h> 26#include <mach/regs-clock.h>
27 27
28#include <plat/cpu.h> 28#include <plat/cpu.h>
29#include <plat/clock.h>
30#include <plat/cpu-freq-core.h> 29#include <plat/cpu-freq-core.h>
31 30
32/* Note, 2410A has an extra mode for 1:4:4 ratio, bit 2 of CLKDIV */ 31/* Note, 2410A has an extra mode for 1:4:4 ratio, bit 2 of CLKDIV */
@@ -104,7 +103,6 @@ static struct s3c_cpufreq_info s3c2410_cpufreq_info = {
104 .calc_iotiming = s3c2410_iotiming_calc, 103 .calc_iotiming = s3c2410_iotiming_calc,
105 .set_iotiming = s3c2410_iotiming_set, 104 .set_iotiming = s3c2410_iotiming_set,
106 .get_iotiming = s3c2410_iotiming_get, 105 .get_iotiming = s3c2410_iotiming_get,
107 .resume_clocks = s3c2410_setup_clocks,
108 106
109 .set_fvco = s3c2410_set_fvco, 107 .set_fvco = s3c2410_set_fvco,
110 .set_refresh = s3c2410_cpufreq_setrefresh, 108 .set_refresh = s3c2410_cpufreq_setrefresh,
diff --git a/drivers/cpufreq/s3c2412-cpufreq.c b/drivers/cpufreq/s3c2412-cpufreq.c
index 4645b4898996..eb262133fef2 100644
--- a/drivers/cpufreq/s3c2412-cpufreq.c
+++ b/drivers/cpufreq/s3c2412-cpufreq.c
@@ -28,7 +28,6 @@
28#include <mach/s3c2412.h> 28#include <mach/s3c2412.h>
29 29
30#include <plat/cpu.h> 30#include <plat/cpu.h>
31#include <plat/clock.h>
32#include <plat/cpu-freq-core.h> 31#include <plat/cpu-freq-core.h>
33 32
34/* our clock resources. */ 33/* our clock resources. */
@@ -188,8 +187,6 @@ static struct s3c_cpufreq_info s3c2412_cpufreq_info = {
188 .set_iotiming = s3c2412_iotiming_set, 187 .set_iotiming = s3c2412_iotiming_set,
189 .get_iotiming = s3c2412_iotiming_get, 188 .get_iotiming = s3c2412_iotiming_get,
190 189
191 .resume_clocks = s3c2412_setup_clocks,
192
193 .debug_io_show = s3c_cpufreq_debugfs_call(s3c2412_iotiming_debugfs), 190 .debug_io_show = s3c_cpufreq_debugfs_call(s3c2412_iotiming_debugfs),
194}; 191};
195 192
diff --git a/drivers/cpufreq/s3c2440-cpufreq.c b/drivers/cpufreq/s3c2440-cpufreq.c
index f84ed10755b5..0129f5c70a61 100644
--- a/drivers/cpufreq/s3c2440-cpufreq.c
+++ b/drivers/cpufreq/s3c2440-cpufreq.c
@@ -29,7 +29,6 @@
29 29
30#include <plat/cpu.h> 30#include <plat/cpu.h>
31#include <plat/cpu-freq-core.h> 31#include <plat/cpu-freq-core.h>
32#include <plat/clock.h>
33 32
34static struct clk *xtal; 33static struct clk *xtal;
35static struct clk *fclk; 34static struct clk *fclk;
@@ -262,8 +261,6 @@ static struct s3c_cpufreq_info s3c2440_cpufreq_info = {
262 .calc_divs = s3c2440_cpufreq_calcdivs, 261 .calc_divs = s3c2440_cpufreq_calcdivs,
263 .calc_freqtable = s3c2440_cpufreq_calctable, 262 .calc_freqtable = s3c2440_cpufreq_calctable,
264 263
265 .resume_clocks = s3c244x_setup_clocks,
266
267 .debug_io_show = s3c_cpufreq_debugfs_call(s3c2410_iotiming_debugfs), 264 .debug_io_show = s3c_cpufreq_debugfs_call(s3c2410_iotiming_debugfs),
268}; 265};
269 266
diff --git a/drivers/cpufreq/s3c24xx-cpufreq.c b/drivers/cpufreq/s3c24xx-cpufreq.c
index 227ebf7c1eea..d00f1cee4509 100644
--- a/drivers/cpufreq/s3c24xx-cpufreq.c
+++ b/drivers/cpufreq/s3c24xx-cpufreq.c
@@ -27,7 +27,6 @@
27#include <asm/mach/map.h> 27#include <asm/mach/map.h>
28 28
29#include <plat/cpu.h> 29#include <plat/cpu.h>
30#include <plat/clock.h>
31#include <plat/cpu-freq-core.h> 30#include <plat/cpu-freq-core.h>
32 31
33#include <mach/regs-clock.h> 32#include <mach/regs-clock.h>
diff --git a/drivers/cpufreq/s5pv210-cpufreq.c b/drivers/cpufreq/s5pv210-cpufreq.c
index 19a10b89fef7..9a68225a757e 100644
--- a/drivers/cpufreq/s5pv210-cpufreq.c
+++ b/drivers/cpufreq/s5pv210-cpufreq.c
@@ -16,11 +16,70 @@
16#include <linux/clk.h> 16#include <linux/clk.h>
17#include <linux/io.h> 17#include <linux/io.h>
18#include <linux/cpufreq.h> 18#include <linux/cpufreq.h>
19#include <linux/of.h>
20#include <linux/of_address.h>
21#include <linux/platform_device.h>
19#include <linux/reboot.h> 22#include <linux/reboot.h>
20#include <linux/regulator/consumer.h> 23#include <linux/regulator/consumer.h>
21 24
22#include <mach/map.h> 25static void __iomem *clk_base;
23#include <mach/regs-clock.h> 26static void __iomem *dmc_base[2];
27
28#define S5P_CLKREG(x) (clk_base + (x))
29
30#define S5P_APLL_LOCK S5P_CLKREG(0x00)
31#define S5P_APLL_CON S5P_CLKREG(0x100)
32#define S5P_CLK_SRC0 S5P_CLKREG(0x200)
33#define S5P_CLK_SRC2 S5P_CLKREG(0x208)
34#define S5P_CLK_DIV0 S5P_CLKREG(0x300)
35#define S5P_CLK_DIV2 S5P_CLKREG(0x308)
36#define S5P_CLK_DIV6 S5P_CLKREG(0x318)
37#define S5P_CLKDIV_STAT0 S5P_CLKREG(0x1000)
38#define S5P_CLKDIV_STAT1 S5P_CLKREG(0x1004)
39#define S5P_CLKMUX_STAT0 S5P_CLKREG(0x1100)
40#define S5P_CLKMUX_STAT1 S5P_CLKREG(0x1104)
41
42#define S5P_ARM_MCS_CON S5P_CLKREG(0x6100)
43
44/* CLKSRC0 */
45#define S5P_CLKSRC0_MUX200_SHIFT (16)
46#define S5P_CLKSRC0_MUX200_MASK (0x1 << S5P_CLKSRC0_MUX200_SHIFT)
47#define S5P_CLKSRC0_MUX166_MASK (0x1<<20)
48#define S5P_CLKSRC0_MUX133_MASK (0x1<<24)
49
50/* CLKSRC2 */
51#define S5P_CLKSRC2_G3D_SHIFT (0)
52#define S5P_CLKSRC2_G3D_MASK (0x3 << S5P_CLKSRC2_G3D_SHIFT)
53#define S5P_CLKSRC2_MFC_SHIFT (4)
54#define S5P_CLKSRC2_MFC_MASK (0x3 << S5P_CLKSRC2_MFC_SHIFT)
55
56/* CLKDIV0 */
57#define S5P_CLKDIV0_APLL_SHIFT (0)
58#define S5P_CLKDIV0_APLL_MASK (0x7 << S5P_CLKDIV0_APLL_SHIFT)
59#define S5P_CLKDIV0_A2M_SHIFT (4)
60#define S5P_CLKDIV0_A2M_MASK (0x7 << S5P_CLKDIV0_A2M_SHIFT)
61#define S5P_CLKDIV0_HCLK200_SHIFT (8)
62#define S5P_CLKDIV0_HCLK200_MASK (0x7 << S5P_CLKDIV0_HCLK200_SHIFT)
63#define S5P_CLKDIV0_PCLK100_SHIFT (12)
64#define S5P_CLKDIV0_PCLK100_MASK (0x7 << S5P_CLKDIV0_PCLK100_SHIFT)
65#define S5P_CLKDIV0_HCLK166_SHIFT (16)
66#define S5P_CLKDIV0_HCLK166_MASK (0xF << S5P_CLKDIV0_HCLK166_SHIFT)
67#define S5P_CLKDIV0_PCLK83_SHIFT (20)
68#define S5P_CLKDIV0_PCLK83_MASK (0x7 << S5P_CLKDIV0_PCLK83_SHIFT)
69#define S5P_CLKDIV0_HCLK133_SHIFT (24)
70#define S5P_CLKDIV0_HCLK133_MASK (0xF << S5P_CLKDIV0_HCLK133_SHIFT)
71#define S5P_CLKDIV0_PCLK66_SHIFT (28)
72#define S5P_CLKDIV0_PCLK66_MASK (0x7 << S5P_CLKDIV0_PCLK66_SHIFT)
73
74/* CLKDIV2 */
75#define S5P_CLKDIV2_G3D_SHIFT (0)
76#define S5P_CLKDIV2_G3D_MASK (0xF << S5P_CLKDIV2_G3D_SHIFT)
77#define S5P_CLKDIV2_MFC_SHIFT (4)
78#define S5P_CLKDIV2_MFC_MASK (0xF << S5P_CLKDIV2_MFC_SHIFT)
79
80/* CLKDIV6 */
81#define S5P_CLKDIV6_ONEDRAM_SHIFT (28)
82#define S5P_CLKDIV6_ONEDRAM_MASK (0xF << S5P_CLKDIV6_ONEDRAM_SHIFT)
24 83
25static struct clk *dmc0_clk; 84static struct clk *dmc0_clk;
26static struct clk *dmc1_clk; 85static struct clk *dmc1_clk;
@@ -142,9 +201,9 @@ static void s5pv210_set_refresh(enum s5pv210_dmc_port ch, unsigned long freq)
142 void __iomem *reg = NULL; 201 void __iomem *reg = NULL;
143 202
144 if (ch == DMC0) { 203 if (ch == DMC0) {
145 reg = (S5P_VA_DMC0 + 0x30); 204 reg = (dmc_base[0] + 0x30);
146 } else if (ch == DMC1) { 205 } else if (ch == DMC1) {
147 reg = (S5P_VA_DMC1 + 0x30); 206 reg = (dmc_base[1] + 0x30);
148 } else { 207 } else {
149 printk(KERN_ERR "Cannot find DMC port\n"); 208 printk(KERN_ERR "Cannot find DMC port\n");
150 return; 209 return;
@@ -472,7 +531,7 @@ static int __init s5pv210_cpu_init(struct cpufreq_policy *policy)
472 * check_mem_type : This driver only support LPDDR & LPDDR2. 531 * check_mem_type : This driver only support LPDDR & LPDDR2.
473 * other memory type is not supported. 532 * other memory type is not supported.
474 */ 533 */
475 mem_type = check_mem_type(S5P_VA_DMC0); 534 mem_type = check_mem_type(dmc_base[0]);
476 535
477 if ((mem_type != LPDDR) && (mem_type != LPDDR2)) { 536 if ((mem_type != LPDDR) && (mem_type != LPDDR2)) {
478 printk(KERN_ERR "CPUFreq doesn't support this memory type\n"); 537 printk(KERN_ERR "CPUFreq doesn't support this memory type\n");
@@ -481,10 +540,10 @@ static int __init s5pv210_cpu_init(struct cpufreq_policy *policy)
481 } 540 }
482 541
483 /* Find current refresh counter and frequency each DMC */ 542 /* Find current refresh counter and frequency each DMC */
484 s5pv210_dram_conf[0].refresh = (__raw_readl(S5P_VA_DMC0 + 0x30) * 1000); 543 s5pv210_dram_conf[0].refresh = (__raw_readl(dmc_base[0] + 0x30) * 1000);
485 s5pv210_dram_conf[0].freq = clk_get_rate(dmc0_clk); 544 s5pv210_dram_conf[0].freq = clk_get_rate(dmc0_clk);
486 545
487 s5pv210_dram_conf[1].refresh = (__raw_readl(S5P_VA_DMC1 + 0x30) * 1000); 546 s5pv210_dram_conf[1].refresh = (__raw_readl(dmc_base[1] + 0x30) * 1000);
488 s5pv210_dram_conf[1].freq = clk_get_rate(dmc1_clk); 547 s5pv210_dram_conf[1].freq = clk_get_rate(dmc1_clk);
489 548
490 policy->suspend_freq = SLEEP_FREQ; 549 policy->suspend_freq = SLEEP_FREQ;
@@ -527,8 +586,55 @@ static struct notifier_block s5pv210_cpufreq_reboot_notifier = {
527 .notifier_call = s5pv210_cpufreq_reboot_notifier_event, 586 .notifier_call = s5pv210_cpufreq_reboot_notifier_event,
528}; 587};
529 588
530static int __init s5pv210_cpufreq_init(void) 589static int s5pv210_cpufreq_probe(struct platform_device *pdev)
531{ 590{
591 struct device_node *np;
592 int id;
593
594 /*
595 * HACK: This is a temporary workaround to get access to clock
596 * and DMC controller registers directly and remove static mappings
597 * and dependencies on platform headers. It is necessary to enable
598 * S5PV210 multi-platform support and will be removed together with
599 * this whole driver as soon as S5PV210 gets migrated to use
600 * cpufreq-cpu0 driver.
601 */
602 np = of_find_compatible_node(NULL, NULL, "samsung,s5pv210-clock");
603 if (!np) {
604 pr_err("%s: failed to find clock controller DT node\n",
605 __func__);
606 return -ENODEV;
607 }
608
609 clk_base = of_iomap(np, 0);
610 if (!clk_base) {
611 pr_err("%s: failed to map clock registers\n", __func__);
612 return -EFAULT;
613 }
614
615 for_each_compatible_node(np, NULL, "samsung,s5pv210-dmc") {
616 id = of_alias_get_id(np, "dmc");
617 if (id < 0 || id >= ARRAY_SIZE(dmc_base)) {
618 pr_err("%s: failed to get alias of dmc node '%s'\n",
619 __func__, np->name);
620 return id;
621 }
622
623 dmc_base[id] = of_iomap(np, 0);
624 if (!dmc_base[id]) {
625 pr_err("%s: failed to map dmc%d registers\n",
626 __func__, id);
627 return -EFAULT;
628 }
629 }
630
631 for (id = 0; id < ARRAY_SIZE(dmc_base); ++id) {
632 if (!dmc_base[id]) {
633 pr_err("%s: failed to find dmc%d node\n", __func__, id);
634 return -ENODEV;
635 }
636 }
637
532 arm_regulator = regulator_get(NULL, "vddarm"); 638 arm_regulator = regulator_get(NULL, "vddarm");
533 if (IS_ERR(arm_regulator)) { 639 if (IS_ERR(arm_regulator)) {
534 pr_err("failed to get regulator vddarm"); 640 pr_err("failed to get regulator vddarm");
@@ -547,4 +653,11 @@ static int __init s5pv210_cpufreq_init(void)
547 return cpufreq_register_driver(&s5pv210_driver); 653 return cpufreq_register_driver(&s5pv210_driver);
548} 654}
549 655
550late_initcall(s5pv210_cpufreq_init); 656static struct platform_driver s5pv210_cpufreq_platdrv = {
657 .driver = {
658 .name = "s5pv210-cpufreq",
659 .owner = THIS_MODULE,
660 },
661 .probe = s5pv210_cpufreq_probe,
662};
663module_platform_driver(s5pv210_cpufreq_platdrv);