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