xref: /openbmc/linux/arch/sh/kernel/cpu/shmobile/sleep.S (revision 237674e0)
1e9edb3feSPaul Mundt/*
2e9edb3feSPaul Mundt * arch/sh/kernel/cpu/sh4a/sleep-sh_mobile.S
3e9edb3feSPaul Mundt *
4e9edb3feSPaul Mundt * Sleep mode and Standby modes support for SuperH Mobile
5e9edb3feSPaul Mundt *
6e9edb3feSPaul Mundt *  Copyright (C) 2009 Magnus Damm
7e9edb3feSPaul Mundt *
8e9edb3feSPaul Mundt * This file is subject to the terms and conditions of the GNU General Public
9e9edb3feSPaul Mundt * License.  See the file "COPYING" in the main directory of this archive
10e9edb3feSPaul Mundt * for more details.
11e9edb3feSPaul Mundt */
12e9edb3feSPaul Mundt
13e9edb3feSPaul Mundt#include <linux/sys.h>
14e9edb3feSPaul Mundt#include <linux/errno.h>
15e9edb3feSPaul Mundt#include <linux/linkage.h>
16e9edb3feSPaul Mundt#include <asm/asm-offsets.h>
17e9edb3feSPaul Mundt#include <asm/suspend.h>
18e9edb3feSPaul Mundt
19e9edb3feSPaul Mundt/* manage self-refresh and enter standby mode.
20e9edb3feSPaul Mundt * this code will be copied to on-chip memory and executed from there.
21e9edb3feSPaul Mundt */
22e9edb3feSPaul Mundt
23e9edb3feSPaul Mundt	.balign 	4096,0,4096
24e9edb3feSPaul MundtENTRY(sh_mobile_standby)
25e9edb3feSPaul Mundt	mov	r4, r0
26e9edb3feSPaul Mundt
27e9edb3feSPaul Mundt	tst	#SUSP_SH_SF, r0
28e9edb3feSPaul Mundt	bt	skip_set_sf
29237674e0SMagnus Damm#ifdef CONFIG_CPU_SUBTYPE_SH7724
30237674e0SMagnus Damm	/* DBSC: put memory in self-refresh mode */
31e9edb3feSPaul Mundt
32237674e0SMagnus Damm	mov.l	dben_reg, r4
33237674e0SMagnus Damm	mov.l	dben_data0, r1
34237674e0SMagnus Damm	mov.l	r1, @r4
35237674e0SMagnus Damm
36237674e0SMagnus Damm	mov.l	dbrfpdn0_reg, r4
37237674e0SMagnus Damm	mov.l	dbrfpdn0_data0, r1
38237674e0SMagnus Damm	mov.l	r1, @r4
39237674e0SMagnus Damm
40237674e0SMagnus Damm	mov.l	dbcmdcnt_reg, r4
41237674e0SMagnus Damm	mov.l	dbcmdcnt_data0, r1
42237674e0SMagnus Damm	mov.l	r1, @r4
43237674e0SMagnus Damm
44237674e0SMagnus Damm	mov.l	dbcmdcnt_reg, r4
45237674e0SMagnus Damm	mov.l	dbcmdcnt_data1, r1
46237674e0SMagnus Damm	mov.l	r1, @r4
47237674e0SMagnus Damm
48237674e0SMagnus Damm	mov.l	dbrfpdn0_reg, r4
49237674e0SMagnus Damm	mov.l	dbrfpdn0_data1, r1
50237674e0SMagnus Damm	mov.l	r1, @r4
51237674e0SMagnus Damm#else
52237674e0SMagnus Damm	/* SBSC: disable power down and put in self-refresh mode */
53e9edb3feSPaul Mundt	mov.l	1f, r4
54e9edb3feSPaul Mundt	mov.l	2f, r1
55e9edb3feSPaul Mundt	mov.l	@r4, r2
56e9edb3feSPaul Mundt	or	r1, r2
57e9edb3feSPaul Mundt	mov.l   3f, r3
58e9edb3feSPaul Mundt	and	r3, r2
59e9edb3feSPaul Mundt	mov.l	r2, @r4
60237674e0SMagnus Damm#endif
61e9edb3feSPaul Mundt
62e9edb3feSPaul Mundtskip_set_sf:
63e9edb3feSPaul Mundt	tst	#SUSP_SH_SLEEP, r0
64e9edb3feSPaul Mundt	bt	test_standby
65e9edb3feSPaul Mundt
66e9edb3feSPaul Mundt	/* set mode to "sleep mode" */
67e9edb3feSPaul Mundt	bra	do_sleep
68e9edb3feSPaul Mundt	 mov	#0x00, r1
69e9edb3feSPaul Mundt
70e9edb3feSPaul Mundttest_standby:
71e9edb3feSPaul Mundt	tst	#SUSP_SH_STANDBY, r0
72e9edb3feSPaul Mundt	bt	test_rstandby
73e9edb3feSPaul Mundt
74e9edb3feSPaul Mundt	/* set mode to "software standby mode" */
75e9edb3feSPaul Mundt	bra	do_sleep
76e9edb3feSPaul Mundt	 mov	#0x80, r1
77e9edb3feSPaul Mundt
78e9edb3feSPaul Mundttest_rstandby:
79e9edb3feSPaul Mundt	tst	#SUSP_SH_RSTANDBY, r0
80e9edb3feSPaul Mundt	bt	test_ustandby
81e9edb3feSPaul Mundt
82e9edb3feSPaul Mundt	/* set mode to "r-standby mode" */
83e9edb3feSPaul Mundt	bra	do_sleep
84e9edb3feSPaul Mundt	 mov	#0x20, r1
85e9edb3feSPaul Mundt
86e9edb3feSPaul Mundttest_ustandby:
87e9edb3feSPaul Mundt	tst	#SUSP_SH_USTANDBY, r0
88e9edb3feSPaul Mundt	bt	done_sleep
89e9edb3feSPaul Mundt
90e9edb3feSPaul Mundt	/* set mode to "u-standby mode" */
91e9edb3feSPaul Mundt	mov	#0x10, r1
92e9edb3feSPaul Mundt
93e9edb3feSPaul Mundt	/* fall-through */
94e9edb3feSPaul Mundt
95e9edb3feSPaul Mundtdo_sleep:
96e9edb3feSPaul Mundt	/* setup and enter selected standby mode */
97e9edb3feSPaul Mundt	mov.l	5f, r4
98e9edb3feSPaul Mundt	mov.l	r1, @r4
99e9edb3feSPaul Mundt	sleep
100e9edb3feSPaul Mundt
101e9edb3feSPaul Mundtdone_sleep:
102e9edb3feSPaul Mundt	/* reset standby mode to sleep mode */
103e9edb3feSPaul Mundt	mov.l	5f, r4
104e9edb3feSPaul Mundt	mov	#0x00, r1
105e9edb3feSPaul Mundt	mov.l	r1, @r4
106e9edb3feSPaul Mundt
107e9edb3feSPaul Mundt	tst	#SUSP_SH_SF, r0
108e9edb3feSPaul Mundt	bt	skip_restore_sf
109e9edb3feSPaul Mundt
110237674e0SMagnus Damm#ifdef CONFIG_CPU_SUBTYPE_SH7724
111237674e0SMagnus Damm	/* DBSC: put memory in auto-refresh mode */
112237674e0SMagnus Damm
113237674e0SMagnus Damm	mov.l	dbrfpdn0_reg, r4
114237674e0SMagnus Damm	mov.l	dbrfpdn0_data0, r1
115237674e0SMagnus Damm	mov.l	r1, @r4
116237674e0SMagnus Damm
117237674e0SMagnus Damm	/* sleep 140 ns */
118237674e0SMagnus Damm	nop
119237674e0SMagnus Damm	nop
120237674e0SMagnus Damm	nop
121237674e0SMagnus Damm	nop
122237674e0SMagnus Damm
123237674e0SMagnus Damm	mov.l	dbcmdcnt_reg, r4
124237674e0SMagnus Damm	mov.l	dbcmdcnt_data0, r1
125237674e0SMagnus Damm	mov.l	r1, @r4
126237674e0SMagnus Damm
127237674e0SMagnus Damm	mov.l	dbcmdcnt_reg, r4
128237674e0SMagnus Damm	mov.l	dbcmdcnt_data1, r1
129237674e0SMagnus Damm	mov.l	r1, @r4
130237674e0SMagnus Damm
131237674e0SMagnus Damm	mov.l	dben_reg, r4
132237674e0SMagnus Damm	mov.l	dben_data1, r1
133237674e0SMagnus Damm	mov.l	r1, @r4
134237674e0SMagnus Damm
135237674e0SMagnus Damm	mov.l	dbrfpdn0_reg, r4
136237674e0SMagnus Damm	mov.l	dbrfpdn0_data2, r1
137237674e0SMagnus Damm	mov.l	r1, @r4
138237674e0SMagnus Damm#else
139237674e0SMagnus Damm	/* SBSC: set auto-refresh mode */
140e9edb3feSPaul Mundt	mov.l	1f, r4
141e9edb3feSPaul Mundt	mov.l	@r4, r2
142e9edb3feSPaul Mundt	mov.l   4f, r3
143e9edb3feSPaul Mundt	and	r3, r2
144e9edb3feSPaul Mundt	mov.l	r2, @r4
145e9edb3feSPaul Mundt	mov.l	6f, r4
146e9edb3feSPaul Mundt	mov.l	7f, r1
147e9edb3feSPaul Mundt	mov.l	8f, r2
148e9edb3feSPaul Mundt	mov.l	@r4, r3
149e9edb3feSPaul Mundt	mov	#-1, r4
150e9edb3feSPaul Mundt	add	r4, r3
151e9edb3feSPaul Mundt	or	r2, r3
152e9edb3feSPaul Mundt	mov.l	r3, @r1
153237674e0SMagnus Damm#endif
154e9edb3feSPaul Mundtskip_restore_sf:
155e9edb3feSPaul Mundt	rts
156e9edb3feSPaul Mundt	 nop
157e9edb3feSPaul Mundt
158e9edb3feSPaul Mundt	.balign 4
159237674e0SMagnus Damm#ifdef CONFIG_CPU_SUBTYPE_SH7724
160237674e0SMagnus Dammdben_reg:	.long	0xfd000010 /* DBEN */
161237674e0SMagnus Dammdben_data0:	.long	0
162237674e0SMagnus Dammdben_data1:	.long	1
163237674e0SMagnus Dammdbrfpdn0_reg:	.long	0xfd000040 /* DBRFPDN0 */
164237674e0SMagnus Dammdbrfpdn0_data0:	.long	0
165237674e0SMagnus Dammdbrfpdn0_data1:	.long	1
166237674e0SMagnus Dammdbrfpdn0_data2:	.long	0x00010000
167237674e0SMagnus Dammdbcmdcnt_reg:	.long	0xfd000014 /* DBCMDCNT */
168237674e0SMagnus Dammdbcmdcnt_data0:	.long	2
169237674e0SMagnus Dammdbcmdcnt_data1:	.long	4
170237674e0SMagnus Damm#else
171e9edb3feSPaul Mundt1:	.long	0xfe400008 /* SDCR0 */
172e9edb3feSPaul Mundt2:	.long	0x00000400
173e9edb3feSPaul Mundt3:	.long	0xffff7fff
174e9edb3feSPaul Mundt4:	.long	0xfffffbff
175237674e0SMagnus Damm#endif
176e9edb3feSPaul Mundt5:	.long	0xa4150020 /* STBCR */
177e9edb3feSPaul Mundt6:	.long   0xfe40001c /* RTCOR */
178e9edb3feSPaul Mundt7:	.long   0xfe400018 /* RTCNT */
179e9edb3feSPaul Mundt8:	.long   0xa55a0000
180e9edb3feSPaul Mundt
181e9edb3feSPaul Mundt/* interrupt vector @ 0x600 */
182e9edb3feSPaul Mundt	.balign 	0x400,0,0x400
183e9edb3feSPaul Mundt	.long	0xdeadbeef
184e9edb3feSPaul Mundt	.balign 	0x200,0,0x200
185e9edb3feSPaul Mundt	/* sh7722 will end up here in sleep mode */
186e9edb3feSPaul Mundt	rte
187e9edb3feSPaul Mundt	 nop
188e9edb3feSPaul Mundtsh_mobile_standby_end:
189e9edb3feSPaul Mundt
190e9edb3feSPaul MundtENTRY(sh_mobile_standby_size)
191e9edb3feSPaul Mundt	.long sh_mobile_standby_end - sh_mobile_standby
192