From 23b2441b90026ff56b3a4dd9af33a39730cffa21 Mon Sep 17 00:00:00 2001 From: Stefan Agner Date: Thu, 3 Jan 2019 15:36:31 +0100 Subject: [PATCH 1/5] ARM: imx: don't build ssi-fiq if not required The symbols provided by ssi-fiq are used in sound/soc/fsl/imx-pcm-fiq.c only. Build ssi-fiq.o/ssi-fiq-ksym.o only if SND_SOC_IMX_PCM_FIQ is enabled. Signed-off-by: Stefan Agner Signed-off-by: Shawn Guo --- arch/arm/mach-imx/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/mach-imx/Makefile b/arch/arm/mach-imx/Makefile index 8af2f7e91d13..b6c87d7d3a5d 100644 --- a/arch/arm/mach-imx/Makefile +++ b/arch/arm/mach-imx/Makefile @@ -31,7 +31,7 @@ obj-$(CONFIG_SOC_IMX6SX) += cpuidle-imx6sx.o obj-$(CONFIG_SOC_IMX6UL) += cpuidle-imx6sx.o endif -ifdef CONFIG_SND_IMX_SOC +ifdef CONFIG_SND_SOC_IMX_PCM_FIQ obj-y += ssi-fiq.o obj-y += ssi-fiq-ksym.o endif From 6d45a4028c8a6bc0a1e92438283ef7d4ed6ffe71 Mon Sep 17 00:00:00 2001 From: Anson Huang Date: Mon, 14 Jan 2019 08:54:59 +0800 Subject: [PATCH 2/5] ARM: imx: add i.MX7ULP cpuidle support This patch adds cpuidle support for i.MX7ULP, 3 cpuidle states supported as below: 1. WFI, just ARM wfi; 2. WAIT mode, mapped to SoC's partial stop mode #3; 3. STOP mode, mapped to SoC's partial stop mode #1. In WAIT mode, system clock and bus clock will be enabled; In STOP mode, system clock and bus clock will be disabled. Signed-off-by: Anson Huang Signed-off-by: Shawn Guo --- arch/arm/mach-imx/Makefile | 1 + arch/arm/mach-imx/common.h | 10 +++++ arch/arm/mach-imx/cpuidle-imx7ulp.c | 60 +++++++++++++++++++++++++++++ arch/arm/mach-imx/cpuidle.h | 5 +++ arch/arm/mach-imx/mach-imx7ulp.c | 7 ++++ arch/arm/mach-imx/pm-imx7ulp.c | 49 ++++++++++++++++++++--- 6 files changed, 127 insertions(+), 5 deletions(-) create mode 100644 arch/arm/mach-imx/cpuidle-imx7ulp.c diff --git a/arch/arm/mach-imx/Makefile b/arch/arm/mach-imx/Makefile index b6c87d7d3a5d..35ff620537e6 100644 --- a/arch/arm/mach-imx/Makefile +++ b/arch/arm/mach-imx/Makefile @@ -29,6 +29,7 @@ obj-$(CONFIG_SOC_IMX6SL) += cpuidle-imx6sl.o obj-$(CONFIG_SOC_IMX6SLL) += cpuidle-imx6sx.o obj-$(CONFIG_SOC_IMX6SX) += cpuidle-imx6sx.o obj-$(CONFIG_SOC_IMX6UL) += cpuidle-imx6sx.o +obj-$(CONFIG_SOC_IMX7ULP) += cpuidle-imx7ulp.o endif ifdef CONFIG_SND_SOC_IMX_PCM_FIQ diff --git a/arch/arm/mach-imx/common.h b/arch/arm/mach-imx/common.h index bc915e5b4d56..c51764a85fd7 100644 --- a/arch/arm/mach-imx/common.h +++ b/arch/arm/mach-imx/common.h @@ -72,6 +72,15 @@ enum mxc_cpu_pwr_mode { STOP_POWER_OFF, /* STOP + SRPG */ }; +enum ulp_cpu_pwr_mode { + ULP_PM_HSRUN, /* High speed run mode */ + ULP_PM_RUN, /* Run mode */ + ULP_PM_WAIT, /* Wait mode */ + ULP_PM_STOP, /* Stop mode */ + ULP_PM_VLPS, /* Very low power stop mode */ + ULP_PM_VLLS, /* very low leakage stop mode */ +}; + void imx_enable_cpu(int cpu, bool enable); void imx_set_cpu_jump(int cpu, void *jump_addr); u32 imx_get_cpu_arg(int cpu); @@ -98,6 +107,7 @@ int imx6_set_lpm(enum mxc_cpu_pwr_mode mode); void imx6_set_int_mem_clk_lpm(bool enable); void imx6sl_set_wait_clk(bool enter); int imx_mmdc_get_ddr_type(void); +int imx7ulp_set_lpm(enum ulp_cpu_pwr_mode mode); void imx_cpu_die(unsigned int cpu); int imx_cpu_kill(unsigned int cpu); diff --git a/arch/arm/mach-imx/cpuidle-imx7ulp.c b/arch/arm/mach-imx/cpuidle-imx7ulp.c new file mode 100644 index 000000000000..ca86c967d19e --- /dev/null +++ b/arch/arm/mach-imx/cpuidle-imx7ulp.c @@ -0,0 +1,60 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Copyright (C) 2016 Freescale Semiconductor, Inc. + * Copyright 2017-2018 NXP + * Anson Huang + */ + +#include +#include +#include + +#include "common.h" +#include "cpuidle.h" + +static int imx7ulp_enter_wait(struct cpuidle_device *dev, + struct cpuidle_driver *drv, int index) +{ + if (index == 1) + imx7ulp_set_lpm(ULP_PM_WAIT); + else + imx7ulp_set_lpm(ULP_PM_STOP); + + cpu_do_idle(); + + imx7ulp_set_lpm(ULP_PM_RUN); + + return index; +} + +static struct cpuidle_driver imx7ulp_cpuidle_driver = { + .name = "imx7ulp_cpuidle", + .owner = THIS_MODULE, + .states = { + /* WFI */ + ARM_CPUIDLE_WFI_STATE, + /* WAIT */ + { + .exit_latency = 50, + .target_residency = 75, + .enter = imx7ulp_enter_wait, + .name = "WAIT", + .desc = "PSTOP2", + }, + /* STOP */ + { + .exit_latency = 100, + .target_residency = 150, + .enter = imx7ulp_enter_wait, + .name = "STOP", + .desc = "PSTOP1", + }, + }, + .state_count = 3, + .safe_state_index = 0, +}; + +int __init imx7ulp_cpuidle_init(void) +{ + return cpuidle_register(&imx7ulp_cpuidle_driver, NULL); +} diff --git a/arch/arm/mach-imx/cpuidle.h b/arch/arm/mach-imx/cpuidle.h index f9140128ba05..7694c8f810a4 100644 --- a/arch/arm/mach-imx/cpuidle.h +++ b/arch/arm/mach-imx/cpuidle.h @@ -15,6 +15,7 @@ extern int imx5_cpuidle_init(void); extern int imx6q_cpuidle_init(void); extern int imx6sl_cpuidle_init(void); extern int imx6sx_cpuidle_init(void); +extern int imx7ulp_cpuidle_init(void); #else static inline int imx5_cpuidle_init(void) { @@ -32,4 +33,8 @@ static inline int imx6sx_cpuidle_init(void) { return 0; } +static inline int imx7ulp_cpuidle_init(void) +{ + return 0; +} #endif diff --git a/arch/arm/mach-imx/mach-imx7ulp.c b/arch/arm/mach-imx/mach-imx7ulp.c index 33937ebf66b5..19c5b3050cb9 100644 --- a/arch/arm/mach-imx/mach-imx7ulp.c +++ b/arch/arm/mach-imx/mach-imx7ulp.c @@ -10,6 +10,7 @@ #include #include "common.h" +#include "cpuidle.h" #include "hardware.h" static void __init imx7ulp_init_machine(void) @@ -25,7 +26,13 @@ static const char *const imx7ulp_dt_compat[] __initconst = { NULL, }; +static void __init imx7ulp_init_late(void) +{ + imx7ulp_cpuidle_init(); +} + DT_MACHINE_START(IMX7ulp, "Freescale i.MX7ULP (Device Tree)") .init_machine = imx7ulp_init_machine, .dt_compat = imx7ulp_dt_compat, + .init_late = imx7ulp_init_late, MACHINE_END diff --git a/arch/arm/mach-imx/pm-imx7ulp.c b/arch/arm/mach-imx/pm-imx7ulp.c index cf6a380c2b8d..7b2f7387e662 100644 --- a/arch/arm/mach-imx/pm-imx7ulp.c +++ b/arch/arm/mach-imx/pm-imx7ulp.c @@ -9,21 +9,60 @@ #include #include +#include "common.h" + #define SMC_PMCTRL 0x10 #define BP_PMCTRL_PSTOPO 16 #define PSTOPO_PSTOP3 0x3 +#define PSTOPO_PSTOP2 0x2 +#define PSTOPO_PSTOP1 0x1 +#define BP_PMCTRL_RUNM 8 +#define RUNM_RUN 0 +#define BP_PMCTRL_STOPM 0 +#define STOPM_STOP 0 + +#define BM_PMCTRL_PSTOPO (3 << BP_PMCTRL_PSTOPO) +#define BM_PMCTRL_RUNM (3 << BP_PMCTRL_RUNM) +#define BM_PMCTRL_STOPM (7 << BP_PMCTRL_STOPM) + +static void __iomem *smc1_base; + +int imx7ulp_set_lpm(enum ulp_cpu_pwr_mode mode) +{ + u32 val = readl_relaxed(smc1_base + SMC_PMCTRL); + + /* clear all */ + val &= ~(BM_PMCTRL_RUNM | BM_PMCTRL_STOPM | BM_PMCTRL_PSTOPO); + + switch (mode) { + case ULP_PM_RUN: + /* system/bus clock enabled */ + val |= PSTOPO_PSTOP3 << BP_PMCTRL_PSTOPO; + break; + case ULP_PM_WAIT: + /* system clock disabled, bus clock enabled */ + val |= PSTOPO_PSTOP2 << BP_PMCTRL_PSTOPO; + break; + case ULP_PM_STOP: + /* system/bus clock disabled */ + val |= PSTOPO_PSTOP1 << BP_PMCTRL_PSTOPO; + break; + default: + return -EINVAL; + } + + writel_relaxed(val, smc1_base + SMC_PMCTRL); + + return 0; +} void __init imx7ulp_pm_init(void) { struct device_node *np; - void __iomem *smc1_base; np = of_find_compatible_node(NULL, NULL, "fsl,imx7ulp-smc1"); smc1_base = of_iomap(np, 0); WARN_ON(!smc1_base); - /* Partial Stop mode 3 with system/bus clock enabled */ - writel_relaxed(PSTOPO_PSTOP3 << BP_PMCTRL_PSTOPO, - smc1_base + SMC_PMCTRL); - iounmap(smc1_base); + imx7ulp_set_lpm(ULP_PM_RUN); } From 9edf908a16c43c438f0edc08ce839c5a7ef7d039 Mon Sep 17 00:00:00 2001 From: Anson Huang Date: Fri, 11 Jan 2019 06:22:50 +0000 Subject: [PATCH 3/5] ARM: imx: add i.MX7ULP SoC revision support i.MX7ULP SoC's revision info is inside the SIM module, bit[31:28] of JTAG_ID register defines revision as below from B0: 0001 B0 0010 B1 This patch adds SoC revision support for i.MX7ULP, test result as below: root@imx7ulp-evk ~$ cat /sys/devices/soc0/revision 2.1 Signed-off-by: Anson Huang Signed-off-by: Shawn Guo --- arch/arm/mach-imx/mach-imx7ulp.c | 39 ++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) diff --git a/arch/arm/mach-imx/mach-imx7ulp.c b/arch/arm/mach-imx/mach-imx7ulp.c index 19c5b3050cb9..11ac71aaf965 100644 --- a/arch/arm/mach-imx/mach-imx7ulp.c +++ b/arch/arm/mach-imx/mach-imx7ulp.c @@ -6,18 +6,57 @@ */ #include +#include #include +#include #include #include "common.h" #include "cpuidle.h" #include "hardware.h" +#define SIM_JTAG_ID_REG 0x8c + +static void __init imx7ulp_set_revision(void) +{ + struct regmap *sim; + u32 revision; + + sim = syscon_regmap_lookup_by_compatible("fsl,imx7ulp-sim"); + if (IS_ERR(sim)) { + pr_warn("failed to find fsl,imx7ulp-sim regmap!\n"); + return; + } + + if (regmap_read(sim, SIM_JTAG_ID_REG, &revision)) { + pr_warn("failed to read sim regmap!\n"); + return; + } + + /* + * bit[31:28] of JTAG_ID register defines revision as below from B0: + * 0001 B0 + * 0010 B1 + */ + switch (revision >> 28) { + case 1: + imx_set_soc_revision(IMX_CHIP_REVISION_2_0); + break; + case 2: + imx_set_soc_revision(IMX_CHIP_REVISION_2_1); + break; + default: + imx_set_soc_revision(IMX_CHIP_REVISION_1_0); + break; + } +} + static void __init imx7ulp_init_machine(void) { imx7ulp_pm_init(); mxc_set_cpu_type(MXC_CPU_IMX7ULP); + imx7ulp_set_revision(); of_platform_default_populate(NULL, NULL, imx_soc_device_init()); } From 67b9282387c579f6011a3204149d1566b79d9d60 Mon Sep 17 00:00:00 2001 From: Lucas Stach Date: Fri, 25 Jan 2019 17:20:34 +0100 Subject: [PATCH 4/5] arm64: imx8mq: select GPCv2 irqchip driver The system is unable to boot without this driver being present, as most of the peripherals are connected to this IRQ controller. Signed-off-by: Lucas Stach Reviewed-by: Fabio Estevam Signed-off-by: Shawn Guo --- arch/arm64/Kconfig.platforms | 1 + 1 file changed, 1 insertion(+) diff --git a/arch/arm64/Kconfig.platforms b/arch/arm64/Kconfig.platforms index 251ecf34cb02..f4e45c52aea4 100644 --- a/arch/arm64/Kconfig.platforms +++ b/arch/arm64/Kconfig.platforms @@ -146,6 +146,7 @@ config ARCH_MXC bool "ARMv8 based NXP i.MX SoC family" select ARM64_ERRATUM_843419 select ARM64_ERRATUM_845719 + select IMX_GPCV2 help This enables support for the ARMv8 based SoCs in the NXP i.MX family. From 84a2ab25b12d69914c96dd12e762f7ff912f9735 Mon Sep 17 00:00:00 2001 From: Lucas Stach Date: Fri, 25 Jan 2019 17:24:37 +0100 Subject: [PATCH 5/5] arm64: imx8mq: select PM support The ATF on the i.MX8MQ device disables all non-essential power domains. For correct on-SoC peripheral operation we need both the power domain driver and generic domains, so device driver probe gets ordered behind the power domain controller driver. Select those options, as those being absent can lead to very hard to debug failures. Signed-off-by: Lucas Stach Signed-off-by: Shawn Guo --- arch/arm64/Kconfig.platforms | 3 +++ 1 file changed, 3 insertions(+) diff --git a/arch/arm64/Kconfig.platforms b/arch/arm64/Kconfig.platforms index f4e45c52aea4..8c2fc4bb20a5 100644 --- a/arch/arm64/Kconfig.platforms +++ b/arch/arm64/Kconfig.platforms @@ -147,6 +147,9 @@ config ARCH_MXC select ARM64_ERRATUM_843419 select ARM64_ERRATUM_845719 select IMX_GPCV2 + select IMX_GPCV2_PM_DOMAINS + select PM + select PM_GENERIC_DOMAINS help This enables support for the ARMv8 based SoCs in the NXP i.MX family.