1/* 2 * arch/arm/mach-at91/pm_slow_clock.S 3 * 4 * Copyright (C) 2006 Savin Zlobec 5 * 6 * AT91SAM9 support: 7 * Copyright (C) 2007 Anti Sullin <anti.sullin@artecdesign.ee> 8 * 9 * This program is free software; you can redistribute it and/or modify 10 * it under the terms of the GNU General Public License version 2 as 11 * published by the Free Software Foundation. 12 * 13 */ 14#include <linux/linkage.h> 15#include <linux/clk/at91_pmc.h> 16#include "pm.h" 17#include "generated/at91_pm_data-offsets.h" 18 19#define SRAMC_SELF_FRESH_ACTIVE 0x01 20#define SRAMC_SELF_FRESH_EXIT 0x00 21 22pmc .req r0 23tmp1 .req r4 24tmp2 .req r5 25 26/* 27 * Wait until master clock is ready (after switching master clock source) 28 */ 29 .macro wait_mckrdy 301: ldr tmp1, [pmc, #AT91_PMC_SR] 31 tst tmp1, #AT91_PMC_MCKRDY 32 beq 1b 33 .endm 34 35/* 36 * Wait until master oscillator has stabilized. 37 */ 38 .macro wait_moscrdy 391: ldr tmp1, [pmc, #AT91_PMC_SR] 40 tst tmp1, #AT91_PMC_MOSCS 41 beq 1b 42 .endm 43 44/* 45 * Wait for main oscillator selection is done 46 */ 47 .macro wait_moscsels 481: ldr tmp1, [pmc, #AT91_PMC_SR] 49 tst tmp1, #AT91_PMC_MOSCSELS 50 beq 1b 51 .endm 52 53/* 54 * Wait until PLLA has locked. 55 */ 56 .macro wait_pllalock 571: ldr tmp1, [pmc, #AT91_PMC_SR] 58 tst tmp1, #AT91_PMC_LOCKA 59 beq 1b 60 .endm 61 62/* 63 * Put the processor to enter the idle state 64 */ 65 .macro at91_cpu_idle 66 67#if defined(CONFIG_CPU_V7) 68 mov tmp1, #AT91_PMC_PCK 69 str tmp1, [pmc, #AT91_PMC_SCDR] 70 71 dsb 72 73 wfi @ Wait For Interrupt 74#else 75 mcr p15, 0, tmp1, c7, c0, 4 76#endif 77 78 .endm 79 80 .text 81 82 .arm 83 84/* 85 * void at91_suspend_sram_fn(struct at91_pm_data*) 86 * @input param: 87 * @r0: base address of struct at91_pm_data 88 */ 89/* at91_pm_suspend_in_sram must be 8-byte aligned per the requirements of fncpy() */ 90 .align 3 91ENTRY(at91_pm_suspend_in_sram) 92 /* Save registers on stack */ 93 stmfd sp!, {r4 - r12, lr} 94 95 /* Drain write buffer */ 96 mov tmp1, #0 97 mcr p15, 0, tmp1, c7, c10, 4 98 99 ldr tmp1, [r0, #PM_DATA_PMC] 100 str tmp1, .pmc_base 101 ldr tmp1, [r0, #PM_DATA_RAMC0] 102 str tmp1, .sramc_base 103 ldr tmp1, [r0, #PM_DATA_RAMC1] 104 str tmp1, .sramc1_base 105 ldr tmp1, [r0, #PM_DATA_MEMCTRL] 106 str tmp1, .memtype 107 ldr tmp1, [r0, #PM_DATA_MODE] 108 str tmp1, .pm_mode 109 /* Both ldrne below are here to preload their address in the TLB */ 110 ldr tmp1, [r0, #PM_DATA_SHDWC] 111 str tmp1, .shdwc 112 cmp tmp1, #0 113 ldrne tmp2, [tmp1, #0] 114 ldr tmp1, [r0, #PM_DATA_SFRBU] 115 str tmp1, .sfr 116 cmp tmp1, #0 117 ldrne tmp2, [tmp1, #0x10] 118 119 /* Active the self-refresh mode */ 120 mov r0, #SRAMC_SELF_FRESH_ACTIVE 121 bl at91_sramc_self_refresh 122 123 ldr r0, .pm_mode 124 cmp r0, #AT91_PM_STANDBY 125 beq standby 126 cmp r0, #AT91_PM_BACKUP 127 beq backup_mode 128 129 bl at91_ulp_mode 130 b exit_suspend 131 132standby: 133 /* Wait for interrupt */ 134 ldr pmc, .pmc_base 135 at91_cpu_idle 136 b exit_suspend 137 138backup_mode: 139 bl at91_backup_mode 140 b exit_suspend 141 142exit_suspend: 143 /* Exit the self-refresh mode */ 144 mov r0, #SRAMC_SELF_FRESH_EXIT 145 bl at91_sramc_self_refresh 146 147 /* Restore registers, and return */ 148 ldmfd sp!, {r4 - r12, pc} 149ENDPROC(at91_pm_suspend_in_sram) 150 151ENTRY(at91_backup_mode) 152 /*BUMEN*/ 153 ldr r0, .sfr 154 mov tmp1, #0x1 155 str tmp1, [r0, #0x10] 156 157 /* Shutdown */ 158 ldr r0, .shdwc 159 mov tmp1, #0xA5000000 160 add tmp1, tmp1, #0x1 161 str tmp1, [r0, #0] 162ENDPROC(at91_backup_mode) 163 164.macro at91_pm_ulp0_mode 165 ldr pmc, .pmc_base 166 167 /* Turn off the crystal oscillator */ 168 ldr tmp1, [pmc, #AT91_CKGR_MOR] 169 bic tmp1, tmp1, #AT91_PMC_MOSCEN 170 orr tmp1, tmp1, #AT91_PMC_KEY 171 str tmp1, [pmc, #AT91_CKGR_MOR] 172 173 /* Wait for interrupt */ 174 at91_cpu_idle 175 176 /* Turn on the crystal oscillator */ 177 ldr tmp1, [pmc, #AT91_CKGR_MOR] 178 orr tmp1, tmp1, #AT91_PMC_MOSCEN 179 orr tmp1, tmp1, #AT91_PMC_KEY 180 str tmp1, [pmc, #AT91_CKGR_MOR] 181 182 wait_moscrdy 183.endm 184 185/** 186 * Note: This procedure only applies on the platform which uses 187 * the external crystal oscillator as a main clock source. 188 */ 189.macro at91_pm_ulp1_mode 190 ldr pmc, .pmc_base 191 192 /* Switch the main clock source to 12-MHz RC oscillator */ 193 ldr tmp1, [pmc, #AT91_CKGR_MOR] 194 bic tmp1, tmp1, #AT91_PMC_MOSCSEL 195 bic tmp1, tmp1, #AT91_PMC_KEY_MASK 196 orr tmp1, tmp1, #AT91_PMC_KEY 197 str tmp1, [pmc, #AT91_CKGR_MOR] 198 199 wait_moscsels 200 201 /* Disable the crystal oscillator */ 202 ldr tmp1, [pmc, #AT91_CKGR_MOR] 203 bic tmp1, tmp1, #AT91_PMC_MOSCEN 204 bic tmp1, tmp1, #AT91_PMC_KEY_MASK 205 orr tmp1, tmp1, #AT91_PMC_KEY 206 str tmp1, [pmc, #AT91_CKGR_MOR] 207 208 /* Switch the master clock source to main clock */ 209 ldr tmp1, [pmc, #AT91_PMC_MCKR] 210 bic tmp1, tmp1, #AT91_PMC_CSS 211 orr tmp1, tmp1, #AT91_PMC_CSS_MAIN 212 str tmp1, [pmc, #AT91_PMC_MCKR] 213 214 wait_mckrdy 215 216 /* Enter the ULP1 mode by set WAITMODE bit in CKGR_MOR */ 217 ldr tmp1, [pmc, #AT91_CKGR_MOR] 218 orr tmp1, tmp1, #AT91_PMC_WAITMODE 219 bic tmp1, tmp1, #AT91_PMC_KEY_MASK 220 orr tmp1, tmp1, #AT91_PMC_KEY 221 str tmp1, [pmc, #AT91_CKGR_MOR] 222 223 wait_mckrdy 224 225 /* Enable the crystal oscillator */ 226 ldr tmp1, [pmc, #AT91_CKGR_MOR] 227 orr tmp1, tmp1, #AT91_PMC_MOSCEN 228 bic tmp1, tmp1, #AT91_PMC_KEY_MASK 229 orr tmp1, tmp1, #AT91_PMC_KEY 230 str tmp1, [pmc, #AT91_CKGR_MOR] 231 232 wait_moscrdy 233 234 /* Switch the master clock source to slow clock */ 235 ldr tmp1, [pmc, #AT91_PMC_MCKR] 236 bic tmp1, tmp1, #AT91_PMC_CSS 237 str tmp1, [pmc, #AT91_PMC_MCKR] 238 239 wait_mckrdy 240 241 /* Switch main clock source to crystal oscillator */ 242 ldr tmp1, [pmc, #AT91_CKGR_MOR] 243 orr tmp1, tmp1, #AT91_PMC_MOSCSEL 244 bic tmp1, tmp1, #AT91_PMC_KEY_MASK 245 orr tmp1, tmp1, #AT91_PMC_KEY 246 str tmp1, [pmc, #AT91_CKGR_MOR] 247 248 wait_moscsels 249 250 /* Switch the master clock source to main clock */ 251 ldr tmp1, [pmc, #AT91_PMC_MCKR] 252 bic tmp1, tmp1, #AT91_PMC_CSS 253 orr tmp1, tmp1, #AT91_PMC_CSS_MAIN 254 str tmp1, [pmc, #AT91_PMC_MCKR] 255 256 wait_mckrdy 257.endm 258 259ENTRY(at91_ulp_mode) 260 ldr pmc, .pmc_base 261 262 /* Save Master clock setting */ 263 ldr tmp1, [pmc, #AT91_PMC_MCKR] 264 str tmp1, .saved_mckr 265 266 /* 267 * Set the Master clock source to slow clock 268 */ 269 bic tmp1, tmp1, #AT91_PMC_CSS 270 str tmp1, [pmc, #AT91_PMC_MCKR] 271 272 wait_mckrdy 273 274 /* Save PLLA setting and disable it */ 275 ldr tmp1, [pmc, #AT91_CKGR_PLLAR] 276 str tmp1, .saved_pllar 277 278 mov tmp1, #AT91_PMC_PLLCOUNT 279 orr tmp1, tmp1, #(1 << 29) /* bit 29 always set */ 280 str tmp1, [pmc, #AT91_CKGR_PLLAR] 281 282 ldr r0, .pm_mode 283 cmp r0, #AT91_PM_ULP1 284 beq ulp1_mode 285 286 at91_pm_ulp0_mode 287 b ulp_exit 288 289ulp1_mode: 290 at91_pm_ulp1_mode 291 b ulp_exit 292 293ulp_exit: 294 ldr pmc, .pmc_base 295 296 /* Restore PLLA setting */ 297 ldr tmp1, .saved_pllar 298 str tmp1, [pmc, #AT91_CKGR_PLLAR] 299 300 tst tmp1, #(AT91_PMC_MUL & 0xff0000) 301 bne 3f 302 tst tmp1, #(AT91_PMC_MUL & ~0xff0000) 303 beq 4f 3043: 305 wait_pllalock 3064: 307 308 /* 309 * Restore master clock setting 310 */ 311 ldr tmp1, .saved_mckr 312 str tmp1, [pmc, #AT91_PMC_MCKR] 313 314 wait_mckrdy 315 316 mov pc, lr 317ENDPROC(at91_ulp_mode) 318 319/* 320 * void at91_sramc_self_refresh(unsigned int is_active) 321 * 322 * @input param: 323 * @r0: 1 - active self-refresh mode 324 * 0 - exit self-refresh mode 325 * register usage: 326 * @r1: memory type 327 * @r2: base address of the sram controller 328 */ 329 330ENTRY(at91_sramc_self_refresh) 331 ldr r1, .memtype 332 ldr r2, .sramc_base 333 334 cmp r1, #AT91_MEMCTRL_MC 335 bne ddrc_sf 336 337 /* 338 * at91rm9200 Memory controller 339 */ 340 341 /* 342 * For exiting the self-refresh mode, do nothing, 343 * automatically exit the self-refresh mode. 344 */ 345 tst r0, #SRAMC_SELF_FRESH_ACTIVE 346 beq exit_sramc_sf 347 348 /* Active SDRAM self-refresh mode */ 349 mov r3, #1 350 str r3, [r2, #AT91_MC_SDRAMC_SRR] 351 b exit_sramc_sf 352 353ddrc_sf: 354 cmp r1, #AT91_MEMCTRL_DDRSDR 355 bne sdramc_sf 356 357 /* 358 * DDR Memory controller 359 */ 360 tst r0, #SRAMC_SELF_FRESH_ACTIVE 361 beq ddrc_exit_sf 362 363 /* LPDDR1 --> force DDR2 mode during self-refresh */ 364 ldr r3, [r2, #AT91_DDRSDRC_MDR] 365 str r3, .saved_sam9_mdr 366 bic r3, r3, #~AT91_DDRSDRC_MD 367 cmp r3, #AT91_DDRSDRC_MD_LOW_POWER_DDR 368 ldreq r3, [r2, #AT91_DDRSDRC_MDR] 369 biceq r3, r3, #AT91_DDRSDRC_MD 370 orreq r3, r3, #AT91_DDRSDRC_MD_DDR2 371 streq r3, [r2, #AT91_DDRSDRC_MDR] 372 373 /* Active DDRC self-refresh mode */ 374 ldr r3, [r2, #AT91_DDRSDRC_LPR] 375 str r3, .saved_sam9_lpr 376 bic r3, r3, #AT91_DDRSDRC_LPCB 377 orr r3, r3, #AT91_DDRSDRC_LPCB_SELF_REFRESH 378 str r3, [r2, #AT91_DDRSDRC_LPR] 379 380 /* If using the 2nd ddr controller */ 381 ldr r2, .sramc1_base 382 cmp r2, #0 383 beq no_2nd_ddrc 384 385 ldr r3, [r2, #AT91_DDRSDRC_MDR] 386 str r3, .saved_sam9_mdr1 387 bic r3, r3, #~AT91_DDRSDRC_MD 388 cmp r3, #AT91_DDRSDRC_MD_LOW_POWER_DDR 389 ldreq r3, [r2, #AT91_DDRSDRC_MDR] 390 biceq r3, r3, #AT91_DDRSDRC_MD 391 orreq r3, r3, #AT91_DDRSDRC_MD_DDR2 392 streq r3, [r2, #AT91_DDRSDRC_MDR] 393 394 /* Active DDRC self-refresh mode */ 395 ldr r3, [r2, #AT91_DDRSDRC_LPR] 396 str r3, .saved_sam9_lpr1 397 bic r3, r3, #AT91_DDRSDRC_LPCB 398 orr r3, r3, #AT91_DDRSDRC_LPCB_SELF_REFRESH 399 str r3, [r2, #AT91_DDRSDRC_LPR] 400 401no_2nd_ddrc: 402 b exit_sramc_sf 403 404ddrc_exit_sf: 405 /* Restore MDR in case of LPDDR1 */ 406 ldr r3, .saved_sam9_mdr 407 str r3, [r2, #AT91_DDRSDRC_MDR] 408 /* Restore LPR on AT91 with DDRAM */ 409 ldr r3, .saved_sam9_lpr 410 str r3, [r2, #AT91_DDRSDRC_LPR] 411 412 /* If using the 2nd ddr controller */ 413 ldr r2, .sramc1_base 414 cmp r2, #0 415 ldrne r3, .saved_sam9_mdr1 416 strne r3, [r2, #AT91_DDRSDRC_MDR] 417 ldrne r3, .saved_sam9_lpr1 418 strne r3, [r2, #AT91_DDRSDRC_LPR] 419 420 b exit_sramc_sf 421 422 /* 423 * SDRAMC Memory controller 424 */ 425sdramc_sf: 426 tst r0, #SRAMC_SELF_FRESH_ACTIVE 427 beq sdramc_exit_sf 428 429 /* Active SDRAMC self-refresh mode */ 430 ldr r3, [r2, #AT91_SDRAMC_LPR] 431 str r3, .saved_sam9_lpr 432 bic r3, r3, #AT91_SDRAMC_LPCB 433 orr r3, r3, #AT91_SDRAMC_LPCB_SELF_REFRESH 434 str r3, [r2, #AT91_SDRAMC_LPR] 435 436sdramc_exit_sf: 437 ldr r3, .saved_sam9_lpr 438 str r3, [r2, #AT91_SDRAMC_LPR] 439 440exit_sramc_sf: 441 mov pc, lr 442ENDPROC(at91_sramc_self_refresh) 443 444.pmc_base: 445 .word 0 446.sramc_base: 447 .word 0 448.sramc1_base: 449 .word 0 450.shdwc: 451 .word 0 452.sfr: 453 .word 0 454.memtype: 455 .word 0 456.pm_mode: 457 .word 0 458.saved_mckr: 459 .word 0 460.saved_pllar: 461 .word 0 462.saved_sam9_lpr: 463 .word 0 464.saved_sam9_lpr1: 465 .word 0 466.saved_sam9_mdr: 467 .word 0 468.saved_sam9_mdr1: 469 .word 0 470 471ENTRY(at91_pm_suspend_in_sram_sz) 472 .word .-at91_pm_suspend_in_sram 473