]> git.kernelconcepts.de Git - karo-tx-linux.git/blobdiff - arch/arm/mach-imx/pm-imx6.c
Merge remote-tracking branch 'ubifs/linux-next'
[karo-tx-linux.git] / arch / arm / mach-imx / pm-imx6.c
index 8ff8fc0b261ccd7a6d6912b4478e60b15606c097..4470376af5f815fd5f8f2d12c5e7d18306675bb4 100644 (file)
@@ -93,6 +93,7 @@ struct imx6_pm_socdata {
        const char *src_compat;
        const char *iomuxc_compat;
        const char *gpc_compat;
+       const char *pl310_compat;
        const u32 mmdc_io_num;
        const u32 *mmdc_io_offset;
 };
@@ -137,11 +138,19 @@ static const u32 imx6sx_mmdc_io_offset[] __initconst = {
        0x330, 0x334, 0x338, 0x33c, /* SDQS0 ~ SDQS3 */
 };
 
+static const u32 imx6ul_mmdc_io_offset[] __initconst = {
+       0x244, 0x248, 0x24c, 0x250, /* DQM0, DQM1, RAS, CAS */
+       0x27c, 0x498, 0x4a4, 0x490, /* SDCLK0, GPR_B0DS-B1DS, GPR_ADDS */
+       0x280, 0x284, 0x260, 0x264, /* SDQS0~1, SODT0, SODT1 */
+       0x494, 0x4b0,               /* MODE_CTL, MODE, */
+};
+
 static const struct imx6_pm_socdata imx6q_pm_data __initconst = {
        .mmdc_compat = "fsl,imx6q-mmdc",
        .src_compat = "fsl,imx6q-src",
        .iomuxc_compat = "fsl,imx6q-iomuxc",
        .gpc_compat = "fsl,imx6q-gpc",
+       .pl310_compat = "arm,pl310-cache",
        .mmdc_io_num = ARRAY_SIZE(imx6q_mmdc_io_offset),
        .mmdc_io_offset = imx6q_mmdc_io_offset,
 };
@@ -151,6 +160,7 @@ static const struct imx6_pm_socdata imx6dl_pm_data __initconst = {
        .src_compat = "fsl,imx6q-src",
        .iomuxc_compat = "fsl,imx6dl-iomuxc",
        .gpc_compat = "fsl,imx6q-gpc",
+       .pl310_compat = "arm,pl310-cache",
        .mmdc_io_num = ARRAY_SIZE(imx6dl_mmdc_io_offset),
        .mmdc_io_offset = imx6dl_mmdc_io_offset,
 };
@@ -160,6 +170,7 @@ static const struct imx6_pm_socdata imx6sl_pm_data __initconst = {
        .src_compat = "fsl,imx6sl-src",
        .iomuxc_compat = "fsl,imx6sl-iomuxc",
        .gpc_compat = "fsl,imx6sl-gpc",
+       .pl310_compat = "arm,pl310-cache",
        .mmdc_io_num = ARRAY_SIZE(imx6sl_mmdc_io_offset),
        .mmdc_io_offset = imx6sl_mmdc_io_offset,
 };
@@ -169,10 +180,21 @@ static const struct imx6_pm_socdata imx6sx_pm_data __initconst = {
        .src_compat = "fsl,imx6sx-src",
        .iomuxc_compat = "fsl,imx6sx-iomuxc",
        .gpc_compat = "fsl,imx6sx-gpc",
+       .pl310_compat = "arm,pl310-cache",
        .mmdc_io_num = ARRAY_SIZE(imx6sx_mmdc_io_offset),
        .mmdc_io_offset = imx6sx_mmdc_io_offset,
 };
 
+static const struct imx6_pm_socdata imx6ul_pm_data __initconst = {
+       .mmdc_compat = "fsl,imx6ul-mmdc",
+       .src_compat = "fsl,imx6ul-src",
+       .iomuxc_compat = "fsl,imx6ul-iomuxc",
+       .gpc_compat = "fsl,imx6ul-gpc",
+       .pl310_compat = NULL,
+       .mmdc_io_num = ARRAY_SIZE(imx6ul_mmdc_io_offset),
+       .mmdc_io_offset = imx6ul_mmdc_io_offset,
+};
+
 /*
  * This structure is for passing necessary data for low level ocram
  * suspend code(arch/arm/mach-imx/suspend-imx6.S), if this struct
@@ -290,7 +312,7 @@ int imx6_set_lpm(enum mxc_cpu_pwr_mode mode)
                val |= BM_CLPCR_SBYOS;
                if (cpu_is_imx6sl())
                        val |= BM_CLPCR_BYPASS_PMIC_READY;
-               if (cpu_is_imx6sl() || cpu_is_imx6sx())
+               if (cpu_is_imx6sl() || cpu_is_imx6sx() || cpu_is_imx6ul())
                        val |= BM_CLPCR_BYP_MMDC_CH0_LPM_HS;
                else
                        val |= BM_CLPCR_BYP_MMDC_CH1_LPM_HS;
@@ -330,6 +352,10 @@ static int imx6q_suspend_finish(unsigned long val)
                 * as we need to float DDR IO.
                 */
                local_flush_tlb_all();
+               /* check if need to flush internal L2 cache */
+               if (!((struct imx6_cpu_pm_info *)
+                       suspend_ocram_base)->l2_base.vbase)
+                       flush_cache_all();
                imx6_suspend_in_ocram_fn(suspend_ocram_base);
        }
 
@@ -470,6 +496,7 @@ static int __init imx6q_suspend_init(const struct imx6_pm_socdata *socdata)
        suspend_ocram_base = __arm_ioremap_exec(ocram_pbase,
                MX6Q_SUSPEND_OCRAM_SIZE, false);
 
+       memset(suspend_ocram_base, 0, sizeof(*pm_info));
        pm_info = suspend_ocram_base;
        pm_info->pbase = ocram_pbase;
        pm_info->resume_addr = virt_to_phys(v7_cpu_resume);
@@ -505,11 +532,13 @@ static int __init imx6q_suspend_init(const struct imx6_pm_socdata *socdata)
                goto gpc_map_failed;
        }
 
-       ret = imx6_pm_get_base(&pm_info->l2_base, "arm,pl310-cache");
-       if (ret) {
-               pr_warn("%s: failed to get pl310-cache base %d!\n",
-                       __func__, ret);
-               goto pl310_cache_map_failed;
+       if (socdata->pl310_compat) {
+               ret = imx6_pm_get_base(&pm_info->l2_base, socdata->pl310_compat);
+               if (ret) {
+                       pr_warn("%s: failed to get pl310-cache base %d!\n",
+                               __func__, ret);
+                       goto pl310_cache_map_failed;
+               }
        }
 
        pm_info->ddr_type = imx_mmdc_get_ddr_type();
@@ -610,3 +639,8 @@ void __init imx6sx_pm_init(void)
 {
        imx6_pm_common_init(&imx6sx_pm_data);
 }
+
+void __init imx6ul_pm_init(void)
+{
+       imx6_pm_common_init(&imx6ul_pm_data);
+}