dpmc_modes.S 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895
  1. /*
  2. * Copyright 2004-2008 Analog Devices Inc.
  3. *
  4. * Licensed under the GPL-2 or later.
  5. */
  6. #include <linux/linkage.h>
  7. #include <asm/blackfin.h>
  8. #include <mach/irq.h>
  9. #include <asm/dpmc.h>
  10. .section .l1.text
  11. ENTRY(_sleep_mode)
  12. [--SP] = (R7:4, P5:3);
  13. [--SP] = RETS;
  14. call _set_sic_iwr;
  15. P0.H = hi(PLL_CTL);
  16. P0.L = lo(PLL_CTL);
  17. R1 = W[P0](z);
  18. BITSET (R1, 3);
  19. W[P0] = R1.L;
  20. CLI R2;
  21. SSYNC;
  22. IDLE;
  23. STI R2;
  24. call _test_pll_locked;
  25. R0 = IWR_ENABLE(0);
  26. R1 = IWR_DISABLE_ALL;
  27. R2 = IWR_DISABLE_ALL;
  28. call _set_sic_iwr;
  29. P0.H = hi(PLL_CTL);
  30. P0.L = lo(PLL_CTL);
  31. R7 = w[p0](z);
  32. BITCLR (R7, 3);
  33. BITCLR (R7, 5);
  34. w[p0] = R7.L;
  35. IDLE;
  36. call _test_pll_locked;
  37. RETS = [SP++];
  38. (R7:4, P5:3) = [SP++];
  39. RTS;
  40. ENDPROC(_sleep_mode)
  41. /*
  42. * This func never returns as it puts the part into hibernate, and
  43. * is only called from do_hibernate, so we don't bother saving or
  44. * restoring any of the normal C runtime state. When we wake up,
  45. * the entry point will be in do_hibernate and not here.
  46. *
  47. * We accept just one argument -- the value to write to VR_CTL.
  48. */
  49. ENTRY(_hibernate_mode)
  50. /* Save/setup the regs we need early for minor pipeline optimization */
  51. R4 = R0;
  52. P3.H = hi(VR_CTL);
  53. P3.L = lo(VR_CTL);
  54. /* Disable all wakeup sources */
  55. R0 = IWR_DISABLE_ALL;
  56. R1 = IWR_DISABLE_ALL;
  57. R2 = IWR_DISABLE_ALL;
  58. call _set_sic_iwr;
  59. call _set_dram_srfs;
  60. SSYNC;
  61. /* Finally, we climb into our cave to hibernate */
  62. W[P3] = R4.L;
  63. CLI R2;
  64. IDLE;
  65. .Lforever:
  66. jump .Lforever;
  67. ENDPROC(_hibernate_mode)
  68. ENTRY(_sleep_deeper)
  69. [--SP] = (R7:4, P5:3);
  70. [--SP] = RETS;
  71. CLI R4;
  72. P3 = R0;
  73. P4 = R1;
  74. P5 = R2;
  75. R0 = IWR_ENABLE(0);
  76. R1 = IWR_DISABLE_ALL;
  77. R2 = IWR_DISABLE_ALL;
  78. call _set_sic_iwr;
  79. call _set_dram_srfs; /* Set SDRAM Self Refresh */
  80. P0.H = hi(PLL_DIV);
  81. P0.L = lo(PLL_DIV);
  82. R6 = W[P0](z);
  83. R0.L = 0xF;
  84. W[P0] = R0.l; /* Set Max VCO to SCLK divider */
  85. P0.H = hi(PLL_CTL);
  86. P0.L = lo(PLL_CTL);
  87. R5 = W[P0](z);
  88. R0.L = (CONFIG_MIN_VCO_HZ/CONFIG_CLKIN_HZ) << 9;
  89. W[P0] = R0.l; /* Set Min CLKIN to VCO multiplier */
  90. SSYNC;
  91. IDLE;
  92. call _test_pll_locked;
  93. P0.H = hi(VR_CTL);
  94. P0.L = lo(VR_CTL);
  95. R7 = W[P0](z);
  96. R1 = 0x6;
  97. R1 <<= 16;
  98. R2 = 0x0404(Z);
  99. R1 = R1|R2;
  100. R2 = DEPOSIT(R7, R1);
  101. W[P0] = R2; /* Set Min Core Voltage */
  102. SSYNC;
  103. IDLE;
  104. call _test_pll_locked;
  105. R0 = P3;
  106. R1 = P4;
  107. R3 = P5;
  108. call _set_sic_iwr; /* Set Awake from IDLE */
  109. P0.H = hi(PLL_CTL);
  110. P0.L = lo(PLL_CTL);
  111. R0 = W[P0](z);
  112. BITSET (R0, 3);
  113. W[P0] = R0.L; /* Turn CCLK OFF */
  114. SSYNC;
  115. IDLE;
  116. call _test_pll_locked;
  117. R0 = IWR_ENABLE(0);
  118. R1 = IWR_DISABLE_ALL;
  119. R2 = IWR_DISABLE_ALL;
  120. call _set_sic_iwr; /* Set Awake from IDLE PLL */
  121. P0.H = hi(VR_CTL);
  122. P0.L = lo(VR_CTL);
  123. W[P0]= R7;
  124. SSYNC;
  125. IDLE;
  126. call _test_pll_locked;
  127. P0.H = hi(PLL_DIV);
  128. P0.L = lo(PLL_DIV);
  129. W[P0]= R6; /* Restore CCLK and SCLK divider */
  130. P0.H = hi(PLL_CTL);
  131. P0.L = lo(PLL_CTL);
  132. w[p0] = R5; /* Restore VCO multiplier */
  133. IDLE;
  134. call _test_pll_locked;
  135. call _unset_dram_srfs; /* SDRAM Self Refresh Off */
  136. STI R4;
  137. RETS = [SP++];
  138. (R7:4, P5:3) = [SP++];
  139. RTS;
  140. ENDPROC(_sleep_deeper)
  141. ENTRY(_set_dram_srfs)
  142. /* set the dram to self refresh mode */
  143. SSYNC;
  144. #if defined(EBIU_RSTCTL) /* DDR */
  145. P0.H = hi(EBIU_RSTCTL);
  146. P0.L = lo(EBIU_RSTCTL);
  147. R2 = [P0];
  148. BITSET(R2, 3); /* SRREQ enter self-refresh mode */
  149. [P0] = R2;
  150. SSYNC;
  151. 1:
  152. R2 = [P0];
  153. CC = BITTST(R2, 4);
  154. if !CC JUMP 1b;
  155. #else /* SDRAM */
  156. P0.L = lo(EBIU_SDGCTL);
  157. P0.H = hi(EBIU_SDGCTL);
  158. P1.L = lo(EBIU_SDSTAT);
  159. P1.H = hi(EBIU_SDSTAT);
  160. R2 = [P0];
  161. BITSET(R2, 24); /* SRFS enter self-refresh mode */
  162. [P0] = R2;
  163. SSYNC;
  164. 1:
  165. R2 = w[P1];
  166. SSYNC;
  167. cc = BITTST(R2, 1); /* SDSRA poll self-refresh status */
  168. if !cc jump 1b;
  169. R2 = [P0];
  170. BITCLR(R2, 0); /* SCTLE disable CLKOUT */
  171. [P0] = R2;
  172. #endif
  173. RTS;
  174. ENDPROC(_set_dram_srfs)
  175. ENTRY(_unset_dram_srfs)
  176. /* set the dram out of self refresh mode */
  177. #if defined(EBIU_RSTCTL) /* DDR */
  178. P0.H = hi(EBIU_RSTCTL);
  179. P0.L = lo(EBIU_RSTCTL);
  180. R2 = [P0];
  181. BITCLR(R2, 3); /* clear SRREQ bit */
  182. [P0] = R2;
  183. #elif defined(EBIU_SDGCTL) /* SDRAM */
  184. /* release CLKOUT from self-refresh */
  185. P0.L = lo(EBIU_SDGCTL);
  186. P0.H = hi(EBIU_SDGCTL);
  187. R2 = [P0];
  188. BITSET(R2, 0); /* SCTLE enable CLKOUT */
  189. [P0] = R2
  190. SSYNC;
  191. /* release SDRAM from self-refresh */
  192. R2 = [P0];
  193. BITCLR(R2, 24); /* clear SRFS bit */
  194. [P0] = R2
  195. #endif
  196. SSYNC;
  197. RTS;
  198. ENDPROC(_unset_dram_srfs)
  199. ENTRY(_set_sic_iwr)
  200. #ifdef SIC_IWR0
  201. P0.H = hi(SYSMMR_BASE);
  202. P0.L = lo(SYSMMR_BASE);
  203. [P0 + (SIC_IWR0 - SYSMMR_BASE)] = R0;
  204. [P0 + (SIC_IWR1 - SYSMMR_BASE)] = R1;
  205. # ifdef SIC_IWR2
  206. [P0 + (SIC_IWR2 - SYSMMR_BASE)] = R2;
  207. # endif
  208. #else
  209. P0.H = hi(SIC_IWR);
  210. P0.L = lo(SIC_IWR);
  211. [P0] = R0;
  212. #endif
  213. SSYNC;
  214. RTS;
  215. ENDPROC(_set_sic_iwr)
  216. ENTRY(_test_pll_locked)
  217. P0.H = hi(PLL_STAT);
  218. P0.L = lo(PLL_STAT);
  219. 1:
  220. R0 = W[P0] (Z);
  221. CC = BITTST(R0,5);
  222. IF !CC JUMP 1b;
  223. RTS;
  224. ENDPROC(_test_pll_locked)
  225. .section .text
  226. #define PM_REG0 R7
  227. #define PM_REG1 R6
  228. #define PM_REG2 R5
  229. #define PM_REG3 R4
  230. #define PM_REG4 R3
  231. #define PM_REG5 R2
  232. #define PM_REG6 R1
  233. #define PM_REG7 R0
  234. #define PM_REG8 P5
  235. #define PM_REG9 P4
  236. #define PM_REG10 P3
  237. #define PM_REG11 P2
  238. #define PM_REG12 P1
  239. #define PM_REG13 P0
  240. #define PM_REGSET0 R7:7
  241. #define PM_REGSET1 R7:6
  242. #define PM_REGSET2 R7:5
  243. #define PM_REGSET3 R7:4
  244. #define PM_REGSET4 R7:3
  245. #define PM_REGSET5 R7:2
  246. #define PM_REGSET6 R7:1
  247. #define PM_REGSET7 R7:0
  248. #define PM_REGSET8 R7:0, P5:5
  249. #define PM_REGSET9 R7:0, P5:4
  250. #define PM_REGSET10 R7:0, P5:3
  251. #define PM_REGSET11 R7:0, P5:2
  252. #define PM_REGSET12 R7:0, P5:1
  253. #define PM_REGSET13 R7:0, P5:0
  254. #define _PM_PUSH(n, x, w, base) PM_REG##n = w[FP + ((x) - (base))];
  255. #define _PM_POP(n, x, w, base) w[FP + ((x) - (base))] = PM_REG##n;
  256. #define PM_PUSH_SYNC(n) [--sp] = (PM_REGSET##n);
  257. #define PM_POP_SYNC(n) (PM_REGSET##n) = [sp++];
  258. #define PM_PUSH(n, x) PM_REG##n = [FP++];
  259. #define PM_POP(n, x) [FP--] = PM_REG##n;
  260. #define PM_CORE_PUSH(n, x) _PM_PUSH(n, x, , COREMMR_BASE)
  261. #define PM_CORE_POP(n, x) _PM_POP(n, x, , COREMMR_BASE)
  262. #define PM_SYS_PUSH(n, x) _PM_PUSH(n, x, , SYSMMR_BASE)
  263. #define PM_SYS_POP(n, x) _PM_POP(n, x, , SYSMMR_BASE)
  264. #define PM_SYS_PUSH16(n, x) _PM_PUSH(n, x, w, SYSMMR_BASE)
  265. #define PM_SYS_POP16(n, x) _PM_POP(n, x, w, SYSMMR_BASE)
  266. ENTRY(_do_hibernate)
  267. /*
  268. * Save the core regs early so we can blow them away when
  269. * saving/restoring MMR states
  270. */
  271. [--sp] = (R7:0, P5:0);
  272. [--sp] = fp;
  273. [--sp] = usp;
  274. [--sp] = i0;
  275. [--sp] = i1;
  276. [--sp] = i2;
  277. [--sp] = i3;
  278. [--sp] = m0;
  279. [--sp] = m1;
  280. [--sp] = m2;
  281. [--sp] = m3;
  282. [--sp] = l0;
  283. [--sp] = l1;
  284. [--sp] = l2;
  285. [--sp] = l3;
  286. [--sp] = b0;
  287. [--sp] = b1;
  288. [--sp] = b2;
  289. [--sp] = b3;
  290. [--sp] = a0.x;
  291. [--sp] = a0.w;
  292. [--sp] = a1.x;
  293. [--sp] = a1.w;
  294. [--sp] = LC0;
  295. [--sp] = LC1;
  296. [--sp] = LT0;
  297. [--sp] = LT1;
  298. [--sp] = LB0;
  299. [--sp] = LB1;
  300. /* We can't push RETI directly as that'll change IPEND[4] */
  301. r7 = RETI;
  302. [--sp] = RETS;
  303. [--sp] = ASTAT;
  304. [--sp] = CYCLES;
  305. [--sp] = CYCLES2;
  306. [--sp] = SYSCFG;
  307. [--sp] = RETX;
  308. [--sp] = SEQSTAT;
  309. [--sp] = r7;
  310. /* Save first func arg in M3 */
  311. M3 = R0;
  312. /* Save system MMRs */
  313. FP.H = hi(SYSMMR_BASE);
  314. FP.L = lo(SYSMMR_BASE);
  315. #ifdef SIC_IMASK0
  316. PM_SYS_PUSH(0, SIC_IMASK0)
  317. PM_SYS_PUSH(1, SIC_IMASK1)
  318. # ifdef SIC_IMASK2
  319. PM_SYS_PUSH(2, SIC_IMASK2)
  320. # endif
  321. #else
  322. PM_SYS_PUSH(0, SIC_IMASK)
  323. #endif
  324. #ifdef SIC_IAR0
  325. PM_SYS_PUSH(3, SIC_IAR0)
  326. PM_SYS_PUSH(4, SIC_IAR1)
  327. PM_SYS_PUSH(5, SIC_IAR2)
  328. #endif
  329. #ifdef SIC_IAR3
  330. PM_SYS_PUSH(6, SIC_IAR3)
  331. #endif
  332. #ifdef SIC_IAR4
  333. PM_SYS_PUSH(7, SIC_IAR4)
  334. PM_SYS_PUSH(8, SIC_IAR5)
  335. PM_SYS_PUSH(9, SIC_IAR6)
  336. #endif
  337. #ifdef SIC_IAR7
  338. PM_SYS_PUSH(10, SIC_IAR7)
  339. #endif
  340. #ifdef SIC_IAR8
  341. PM_SYS_PUSH(11, SIC_IAR8)
  342. PM_SYS_PUSH(12, SIC_IAR9)
  343. PM_SYS_PUSH(13, SIC_IAR10)
  344. #endif
  345. PM_PUSH_SYNC(13)
  346. #ifdef SIC_IAR11
  347. PM_SYS_PUSH(0, SIC_IAR11)
  348. #endif
  349. #ifdef SIC_IWR
  350. PM_SYS_PUSH(1, SIC_IWR)
  351. #endif
  352. #ifdef SIC_IWR0
  353. PM_SYS_PUSH(1, SIC_IWR0)
  354. #endif
  355. #ifdef SIC_IWR1
  356. PM_SYS_PUSH(2, SIC_IWR1)
  357. #endif
  358. #ifdef SIC_IWR2
  359. PM_SYS_PUSH(3, SIC_IWR2)
  360. #endif
  361. #ifdef PINT0_ASSIGN
  362. PM_SYS_PUSH(4, PINT0_MASK_SET)
  363. PM_SYS_PUSH(5, PINT1_MASK_SET)
  364. PM_SYS_PUSH(6, PINT2_MASK_SET)
  365. PM_SYS_PUSH(7, PINT3_MASK_SET)
  366. PM_SYS_PUSH(8, PINT0_ASSIGN)
  367. PM_SYS_PUSH(9, PINT1_ASSIGN)
  368. PM_SYS_PUSH(10, PINT2_ASSIGN)
  369. PM_SYS_PUSH(11, PINT3_ASSIGN)
  370. PM_SYS_PUSH(12, PINT0_INVERT_SET)
  371. PM_SYS_PUSH(13, PINT1_INVERT_SET)
  372. PM_PUSH_SYNC(13)
  373. PM_SYS_PUSH(0, PINT2_INVERT_SET)
  374. PM_SYS_PUSH(1, PINT3_INVERT_SET)
  375. PM_SYS_PUSH(2, PINT0_EDGE_SET)
  376. PM_SYS_PUSH(3, PINT1_EDGE_SET)
  377. PM_SYS_PUSH(4, PINT2_EDGE_SET)
  378. PM_SYS_PUSH(5, PINT3_EDGE_SET)
  379. #endif
  380. PM_SYS_PUSH16(6, SYSCR)
  381. PM_SYS_PUSH16(7, EBIU_AMGCTL)
  382. PM_SYS_PUSH(8, EBIU_AMBCTL0)
  383. PM_SYS_PUSH(9, EBIU_AMBCTL1)
  384. #ifdef EBIU_FCTL
  385. PM_SYS_PUSH(10, EBIU_MBSCTL)
  386. PM_SYS_PUSH(11, EBIU_MODE)
  387. PM_SYS_PUSH(12, EBIU_FCTL)
  388. PM_PUSH_SYNC(12)
  389. #else
  390. PM_PUSH_SYNC(9)
  391. #endif
  392. /* Save Core MMRs */
  393. I0.H = hi(COREMMR_BASE);
  394. I0.L = lo(COREMMR_BASE);
  395. I1 = I0;
  396. I2 = I0;
  397. I3 = I0;
  398. B0 = I0;
  399. B1 = I0;
  400. B2 = I0;
  401. B3 = I0;
  402. I1.L = lo(DCPLB_ADDR0);
  403. I2.L = lo(DCPLB_DATA0);
  404. I3.L = lo(ICPLB_ADDR0);
  405. B0.L = lo(ICPLB_DATA0);
  406. B1.L = lo(EVT2);
  407. B2.L = lo(IMASK);
  408. B3.L = lo(TCNTL);
  409. /* DCPLB Addr */
  410. FP = I1;
  411. PM_PUSH(0, DCPLB_ADDR0)
  412. PM_PUSH(1, DCPLB_ADDR1)
  413. PM_PUSH(2, DCPLB_ADDR2)
  414. PM_PUSH(3, DCPLB_ADDR3)
  415. PM_PUSH(4, DCPLB_ADDR4)
  416. PM_PUSH(5, DCPLB_ADDR5)
  417. PM_PUSH(6, DCPLB_ADDR6)
  418. PM_PUSH(7, DCPLB_ADDR7)
  419. PM_PUSH(8, DCPLB_ADDR8)
  420. PM_PUSH(9, DCPLB_ADDR9)
  421. PM_PUSH(10, DCPLB_ADDR10)
  422. PM_PUSH(11, DCPLB_ADDR11)
  423. PM_PUSH(12, DCPLB_ADDR12)
  424. PM_PUSH(13, DCPLB_ADDR13)
  425. PM_PUSH_SYNC(13)
  426. PM_PUSH(0, DCPLB_ADDR14)
  427. PM_PUSH(1, DCPLB_ADDR15)
  428. /* DCPLB Data */
  429. FP = I2;
  430. PM_PUSH(2, DCPLB_DATA0)
  431. PM_PUSH(3, DCPLB_DATA1)
  432. PM_PUSH(4, DCPLB_DATA2)
  433. PM_PUSH(5, DCPLB_DATA3)
  434. PM_PUSH(6, DCPLB_DATA4)
  435. PM_PUSH(7, DCPLB_DATA5)
  436. PM_PUSH(8, DCPLB_DATA6)
  437. PM_PUSH(9, DCPLB_DATA7)
  438. PM_PUSH(10, DCPLB_DATA8)
  439. PM_PUSH(11, DCPLB_DATA9)
  440. PM_PUSH(12, DCPLB_DATA10)
  441. PM_PUSH(13, DCPLB_DATA11)
  442. PM_PUSH_SYNC(13)
  443. PM_PUSH(0, DCPLB_DATA12)
  444. PM_PUSH(1, DCPLB_DATA13)
  445. PM_PUSH(2, DCPLB_DATA14)
  446. PM_PUSH(3, DCPLB_DATA15)
  447. /* ICPLB Addr */
  448. FP = I3;
  449. PM_PUSH(4, ICPLB_ADDR0)
  450. PM_PUSH(5, ICPLB_ADDR1)
  451. PM_PUSH(6, ICPLB_ADDR2)
  452. PM_PUSH(7, ICPLB_ADDR3)
  453. PM_PUSH(8, ICPLB_ADDR4)
  454. PM_PUSH(9, ICPLB_ADDR5)
  455. PM_PUSH(10, ICPLB_ADDR6)
  456. PM_PUSH(11, ICPLB_ADDR7)
  457. PM_PUSH(12, ICPLB_ADDR8)
  458. PM_PUSH(13, ICPLB_ADDR9)
  459. PM_PUSH_SYNC(13)
  460. PM_PUSH(0, ICPLB_ADDR10)
  461. PM_PUSH(1, ICPLB_ADDR11)
  462. PM_PUSH(2, ICPLB_ADDR12)
  463. PM_PUSH(3, ICPLB_ADDR13)
  464. PM_PUSH(4, ICPLB_ADDR14)
  465. PM_PUSH(5, ICPLB_ADDR15)
  466. /* ICPLB Data */
  467. FP = B0;
  468. PM_PUSH(6, ICPLB_DATA0)
  469. PM_PUSH(7, ICPLB_DATA1)
  470. PM_PUSH(8, ICPLB_DATA2)
  471. PM_PUSH(9, ICPLB_DATA3)
  472. PM_PUSH(10, ICPLB_DATA4)
  473. PM_PUSH(11, ICPLB_DATA5)
  474. PM_PUSH(12, ICPLB_DATA6)
  475. PM_PUSH(13, ICPLB_DATA7)
  476. PM_PUSH_SYNC(13)
  477. PM_PUSH(0, ICPLB_DATA8)
  478. PM_PUSH(1, ICPLB_DATA9)
  479. PM_PUSH(2, ICPLB_DATA10)
  480. PM_PUSH(3, ICPLB_DATA11)
  481. PM_PUSH(4, ICPLB_DATA12)
  482. PM_PUSH(5, ICPLB_DATA13)
  483. PM_PUSH(6, ICPLB_DATA14)
  484. PM_PUSH(7, ICPLB_DATA15)
  485. /* Event Vectors */
  486. FP = B1;
  487. PM_PUSH(8, EVT2)
  488. PM_PUSH(9, EVT3)
  489. FP += 4; /* EVT4 */
  490. PM_PUSH(10, EVT5)
  491. PM_PUSH(11, EVT6)
  492. PM_PUSH(12, EVT7)
  493. PM_PUSH(13, EVT8)
  494. PM_PUSH_SYNC(13)
  495. PM_PUSH(0, EVT9)
  496. PM_PUSH(1, EVT10)
  497. PM_PUSH(2, EVT11)
  498. PM_PUSH(3, EVT12)
  499. PM_PUSH(4, EVT13)
  500. PM_PUSH(5, EVT14)
  501. PM_PUSH(6, EVT15)
  502. /* CEC */
  503. FP = B2;
  504. PM_PUSH(7, IMASK)
  505. FP += 4; /* IPEND */
  506. PM_PUSH(8, ILAT)
  507. PM_PUSH(9, IPRIO)
  508. /* Core Timer */
  509. FP = B3;
  510. PM_PUSH(10, TCNTL)
  511. PM_PUSH(11, TPERIOD)
  512. PM_PUSH(12, TSCALE)
  513. PM_PUSH(13, TCOUNT)
  514. PM_PUSH_SYNC(13)
  515. /* Misc non-contiguous registers */
  516. FP = I0;
  517. PM_CORE_PUSH(0, DMEM_CONTROL);
  518. PM_CORE_PUSH(1, IMEM_CONTROL);
  519. PM_CORE_PUSH(2, TBUFCTL);
  520. PM_PUSH_SYNC(2)
  521. /* Setup args to hibernate mode early for pipeline optimization */
  522. R0 = M3;
  523. P1.H = _hibernate_mode;
  524. P1.L = _hibernate_mode;
  525. /* Save Magic, return address and Stack Pointer */
  526. P0 = 0;
  527. R1.H = 0xDEAD; /* Hibernate Magic */
  528. R1.L = 0xBEEF;
  529. R2.H = .Lpm_resume_here;
  530. R2.L = .Lpm_resume_here;
  531. [P0++] = R1; /* Store Hibernate Magic */
  532. [P0++] = R2; /* Save Return Address */
  533. [P0++] = SP; /* Save Stack Pointer */
  534. /* Must use an indirect call as we need to jump to L1 */
  535. call (P1); /* Goodbye */
  536. .Lpm_resume_here:
  537. /* Restore Core MMRs */
  538. I0.H = hi(COREMMR_BASE);
  539. I0.L = lo(COREMMR_BASE);
  540. I1 = I0;
  541. I2 = I0;
  542. I3 = I0;
  543. B0 = I0;
  544. B1 = I0;
  545. B2 = I0;
  546. B3 = I0;
  547. I1.L = lo(DCPLB_ADDR15);
  548. I2.L = lo(DCPLB_DATA15);
  549. I3.L = lo(ICPLB_ADDR15);
  550. B0.L = lo(ICPLB_DATA15);
  551. B1.L = lo(EVT15);
  552. B2.L = lo(IPRIO);
  553. B3.L = lo(TCOUNT);
  554. /* Misc non-contiguous registers */
  555. FP = I0;
  556. PM_POP_SYNC(2)
  557. PM_CORE_POP(2, TBUFCTL)
  558. PM_CORE_POP(1, IMEM_CONTROL)
  559. PM_CORE_POP(0, DMEM_CONTROL)
  560. /* Core Timer */
  561. PM_POP_SYNC(13)
  562. FP = B3;
  563. PM_POP(13, TCOUNT)
  564. PM_POP(12, TSCALE)
  565. PM_POP(11, TPERIOD)
  566. PM_POP(10, TCNTL)
  567. /* CEC */
  568. FP = B2;
  569. PM_POP(9, IPRIO)
  570. PM_POP(8, ILAT)
  571. FP += -4; /* IPEND */
  572. PM_POP(7, IMASK)
  573. /* Event Vectors */
  574. FP = B1;
  575. PM_POP(6, EVT15)
  576. PM_POP(5, EVT14)
  577. PM_POP(4, EVT13)
  578. PM_POP(3, EVT12)
  579. PM_POP(2, EVT11)
  580. PM_POP(1, EVT10)
  581. PM_POP(0, EVT9)
  582. PM_POP_SYNC(13)
  583. PM_POP(13, EVT8)
  584. PM_POP(12, EVT7)
  585. PM_POP(11, EVT6)
  586. PM_POP(10, EVT5)
  587. FP += -4; /* EVT4 */
  588. PM_POP(9, EVT3)
  589. PM_POP(8, EVT2)
  590. /* ICPLB Data */
  591. FP = B0;
  592. PM_POP(7, ICPLB_DATA15)
  593. PM_POP(6, ICPLB_DATA14)
  594. PM_POP(5, ICPLB_DATA13)
  595. PM_POP(4, ICPLB_DATA12)
  596. PM_POP(3, ICPLB_DATA11)
  597. PM_POP(2, ICPLB_DATA10)
  598. PM_POP(1, ICPLB_DATA9)
  599. PM_POP(0, ICPLB_DATA8)
  600. PM_POP_SYNC(13)
  601. PM_POP(13, ICPLB_DATA7)
  602. PM_POP(12, ICPLB_DATA6)
  603. PM_POP(11, ICPLB_DATA5)
  604. PM_POP(10, ICPLB_DATA4)
  605. PM_POP(9, ICPLB_DATA3)
  606. PM_POP(8, ICPLB_DATA2)
  607. PM_POP(7, ICPLB_DATA1)
  608. PM_POP(6, ICPLB_DATA0)
  609. /* ICPLB Addr */
  610. FP = I3;
  611. PM_POP(5, ICPLB_ADDR15)
  612. PM_POP(4, ICPLB_ADDR14)
  613. PM_POP(3, ICPLB_ADDR13)
  614. PM_POP(2, ICPLB_ADDR12)
  615. PM_POP(1, ICPLB_ADDR11)
  616. PM_POP(0, ICPLB_ADDR10)
  617. PM_POP_SYNC(13)
  618. PM_POP(13, ICPLB_ADDR9)
  619. PM_POP(12, ICPLB_ADDR8)
  620. PM_POP(11, ICPLB_ADDR7)
  621. PM_POP(10, ICPLB_ADDR6)
  622. PM_POP(9, ICPLB_ADDR5)
  623. PM_POP(8, ICPLB_ADDR4)
  624. PM_POP(7, ICPLB_ADDR3)
  625. PM_POP(6, ICPLB_ADDR2)
  626. PM_POP(5, ICPLB_ADDR1)
  627. PM_POP(4, ICPLB_ADDR0)
  628. /* DCPLB Data */
  629. FP = I2;
  630. PM_POP(3, DCPLB_DATA15)
  631. PM_POP(2, DCPLB_DATA14)
  632. PM_POP(1, DCPLB_DATA13)
  633. PM_POP(0, DCPLB_DATA12)
  634. PM_POP_SYNC(13)
  635. PM_POP(13, DCPLB_DATA11)
  636. PM_POP(12, DCPLB_DATA10)
  637. PM_POP(11, DCPLB_DATA9)
  638. PM_POP(10, DCPLB_DATA8)
  639. PM_POP(9, DCPLB_DATA7)
  640. PM_POP(8, DCPLB_DATA6)
  641. PM_POP(7, DCPLB_DATA5)
  642. PM_POP(6, DCPLB_DATA4)
  643. PM_POP(5, DCPLB_DATA3)
  644. PM_POP(4, DCPLB_DATA2)
  645. PM_POP(3, DCPLB_DATA1)
  646. PM_POP(2, DCPLB_DATA0)
  647. /* DCPLB Addr */
  648. FP = I1;
  649. PM_POP(1, DCPLB_ADDR15)
  650. PM_POP(0, DCPLB_ADDR14)
  651. PM_POP_SYNC(13)
  652. PM_POP(13, DCPLB_ADDR13)
  653. PM_POP(12, DCPLB_ADDR12)
  654. PM_POP(11, DCPLB_ADDR11)
  655. PM_POP(10, DCPLB_ADDR10)
  656. PM_POP(9, DCPLB_ADDR9)
  657. PM_POP(8, DCPLB_ADDR8)
  658. PM_POP(7, DCPLB_ADDR7)
  659. PM_POP(6, DCPLB_ADDR6)
  660. PM_POP(5, DCPLB_ADDR5)
  661. PM_POP(4, DCPLB_ADDR4)
  662. PM_POP(3, DCPLB_ADDR3)
  663. PM_POP(2, DCPLB_ADDR2)
  664. PM_POP(1, DCPLB_ADDR1)
  665. PM_POP(0, DCPLB_ADDR0)
  666. /* Restore System MMRs */
  667. FP.H = hi(SYSMMR_BASE);
  668. FP.L = lo(SYSMMR_BASE);
  669. #ifdef EBIU_FCTL
  670. PM_POP_SYNC(12)
  671. PM_SYS_POP(12, EBIU_FCTL)
  672. PM_SYS_POP(11, EBIU_MODE)
  673. PM_SYS_POP(10, EBIU_MBSCTL)
  674. #else
  675. PM_POP_SYNC(9)
  676. #endif
  677. PM_SYS_POP(9, EBIU_AMBCTL1)
  678. PM_SYS_POP(8, EBIU_AMBCTL0)
  679. PM_SYS_POP16(7, EBIU_AMGCTL)
  680. PM_SYS_POP16(6, SYSCR)
  681. #ifdef PINT0_ASSIGN
  682. PM_SYS_POP(5, PINT3_EDGE_SET)
  683. PM_SYS_POP(4, PINT2_EDGE_SET)
  684. PM_SYS_POP(3, PINT1_EDGE_SET)
  685. PM_SYS_POP(2, PINT0_EDGE_SET)
  686. PM_SYS_POP(1, PINT3_INVERT_SET)
  687. PM_SYS_POP(0, PINT2_INVERT_SET)
  688. PM_POP_SYNC(13)
  689. PM_SYS_POP(13, PINT1_INVERT_SET)
  690. PM_SYS_POP(12, PINT0_INVERT_SET)
  691. PM_SYS_POP(11, PINT3_ASSIGN)
  692. PM_SYS_POP(10, PINT2_ASSIGN)
  693. PM_SYS_POP(9, PINT1_ASSIGN)
  694. PM_SYS_POP(8, PINT0_ASSIGN)
  695. PM_SYS_POP(7, PINT3_MASK_SET)
  696. PM_SYS_POP(6, PINT2_MASK_SET)
  697. PM_SYS_POP(5, PINT1_MASK_SET)
  698. PM_SYS_POP(4, PINT0_MASK_SET)
  699. #endif
  700. #ifdef SIC_IWR2
  701. PM_SYS_POP(3, SIC_IWR2)
  702. #endif
  703. #ifdef SIC_IWR1
  704. PM_SYS_POP(2, SIC_IWR1)
  705. #endif
  706. #ifdef SIC_IWR0
  707. PM_SYS_POP(1, SIC_IWR0)
  708. #endif
  709. #ifdef SIC_IWR
  710. PM_SYS_POP(1, SIC_IWR)
  711. #endif
  712. #ifdef SIC_IAR11
  713. PM_SYS_POP(0, SIC_IAR11)
  714. #endif
  715. PM_POP_SYNC(13)
  716. #ifdef SIC_IAR8
  717. PM_SYS_POP(13, SIC_IAR10)
  718. PM_SYS_POP(12, SIC_IAR9)
  719. PM_SYS_POP(11, SIC_IAR8)
  720. #endif
  721. #ifdef SIC_IAR7
  722. PM_SYS_POP(10, SIC_IAR7)
  723. #endif
  724. #ifdef SIC_IAR6
  725. PM_SYS_POP(9, SIC_IAR6)
  726. PM_SYS_POP(8, SIC_IAR5)
  727. PM_SYS_POP(7, SIC_IAR4)
  728. #endif
  729. #ifdef SIC_IAR3
  730. PM_SYS_POP(6, SIC_IAR3)
  731. #endif
  732. #ifdef SIC_IAR0
  733. PM_SYS_POP(5, SIC_IAR2)
  734. PM_SYS_POP(4, SIC_IAR1)
  735. PM_SYS_POP(3, SIC_IAR0)
  736. #endif
  737. #ifdef SIC_IMASK0
  738. # ifdef SIC_IMASK2
  739. PM_SYS_POP(2, SIC_IMASK2)
  740. # endif
  741. PM_SYS_POP(1, SIC_IMASK1)
  742. PM_SYS_POP(0, SIC_IMASK0)
  743. #else
  744. PM_SYS_POP(0, SIC_IMASK)
  745. #endif
  746. /* Restore Core Registers */
  747. RETI = [sp++];
  748. SEQSTAT = [sp++];
  749. RETX = [sp++];
  750. SYSCFG = [sp++];
  751. CYCLES2 = [sp++];
  752. CYCLES = [sp++];
  753. ASTAT = [sp++];
  754. RETS = [sp++];
  755. LB1 = [sp++];
  756. LB0 = [sp++];
  757. LT1 = [sp++];
  758. LT0 = [sp++];
  759. LC1 = [sp++];
  760. LC0 = [sp++];
  761. a1.w = [sp++];
  762. a1.x = [sp++];
  763. a0.w = [sp++];
  764. a0.x = [sp++];
  765. b3 = [sp++];
  766. b2 = [sp++];
  767. b1 = [sp++];
  768. b0 = [sp++];
  769. l3 = [sp++];
  770. l2 = [sp++];
  771. l1 = [sp++];
  772. l0 = [sp++];
  773. m3 = [sp++];
  774. m2 = [sp++];
  775. m1 = [sp++];
  776. m0 = [sp++];
  777. i3 = [sp++];
  778. i2 = [sp++];
  779. i1 = [sp++];
  780. i0 = [sp++];
  781. usp = [sp++];
  782. fp = [sp++];
  783. (R7:0, P5:0) = [sp++];
  784. [--sp] = RETI; /* Clear Global Interrupt Disable */
  785. SP += 4;
  786. RTS;
  787. ENDPROC(_do_hibernate)