* [PATCHv5 1/4] ARM: mx50: Add support to get the silicon revision @ 2011-03-21 21:30 Dinh.Nguyen at freescale.com 2011-03-21 21:30 ` [PATCHv5 2/4] ARM: mx51: Add entry for gpc_dvfs_clk Dinh.Nguyen at freescale.com 0 siblings, 1 reply; 5+ messages in thread From: Dinh.Nguyen at freescale.com @ 2011-03-21 21:30 UTC (permalink / raw) To: linux-arm-kernel From: Dinh Nguyen <Dinh.Nguyen@freescale.com> For MX50, the HW_ADADIG_DIGPROG register in the ANATOP module will have the correct silicon revision: Major Minor Description 0x50 0x0 TO1.0 0x50 0x1 TO1.1 Signed-off-by: Dinh Nguyen <Dinh.Nguyen@freescale.com> --- arch/arm/mach-mx5/cpu.c | 39 +++++++++++++++++++++++++++++++++ arch/arm/plat-mxc/include/mach/mx50.h | 4 +++ 2 files changed, 43 insertions(+), 0 deletions(-) diff --git a/arch/arm/mach-mx5/cpu.c b/arch/arm/mach-mx5/cpu.c index df46b5e..c205494 100644 --- a/arch/arm/mach-mx5/cpu.c +++ b/arch/arm/mach-mx5/cpu.c @@ -21,6 +21,7 @@ static int cpu_silicon_rev = -1; #define IIM_SREV 0x24 +#define MX50_HW_ADADIG_DIGPROG 0xB0 static int get_mx51_srev(void) { @@ -107,6 +108,44 @@ int mx53_revision(void) } EXPORT_SYMBOL(mx53_revision); +static int get_mx50_srev(void) +{ + void __iomem *anatop = ioremap(MX50_ANATOP_BASE_ADDR, SZ_8K); + u32 rev; + + if (!anatop) { + cpu_silicon_rev = -EINVAL; + return 0; + } + + rev = readl(anatop + MX50_HW_ADADIG_DIGPROG); + rev &= 0xff; + + iounmap(anatop); + if (rev == 0x0) + return IMX_CHIP_REVISION_1_0; + else if (rev == 0x1) + return IMX_CHIP_REVISION_1_1; + return 0; +} + +/* + * Returns: + * the silicon revision of the cpu + * -EINVAL - not a mx50 + */ +int mx50_revision(void) +{ + if (!cpu_is_mx50()) + return -EINVAL; + + if (cpu_silicon_rev == -1) + cpu_silicon_rev = get_mx50_srev(); + + return cpu_silicon_rev; +} +EXPORT_SYMBOL(mx50_revision); + static int __init post_cpu_init(void) { unsigned int reg; diff --git a/arch/arm/plat-mxc/include/mach/mx50.h b/arch/arm/plat-mxc/include/mach/mx50.h index aaec2a6..5f2da75 100644 --- a/arch/arm/plat-mxc/include/mach/mx50.h +++ b/arch/arm/plat-mxc/include/mach/mx50.h @@ -282,4 +282,8 @@ #define MX50_INT_APBHDMA_CHAN6 116 #define MX50_INT_APBHDMA_CHAN7 117 +#if !defined(__ASSEMBLY__) && !defined(__MXC_BOOT_UNCOMPRESS) +extern int mx50_revision(void); +#endif + #endif /* ifndef __MACH_MX50_H__ */ -- 1.6.0.4 ^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCHv5 2/4] ARM: mx51: Add entry for gpc_dvfs_clk 2011-03-21 21:30 [PATCHv5 1/4] ARM: mx50: Add support to get the silicon revision Dinh.Nguyen at freescale.com @ 2011-03-21 21:30 ` Dinh.Nguyen at freescale.com 2011-03-21 21:30 ` [PATCHv5 3/4] ARM: mx51: Implement code to allow mx51 to enter WFI Dinh.Nguyen at freescale.com 0 siblings, 1 reply; 5+ messages in thread From: Dinh.Nguyen at freescale.com @ 2011-03-21 21:30 UTC (permalink / raw) To: linux-arm-kernel From: Dinh Nguyen <Dinh.Nguyen@freescale.com> For MX51 SRPG, we need to turn on the GPC clock in order to set the SRPG registers. Signed-off-by: Dinh Nguyen <Dinh.Nguyen@freescale.com> --- arch/arm/mach-mx5/clock-mx51-mx53.c | 8 ++++++++ 1 files changed, 8 insertions(+), 0 deletions(-) diff --git a/arch/arm/mach-mx5/clock-mx51-mx53.c b/arch/arm/mach-mx5/clock-mx51-mx53.c index 652ace4..3eb1c6e 100644 --- a/arch/arm/mach-mx5/clock-mx51-mx53.c +++ b/arch/arm/mach-mx5/clock-mx51-mx53.c @@ -865,6 +865,13 @@ static struct clk aips_tz2_clk = { .disable = _clk_ccgr_disable_inwait, }; +static struct clk gpc_dvfs_clk = { + .enable_reg = MXC_CCM_CCGR5, + .enable_shift = MXC_CCM_CCGRx_CG12_OFFSET, + .enable = _clk_ccgr_enable, + .disable = _clk_ccgr_disable, +}; + static struct clk gpt_32k_clk = { .id = 0, .parent = &ckil_clk, @@ -1448,6 +1455,7 @@ static struct clk_lookup mx51_lookups[] = { _REGISTER_CLOCK("imx-ipuv3", NULL, ipu_clk) _REGISTER_CLOCK("imx-ipuv3", "di0", ipu_di0_clk) _REGISTER_CLOCK("imx-ipuv3", "di1", ipu_di1_clk) + _REGISTER_CLOCK(NULL, "gpc_dvfs", gpc_dvfs_clk) }; static struct clk_lookup mx53_lookups[] = { -- 1.6.0.4 ^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCHv5 3/4] ARM: mx51: Implement code to allow mx51 to enter WFI 2011-03-21 21:30 ` [PATCHv5 2/4] ARM: mx51: Add entry for gpc_dvfs_clk Dinh.Nguyen at freescale.com @ 2011-03-21 21:30 ` Dinh.Nguyen at freescale.com 2011-03-21 21:30 ` [PATCHv5 4/4] ARM: mx51: Add support for low power suspend on MX51 Dinh.Nguyen at freescale.com 0 siblings, 1 reply; 5+ messages in thread From: Dinh.Nguyen at freescale.com @ 2011-03-21 21:30 UTC (permalink / raw) To: linux-arm-kernel From: Dinh Nguyen <Dinh.Nguyen@freescale.com> Implement code for MX51 that allows the SoC to enter WFI when arch_idle is called. This patch is also necessary for correctly suspending the system. Signed-off-by: Dinh Nguyen <Dinh.Nguyen@freescale.com> --- arch/arm/mach-mx5/Makefile | 2 +- arch/arm/mach-mx5/system.c | 85 +++++++++++++++++++++++++++++++ arch/arm/plat-mxc/include/mach/mxc.h | 9 +++ arch/arm/plat-mxc/include/mach/system.h | 6 ++- 4 files changed, 100 insertions(+), 2 deletions(-) create mode 100644 arch/arm/mach-mx5/system.c diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile index 4f63048..0b9338c 100644 --- a/arch/arm/mach-mx5/Makefile +++ b/arch/arm/mach-mx5/Makefile @@ -3,7 +3,7 @@ # # Object file lists. -obj-y := cpu.o mm.o clock-mx51-mx53.o devices.o ehci.o +obj-y := cpu.o mm.o clock-mx51-mx53.o devices.o ehci.o system.o obj-$(CONFIG_SOC_IMX50) += mm-mx50.o obj-$(CONFIG_CPU_FREQ_IMX) += cpu_op-mx51.o diff --git a/arch/arm/mach-mx5/system.c b/arch/arm/mach-mx5/system.c new file mode 100644 index 0000000..f09c17f --- /dev/null +++ b/arch/arm/mach-mx5/system.c @@ -0,0 +1,85 @@ +/* + * Copyright (C) 2011 Freescale Semiconductor, Inc. All Rights Reserved. + */ + +/* + * The code contained herein is licensed under the GNU General Public + * License. You may obtain a copy of the GNU General Public License + * Version 2 or later at the following locations: + * + * http://www.opensource.org/licenses/gpl-license.html + * http://www.gnu.org/copyleft/gpl.html + */ +#include <linux/platform_device.h> +#include <linux/io.h> +#include <mach/hardware.h> +#include "crm_regs.h" + +/* set cpu low power mode before WFI instruction. This function is called + * mx5 because it can be used for mx50, mx51, and mx53.*/ +void mx5_cpu_lp_set(enum mxc_cpu_pwr_mode mode) +{ + u32 plat_lpc, arm_srpgcr, ccm_clpcr; + u32 empgc0, empgc1; + int stop_mode = 0; + + /* always allow platform to issue a deep sleep mode request */ + plat_lpc = __raw_readl(MXC_CORTEXA8_PLAT_LPC) & + ~(MXC_CORTEXA8_PLAT_LPC_DSM); + ccm_clpcr = __raw_readl(MXC_CCM_CLPCR) & ~(MXC_CCM_CLPCR_LPM_MASK); + arm_srpgcr = __raw_readl(MXC_SRPG_ARM_SRPGCR) & ~(MXC_SRPGCR_PCR); + empgc0 = __raw_readl(MXC_SRPG_EMPGC0_SRPGCR) & ~(MXC_SRPGCR_PCR); + empgc1 = __raw_readl(MXC_SRPG_EMPGC1_SRPGCR) & ~(MXC_SRPGCR_PCR); + + switch (mode) { + case WAIT_CLOCKED: + break; + case WAIT_UNCLOCKED: + ccm_clpcr |= 0x1 << MXC_CCM_CLPCR_LPM_OFFSET; + break; + case WAIT_UNCLOCKED_POWER_OFF: + case STOP_POWER_OFF: + plat_lpc |= MXC_CORTEXA8_PLAT_LPC_DSM + | MXC_CORTEXA8_PLAT_LPC_DBG_DSM; + if (mode == WAIT_UNCLOCKED_POWER_OFF) { + ccm_clpcr |= 0x1 << MXC_CCM_CLPCR_LPM_OFFSET; + ccm_clpcr &= ~MXC_CCM_CLPCR_VSTBY; + ccm_clpcr &= ~MXC_CCM_CLPCR_SBYOS; + stop_mode = 0; + } else { + ccm_clpcr |= 0x2 << MXC_CCM_CLPCR_LPM_OFFSET; + ccm_clpcr |= 0x3 << MXC_CCM_CLPCR_STBY_COUNT_OFFSET; + ccm_clpcr |= MXC_CCM_CLPCR_VSTBY; + ccm_clpcr |= MXC_CCM_CLPCR_SBYOS; + stop_mode = 1; + } + arm_srpgcr |= MXC_SRPGCR_PCR; + + if (tzic_enable_wake(1) != 0) + return; + break; + case STOP_POWER_ON: + ccm_clpcr |= 0x2 << MXC_CCM_CLPCR_LPM_OFFSET; + break; + default: + printk(KERN_WARNING "UNKNOWN cpu power mode: %d\n", mode); + return; + } + + __raw_writel(plat_lpc, MXC_CORTEXA8_PLAT_LPC); + __raw_writel(ccm_clpcr, MXC_CCM_CLPCR); + __raw_writel(arm_srpgcr, MXC_SRPG_ARM_SRPGCR); + + /* Enable NEON SRPG for all but MX50TO1.0. */ + if (mx50_revision() != IMX_CHIP_REVISION_1_0) + __raw_writel(arm_srpgcr, MXC_SRPG_NEON_SRPGCR); + + if (stop_mode) { + empgc0 |= MXC_SRPGCR_PCR; + empgc1 |= MXC_SRPGCR_PCR; + + __raw_writel(empgc0, MXC_SRPG_EMPGC0_SRPGCR); + __raw_writel(empgc1, MXC_SRPG_EMPGC1_SRPGCR); + } +} + diff --git a/arch/arm/plat-mxc/include/mach/mxc.h b/arch/arm/plat-mxc/include/mach/mxc.h index 7e07263..6c2a371 100644 --- a/arch/arm/plat-mxc/include/mach/mxc.h +++ b/arch/arm/plat-mxc/include/mach/mxc.h @@ -181,6 +181,15 @@ struct cpu_op { u32 cpu_rate; }; +int tzic_enable_wake(int is_idle); +enum mxc_cpu_pwr_mode { + WAIT_CLOCKED, /* wfi only */ + WAIT_UNCLOCKED, /* WAIT */ + WAIT_UNCLOCKED_POWER_OFF, /* WAIT + SRPG */ + STOP_POWER_ON, /* just STOP */ + STOP_POWER_OFF, /* STOP + SRPG */ +}; + extern struct cpu_op *(*get_cpu_op)(int *op); #endif diff --git a/arch/arm/plat-mxc/include/mach/system.h b/arch/arm/plat-mxc/include/mach/system.h index 95be51b..0417da9 100644 --- a/arch/arm/plat-mxc/include/mach/system.h +++ b/arch/arm/plat-mxc/include/mach/system.h @@ -20,6 +20,8 @@ #include <mach/hardware.h> #include <mach/common.h> +extern void mx5_cpu_lp_set(enum mxc_cpu_pwr_mode mode); + static inline void arch_idle(void) { #ifdef CONFIG_ARCH_MXC91231 @@ -54,7 +56,9 @@ static inline void arch_idle(void) "orr %0, %0, #0x00000004\n" "mcr p15, 0, %0, c1, c0, 0\n" : "=r" (reg)); - } else + } else if (cpu_is_mx51()) + mx5_cpu_lp_set(WAIT_UNCLOCKED_POWER_OFF); + else cpu_do_idle(); } -- 1.6.0.4 ^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCHv5 4/4] ARM: mx51: Add support for low power suspend on MX51 2011-03-21 21:30 ` [PATCHv5 3/4] ARM: mx51: Implement code to allow mx51 to enter WFI Dinh.Nguyen at freescale.com @ 2011-03-21 21:30 ` Dinh.Nguyen at freescale.com 2011-03-23 10:24 ` Sascha Hauer 0 siblings, 1 reply; 5+ messages in thread From: Dinh.Nguyen at freescale.com @ 2011-03-21 21:30 UTC (permalink / raw) To: linux-arm-kernel From: Dinh Nguyen <Dinh.Nguyen@freescale.com> Adds initial low power suspend functionality to MX51. Supports "mem" and "standby" modes. Tested on mx51-babbage. Signed-off-by: Dinh Nguyen <Dinh.Nguyen@freescale.com> --- arch/arm/mach-mx5/Makefile | 1 + arch/arm/mach-mx5/pm-imx51.c | 74 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 75 insertions(+), 0 deletions(-) create mode 100644 arch/arm/mach-mx5/pm-imx51.c diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile index 0b9338c..787cb80 100644 --- a/arch/arm/mach-mx5/Makefile +++ b/arch/arm/mach-mx5/Makefile @@ -6,6 +6,7 @@ obj-y := cpu.o mm.o clock-mx51-mx53.o devices.o ehci.o system.o obj-$(CONFIG_SOC_IMX50) += mm-mx50.o +obj-$(CONFIG_PM) += pm-imx51.o obj-$(CONFIG_CPU_FREQ_IMX) += cpu_op-mx51.o obj-$(CONFIG_MACH_MX51_BABBAGE) += board-mx51_babbage.o obj-$(CONFIG_MACH_MX51_3DS) += board-mx51_3ds.o diff --git a/arch/arm/mach-mx5/pm-imx51.c b/arch/arm/mach-mx5/pm-imx51.c new file mode 100644 index 0000000..f5164b2 --- /dev/null +++ b/arch/arm/mach-mx5/pm-imx51.c @@ -0,0 +1,74 @@ +/* + * Copyright (C) 2011 Freescale Semiconductor, Inc. All Rights Reserved. + * + * The code contained herein is licensed under the GNU General Public + * License. You may obtain a copy of the GNU General Public License + * Version 2 or later at the following locations: + * + * http://www.opensource.org/licenses/gpl-license.html + * http://www.gnu.org/copyleft/gpl.html + */ +#include <linux/suspend.h> +#include <linux/clk.h> +#include <linux/io.h> +#include <asm/cacheflush.h> +#include <asm/tlbflush.h> +#include <mach/system.h> +#include "crm_regs.h" + +static struct clk *gpc_dvfs_clk; + +static int mx5_suspend_enter(suspend_state_t state) +{ + if (gpc_dvfs_clk == NULL) + gpc_dvfs_clk = clk_get(NULL, "gpc_dvfs"); + + if (gpc_dvfs_clk) { + clk_enable(gpc_dvfs_clk); + switch (state) { + case PM_SUSPEND_MEM: + mx5_cpu_lp_set(STOP_POWER_OFF); + break; + case PM_SUSPEND_STANDBY: + mx5_cpu_lp_set(WAIT_UNCLOCKED_POWER_OFF); + break; + default: + return -EINVAL; + } + + if (state == PM_SUSPEND_MEM) { + local_flush_tlb_all(); + flush_cache_all(); + + /*clear the EMPGC0/1 bits */ + __raw_writel(0, MXC_SRPG_EMPGC0_SRPGCR); + __raw_writel(0, MXC_SRPG_EMPGC1_SRPGCR); + } + cpu_do_idle(); + clk_disable(gpc_dvfs_clk); + }else { + printk(KERN_ERR "Cannot enter SRPG suspend -no gpc_dvfs clock!\n"); + return -EPERM; + } + + return 0; +} + +static int mx5_pm_valid(suspend_state_t state) +{ + return (state > PM_SUSPEND_ON && state <= PM_SUSPEND_MAX); +} + +static const struct platform_suspend_ops mx5_suspend_ops = { + .valid = mx5_pm_valid, + .enter = mx5_suspend_enter, +}; + +static int __init mx5_pm_init(void) +{ + if (cpu_is_mx51()) + suspend_set_ops(&mx5_suspend_ops); + + return 0; +} +device_initcall(mx5_pm_init); -- 1.6.0.4 ^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCHv5 4/4] ARM: mx51: Add support for low power suspend on MX51 2011-03-21 21:30 ` [PATCHv5 4/4] ARM: mx51: Add support for low power suspend on MX51 Dinh.Nguyen at freescale.com @ 2011-03-23 10:24 ` Sascha Hauer 0 siblings, 0 replies; 5+ messages in thread From: Sascha Hauer @ 2011-03-23 10:24 UTC (permalink / raw) To: linux-arm-kernel On Mon, Mar 21, 2011 at 04:30:38PM -0500, Dinh.Nguyen at freescale.com wrote: > From: Dinh Nguyen <Dinh.Nguyen@freescale.com> > > Adds initial low power suspend functionality to MX51. > Supports "mem" and "standby" modes. > > Tested on mx51-babbage. > > Signed-off-by: Dinh Nguyen <Dinh.Nguyen@freescale.com> > --- > arch/arm/mach-mx5/Makefile | 1 + > arch/arm/mach-mx5/pm-imx51.c | 74 ++++++++++++++++++++++++++++++++++++++++++ > 2 files changed, 75 insertions(+), 0 deletions(-) > create mode 100644 arch/arm/mach-mx5/pm-imx51.c > > diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile > index 0b9338c..787cb80 100644 > --- a/arch/arm/mach-mx5/Makefile > +++ b/arch/arm/mach-mx5/Makefile > @@ -6,6 +6,7 @@ > obj-y := cpu.o mm.o clock-mx51-mx53.o devices.o ehci.o system.o > obj-$(CONFIG_SOC_IMX50) += mm-mx50.o > > +obj-$(CONFIG_PM) += pm-imx51.o > obj-$(CONFIG_CPU_FREQ_IMX) += cpu_op-mx51.o > obj-$(CONFIG_MACH_MX51_BABBAGE) += board-mx51_babbage.o > obj-$(CONFIG_MACH_MX51_3DS) += board-mx51_3ds.o > diff --git a/arch/arm/mach-mx5/pm-imx51.c b/arch/arm/mach-mx5/pm-imx51.c > new file mode 100644 > index 0000000..f5164b2 > --- /dev/null > +++ b/arch/arm/mach-mx5/pm-imx51.c > @@ -0,0 +1,74 @@ > +/* > + * Copyright (C) 2011 Freescale Semiconductor, Inc. All Rights Reserved. > + * > + * The code contained herein is licensed under the GNU General Public > + * License. You may obtain a copy of the GNU General Public License > + * Version 2 or later at the following locations: > + * > + * http://www.opensource.org/licenses/gpl-license.html > + * http://www.gnu.org/copyleft/gpl.html > + */ > +#include <linux/suspend.h> > +#include <linux/clk.h> > +#include <linux/io.h> > +#include <asm/cacheflush.h> > +#include <asm/tlbflush.h> > +#include <mach/system.h> > +#include "crm_regs.h" > + > +static struct clk *gpc_dvfs_clk; > + > +static int mx5_suspend_enter(suspend_state_t state) Either the name of the file or the name of this function is wrong. You should decide for imx5 or imx51. > +{ > + if (gpc_dvfs_clk == NULL) > + gpc_dvfs_clk = clk_get(NULL, "gpc_dvfs"); > + > + if (gpc_dvfs_clk) { > + clk_enable(gpc_dvfs_clk); > + switch (state) { > + case PM_SUSPEND_MEM: > + mx5_cpu_lp_set(STOP_POWER_OFF); > + break; > + case PM_SUSPEND_STANDBY: > + mx5_cpu_lp_set(WAIT_UNCLOCKED_POWER_OFF); > + break; > + default: > + return -EINVAL; > + } > + > + if (state == PM_SUSPEND_MEM) { > + local_flush_tlb_all(); > + flush_cache_all(); > + > + /*clear the EMPGC0/1 bits */ > + __raw_writel(0, MXC_SRPG_EMPGC0_SRPGCR); > + __raw_writel(0, MXC_SRPG_EMPGC1_SRPGCR); > + } > + cpu_do_idle(); > + clk_disable(gpc_dvfs_clk); > + }else { > + printk(KERN_ERR "Cannot enter SRPG suspend -no gpc_dvfs clock!\n"); > + return -EPERM; > + } > + > + return 0; > +} > + > +static int mx5_pm_valid(suspend_state_t state) > +{ > + return (state > PM_SUSPEND_ON && state <= PM_SUSPEND_MAX); > +} > + > +static const struct platform_suspend_ops mx5_suspend_ops = { > + .valid = mx5_pm_valid, > + .enter = mx5_suspend_enter, > +}; > + > +static int __init mx5_pm_init(void) > +{ You should call clk_get here. Then you don't have to do the test for the clock over and over again and can print the warning only once. Also, NULL can be a valid clock. Please use IS_ERR(). Sascha -- Pengutronix e.K. | | Industrial Linux Solutions | http://www.pengutronix.de/ | Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0 | Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 | ^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2011-03-23 10:24 UTC | newest] Thread overview: 5+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2011-03-21 21:30 [PATCHv5 1/4] ARM: mx50: Add support to get the silicon revision Dinh.Nguyen at freescale.com 2011-03-21 21:30 ` [PATCHv5 2/4] ARM: mx51: Add entry for gpc_dvfs_clk Dinh.Nguyen at freescale.com 2011-03-21 21:30 ` [PATCHv5 3/4] ARM: mx51: Implement code to allow mx51 to enter WFI Dinh.Nguyen at freescale.com 2011-03-21 21:30 ` [PATCHv5 4/4] ARM: mx51: Add support for low power suspend on MX51 Dinh.Nguyen at freescale.com 2011-03-23 10:24 ` Sascha Hauer
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).