1 /* SPDX-License-Identifier: GPL-2.0 */
2 #include <asm/reg.h>
3 #include <asm/ppc_asm.h>
4 #include <asm/processor.h>
5 
6 
7 .text
8 
9 _GLOBAL(mpc52xx_deep_sleep)
10 mpc52xx_deep_sleep: /* args r3-r6: SRAM, SDRAM regs, CDM regs, INTR regs */
11 
12 	/* enable interrupts */
13 	mfmsr	r7
14 	ori	r7, r7, 0x8000 /* EE */
15 	mtmsr	r7
16 	sync; isync;
17 
18 	li	r10, 0 /* flag that irq handler sets */
19 
20 	/* enable tmr7 (or any other) interrupt */
21 	lwz	r8, 0x14(r6) /* intr->main_mask */
22 	ori	r8, r8, 0x1
23 	xori	r8, r8, 0x1
24 	stw	r8, 0x14(r6)
25 	sync
26 
27 	/* emulate tmr7 interrupt */
28 	li	r8, 0x1
29 	stw	r8, 0x40(r6) /* intr->main_emulate */
30 	sync
31 
32 	/* wait for it to happen */
33 1:
34 	cmpi	cr0, r10, 1
35 	bne	cr0, 1b
36 
37 	/* lock icache */
38 	mfspr	r10, SPRN_HID0
39 	ori	r10, r10, 0x2000
40 	sync; isync;
41 	mtspr	SPRN_HID0, r10
42 	sync; isync;
43 
44 
45 	mflr	r9 /* save LR */
46 
47 	/* jump to sram */
48 	mtlr	r3
49 	blrl
50 
51 	mtlr	r9 /* restore LR */
52 
53 	/* unlock icache */
54 	mfspr	r10, SPRN_HID0
55 	ori	r10, r10, 0x2000
56 	xori	r10, r10, 0x2000
57 	sync; isync;
58 	mtspr	SPRN_HID0, r10
59 	sync; isync;
60 
61 
62 	/* return to C code */
63 	blr
64 
65 
66 _GLOBAL(mpc52xx_ds_sram)
67 mpc52xx_ds_sram:
68 	/* put SDRAM into self-refresh */
69 	lwz	r8, 0x4(r4)	/* sdram->ctrl */
70 
71 	oris	r8, r8, 0x8000 /* mode_en */
72 	stw	r8, 0x4(r4)
73 	sync
74 
75 	ori	r8, r8, 0x0002 /* soft_pre */
76 	stw	r8, 0x4(r4)
77 	sync
78 	xori	r8, r8, 0x0002
79 
80 	xoris	r8, r8, 0x8000 /* !mode_en */
81 	stw	r8, 0x4(r4)
82 	sync
83 
84 	oris	r8, r8, 0x5000
85 	xoris	r8, r8, 0x4000 /* ref_en !cke */
86 	stw	r8, 0x4(r4)
87 	sync
88 
89 	/* disable SDRAM clock */
90 	lwz	r8, 0x14(r5) /* cdm->clkenable */
91 	ori	r8, r8, 0x0008
92 	xori	r8, r8, 0x0008
93 	stw	r8, 0x14(r5)
94 	sync
95 
96 
97 	/* put mpc5200 to sleep */
98 	mfmsr	r10
99 	oris	r10, r10, 0x0004	/* POW = 1 */
100 	sync; isync;
101 	mtmsr	r10
102 	sync; isync;
103 
104 
105 	/* enable clock */
106 	lwz	r8, 0x14(r5)
107 	ori	r8, r8, 0x0008
108 	stw	r8, 0x14(r5)
109 	sync
110 
111 	/* get ram out of self-refresh */
112 	lwz	r8, 0x4(r4)
113 	oris	r8, r8, 0x5000 /* cke ref_en */
114 	stw	r8, 0x4(r4)
115 	sync
116 
117 	blr
118 _GLOBAL(mpc52xx_ds_sram_size)
119 mpc52xx_ds_sram_size:
120 	.long $-mpc52xx_ds_sram
121 
122 
123 /* ### interrupt handler for wakeup from deep-sleep ### */
124 _GLOBAL(mpc52xx_ds_cached)
125 mpc52xx_ds_cached:
126 	mtspr	SPRN_SPRG0, r7
127 	mtspr	SPRN_SPRG1, r8
128 
129 	/* disable emulated interrupt */
130 	mfspr	r7, 311 /* MBAR */
131 	addi	r7, r7, 0x540	/* intr->main_emul */
132 	li	r8, 0
133 	stw	r8, 0(r7)
134 	sync
135 	dcbf	0, r7
136 
137 	/* acknowledge wakeup, so CCS releases power pown */
138 	mfspr	r7, 311	/* MBAR */
139 	addi	r7, r7, 0x524	/* intr->enc_status */
140 	lwz	r8, 0(r7)
141 	ori	r8, r8, 0x0400
142 	stw	r8, 0(r7)
143 	sync
144 	dcbf	0, r7
145 
146 	/* flag - we handled the interrupt */
147 	li	r10, 1
148 
149 	mfspr	r8, SPRN_SPRG1
150 	mfspr	r7, SPRN_SPRG0
151 
152 	rfi
153 _GLOBAL(mpc52xx_ds_cached_size)
154 mpc52xx_ds_cached_size:
155 	.long $-mpc52xx_ds_cached
156