1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * AM33XX Arch Power Management Routines 4 * 5 * Copyright (C) 2016-2018 Texas Instruments Incorporated - http://www.ti.com/ 6 * Dave Gerlach 7 */ 8 9 #include <linux/cpuidle.h> 10 #include <linux/platform_data/pm33xx.h> 11 #include <asm/cpuidle.h> 12 #include <asm/smp_scu.h> 13 #include <asm/suspend.h> 14 #include <linux/errno.h> 15 #include <linux/clk.h> 16 #include <linux/cpu.h> 17 #include <linux/platform_data/gpio-omap.h> 18 #include <linux/pinctrl/pinmux.h> 19 #include <linux/wkup_m3_ipc.h> 20 #include <linux/of.h> 21 #include <linux/rtc.h> 22 23 #include "cm33xx.h" 24 #include "common.h" 25 #include "control.h" 26 #include "clockdomain.h" 27 #include "iomap.h" 28 #include "omap_hwmod.h" 29 #include "pm.h" 30 #include "powerdomain.h" 31 #include "prm33xx.h" 32 #include "soc.h" 33 #include "sram.h" 34 #include "omap-secure.h" 35 36 static struct powerdomain *cefuse_pwrdm, *gfx_pwrdm, *per_pwrdm, *mpu_pwrdm; 37 static struct clockdomain *gfx_l4ls_clkdm; 38 static void __iomem *scu_base; 39 static struct omap_hwmod *rtc_oh; 40 41 static int (*idle_fn)(u32 wfi_flags); 42 43 struct amx3_idle_state { 44 int wfi_flags; 45 }; 46 47 static struct amx3_idle_state *idle_states; 48 49 static int am43xx_map_scu(void) 50 { 51 scu_base = ioremap(scu_a9_get_base(), SZ_256); 52 53 if (!scu_base) 54 return -ENOMEM; 55 56 return 0; 57 } 58 59 static int am33xx_check_off_mode_enable(void) 60 { 61 if (enable_off_mode) 62 pr_warn("WARNING: This platform does not support off-mode, entering DeepSleep suspend.\n"); 63 64 /* off mode not supported on am335x so return 0 always */ 65 return 0; 66 } 67 68 static int am43xx_check_off_mode_enable(void) 69 { 70 /* 71 * Check for am437x-gp-evm which has the right Hardware design to 72 * support this mode reliably. 73 */ 74 if (of_machine_is_compatible("ti,am437x-gp-evm") && enable_off_mode) 75 return enable_off_mode; 76 else if (enable_off_mode) 77 pr_warn("WARNING: This platform does not support off-mode, entering DeepSleep suspend.\n"); 78 79 return 0; 80 } 81 82 static int amx3_common_init(int (*idle)(u32 wfi_flags)) 83 { 84 gfx_pwrdm = pwrdm_lookup("gfx_pwrdm"); 85 per_pwrdm = pwrdm_lookup("per_pwrdm"); 86 mpu_pwrdm = pwrdm_lookup("mpu_pwrdm"); 87 88 if ((!gfx_pwrdm) || (!per_pwrdm) || (!mpu_pwrdm)) 89 return -ENODEV; 90 91 (void)clkdm_for_each(omap_pm_clkdms_setup, NULL); 92 93 /* CEFUSE domain can be turned off post bootup */ 94 cefuse_pwrdm = pwrdm_lookup("cefuse_pwrdm"); 95 if (!cefuse_pwrdm) 96 pr_err("PM: Failed to get cefuse_pwrdm\n"); 97 else if (omap_type() != OMAP2_DEVICE_TYPE_GP) 98 pr_info("PM: Leaving EFUSE power domain active\n"); 99 else 100 omap_set_pwrdm_state(cefuse_pwrdm, PWRDM_POWER_OFF); 101 102 idle_fn = idle; 103 104 return 0; 105 } 106 107 static int am33xx_suspend_init(int (*idle)(u32 wfi_flags)) 108 { 109 int ret; 110 111 gfx_l4ls_clkdm = clkdm_lookup("gfx_l4ls_gfx_clkdm"); 112 113 if (!gfx_l4ls_clkdm) { 114 pr_err("PM: Cannot lookup gfx_l4ls_clkdm clockdomains\n"); 115 return -ENODEV; 116 } 117 118 ret = amx3_common_init(idle); 119 120 return ret; 121 } 122 123 static int am43xx_suspend_init(int (*idle)(u32 wfi_flags)) 124 { 125 int ret = 0; 126 127 ret = am43xx_map_scu(); 128 if (ret) { 129 pr_err("PM: Could not ioremap SCU\n"); 130 return ret; 131 } 132 133 ret = amx3_common_init(idle); 134 135 return ret; 136 } 137 138 static int amx3_suspend_deinit(void) 139 { 140 idle_fn = NULL; 141 return 0; 142 } 143 144 static void amx3_pre_suspend_common(void) 145 { 146 omap_set_pwrdm_state(gfx_pwrdm, PWRDM_POWER_OFF); 147 } 148 149 static void amx3_post_suspend_common(void) 150 { 151 int status; 152 /* 153 * Because gfx_pwrdm is the only one under MPU control, 154 * comment on transition status 155 */ 156 status = pwrdm_read_pwrst(gfx_pwrdm); 157 if (status != PWRDM_POWER_OFF) 158 pr_err("PM: GFX domain did not transition: %x\n", status); 159 } 160 161 static int am33xx_suspend(unsigned int state, int (*fn)(unsigned long), 162 unsigned long args) 163 { 164 int ret = 0; 165 166 amx3_pre_suspend_common(); 167 ret = cpu_suspend(args, fn); 168 amx3_post_suspend_common(); 169 170 /* 171 * BUG: GFX_L4LS clock domain needs to be woken up to 172 * ensure thet L4LS clock domain does not get stuck in 173 * transition. If that happens L3 module does not get 174 * disabled, thereby leading to PER power domain 175 * transition failing 176 */ 177 178 clkdm_wakeup(gfx_l4ls_clkdm); 179 clkdm_sleep(gfx_l4ls_clkdm); 180 181 return ret; 182 } 183 184 static int am43xx_suspend(unsigned int state, int (*fn)(unsigned long), 185 unsigned long args) 186 { 187 int ret = 0; 188 189 /* Suspend secure side on HS devices */ 190 if (omap_type() != OMAP2_DEVICE_TYPE_GP) { 191 if (optee_available) 192 omap_smccc_smc(AM43xx_PPA_SVC_PM_SUSPEND, 0); 193 else 194 omap_secure_dispatcher(AM43xx_PPA_SVC_PM_SUSPEND, 195 FLAG_START_CRITICAL, 196 0, 0, 0, 0, 0); 197 } 198 199 amx3_pre_suspend_common(); 200 scu_power_mode(scu_base, SCU_PM_POWEROFF); 201 ret = cpu_suspend(args, fn); 202 scu_power_mode(scu_base, SCU_PM_NORMAL); 203 204 if (!am43xx_check_off_mode_enable()) 205 amx3_post_suspend_common(); 206 207 /* 208 * Resume secure side on HS devices. 209 * 210 * Note that even on systems with OP-TEE available this resume call is 211 * issued to the ROM. This is because upon waking from suspend the ROM 212 * is restored as the secure monitor. On systems with OP-TEE ROM will 213 * restore OP-TEE during this call. 214 */ 215 if (omap_type() != OMAP2_DEVICE_TYPE_GP) 216 omap_secure_dispatcher(AM43xx_PPA_SVC_PM_RESUME, 217 FLAG_START_CRITICAL, 218 0, 0, 0, 0, 0); 219 220 return ret; 221 } 222 223 static int am33xx_cpu_suspend(int (*fn)(unsigned long), unsigned long args) 224 { 225 int ret = 0; 226 227 if (omap_irq_pending() || need_resched()) 228 return ret; 229 230 ret = cpu_suspend(args, fn); 231 232 return ret; 233 } 234 235 static int am43xx_cpu_suspend(int (*fn)(unsigned long), unsigned long args) 236 { 237 int ret = 0; 238 239 if (!scu_base) 240 return 0; 241 242 scu_power_mode(scu_base, SCU_PM_DORMANT); 243 ret = cpu_suspend(args, fn); 244 scu_power_mode(scu_base, SCU_PM_NORMAL); 245 246 return ret; 247 } 248 249 static void amx3_begin_suspend(void) 250 { 251 cpu_idle_poll_ctrl(true); 252 } 253 254 static void amx3_finish_suspend(void) 255 { 256 cpu_idle_poll_ctrl(false); 257 } 258 259 260 static struct am33xx_pm_sram_addr *amx3_get_sram_addrs(void) 261 { 262 if (soc_is_am33xx()) 263 return &am33xx_pm_sram; 264 else if (soc_is_am437x()) 265 return &am43xx_pm_sram; 266 else 267 return NULL; 268 } 269 270 static void __iomem *am43xx_get_rtc_base_addr(void) 271 { 272 rtc_oh = omap_hwmod_lookup("rtc"); 273 274 return omap_hwmod_get_mpu_rt_va(rtc_oh); 275 } 276 277 static void am43xx_save_context(void) 278 { 279 } 280 281 static void am33xx_save_context(void) 282 { 283 omap_intc_save_context(); 284 } 285 286 static void am33xx_restore_context(void) 287 { 288 omap_intc_restore_context(); 289 } 290 291 static void am43xx_restore_context(void) 292 { 293 /* 294 * HACK: restore dpll_per_clkdcoldo register contents, to avoid 295 * breaking suspend-resume 296 */ 297 writel_relaxed(0x0, AM33XX_L4_WK_IO_ADDRESS(0x44df2e14)); 298 } 299 300 static void am43xx_prepare_rtc_suspend(void) 301 { 302 omap_hwmod_enable(rtc_oh); 303 } 304 305 static void am43xx_prepare_rtc_resume(void) 306 { 307 omap_hwmod_idle(rtc_oh); 308 } 309 310 static struct am33xx_pm_platform_data am33xx_ops = { 311 .init = am33xx_suspend_init, 312 .deinit = amx3_suspend_deinit, 313 .soc_suspend = am33xx_suspend, 314 .cpu_suspend = am33xx_cpu_suspend, 315 .begin_suspend = amx3_begin_suspend, 316 .finish_suspend = amx3_finish_suspend, 317 .get_sram_addrs = amx3_get_sram_addrs, 318 .save_context = am33xx_save_context, 319 .restore_context = am33xx_restore_context, 320 .prepare_rtc_suspend = am43xx_prepare_rtc_suspend, 321 .prepare_rtc_resume = am43xx_prepare_rtc_resume, 322 .check_off_mode_enable = am33xx_check_off_mode_enable, 323 .get_rtc_base_addr = am43xx_get_rtc_base_addr, 324 }; 325 326 static struct am33xx_pm_platform_data am43xx_ops = { 327 .init = am43xx_suspend_init, 328 .deinit = amx3_suspend_deinit, 329 .soc_suspend = am43xx_suspend, 330 .cpu_suspend = am43xx_cpu_suspend, 331 .begin_suspend = amx3_begin_suspend, 332 .finish_suspend = amx3_finish_suspend, 333 .get_sram_addrs = amx3_get_sram_addrs, 334 .save_context = am43xx_save_context, 335 .restore_context = am43xx_restore_context, 336 .prepare_rtc_suspend = am43xx_prepare_rtc_suspend, 337 .prepare_rtc_resume = am43xx_prepare_rtc_resume, 338 .check_off_mode_enable = am43xx_check_off_mode_enable, 339 .get_rtc_base_addr = am43xx_get_rtc_base_addr, 340 }; 341 342 static struct am33xx_pm_platform_data *am33xx_pm_get_pdata(void) 343 { 344 if (soc_is_am33xx()) 345 return &am33xx_ops; 346 else if (soc_is_am437x()) 347 return &am43xx_ops; 348 else 349 return NULL; 350 } 351 352 int __init amx3_common_pm_init(void) 353 { 354 struct am33xx_pm_platform_data *pdata; 355 struct platform_device_info devinfo; 356 357 pdata = am33xx_pm_get_pdata(); 358 359 memset(&devinfo, 0, sizeof(devinfo)); 360 devinfo.name = "pm33xx"; 361 devinfo.data = pdata; 362 devinfo.size_data = sizeof(*pdata); 363 devinfo.id = -1; 364 platform_device_register_full(&devinfo); 365 366 return 0; 367 } 368 369 static int __init amx3_idle_init(struct device_node *cpu_node, int cpu) 370 { 371 struct device_node *state_node; 372 struct amx3_idle_state states[CPUIDLE_STATE_MAX]; 373 int i; 374 int state_count = 1; 375 376 for (i = 0; ; i++) { 377 state_node = of_parse_phandle(cpu_node, "cpu-idle-states", i); 378 if (!state_node) 379 break; 380 381 if (!of_device_is_available(state_node)) 382 continue; 383 384 if (i == CPUIDLE_STATE_MAX) { 385 pr_warn("%s: cpuidle states reached max possible\n", 386 __func__); 387 break; 388 } 389 390 states[state_count].wfi_flags = 0; 391 392 if (of_property_read_bool(state_node, "ti,idle-wkup-m3")) 393 states[state_count].wfi_flags |= WFI_FLAG_WAKE_M3 | 394 WFI_FLAG_FLUSH_CACHE; 395 396 state_count++; 397 } 398 399 idle_states = kcalloc(state_count, sizeof(*idle_states), GFP_KERNEL); 400 if (!idle_states) 401 return -ENOMEM; 402 403 for (i = 1; i < state_count; i++) 404 idle_states[i].wfi_flags = states[i].wfi_flags; 405 406 return 0; 407 } 408 409 static int amx3_idle_enter(unsigned long index) 410 { 411 struct amx3_idle_state *idle_state = &idle_states[index]; 412 413 if (!idle_state) 414 return -EINVAL; 415 416 if (idle_fn) 417 idle_fn(idle_state->wfi_flags); 418 419 return 0; 420 } 421 422 static struct cpuidle_ops amx3_cpuidle_ops __initdata = { 423 .init = amx3_idle_init, 424 .suspend = amx3_idle_enter, 425 }; 426 427 CPUIDLE_METHOD_OF_DECLARE(pm33xx_idle, "ti,am3352", &amx3_cpuidle_ops); 428 CPUIDLE_METHOD_OF_DECLARE(pm43xx_idle, "ti,am4372", &amx3_cpuidle_ops); 429