pxa2x0_apm.c revision 1.1.6.2 1 1.1.6.2 mjf /* $NetBSD: pxa2x0_apm.c,v 1.1.6.2 2009/01/17 13:27:54 mjf Exp $ */
2 1.1.6.2 mjf /* $OpenBSD: pxa2x0_apm.c,v 1.28 2007/03/29 18:42:38 uwe Exp $ */
3 1.1.6.2 mjf
4 1.1.6.2 mjf /*-
5 1.1.6.2 mjf * Copyright (c) 2001 Alexander Guy. All rights reserved.
6 1.1.6.2 mjf * Copyright (c) 1998-2001 Michael Shalayeff. All rights reserved.
7 1.1.6.2 mjf * Copyright (c) 1995 John T. Kohl. All rights reserved.
8 1.1.6.2 mjf *
9 1.1.6.2 mjf * Redistribution and use in source and binary forms, with or without
10 1.1.6.2 mjf * modification, are permitted provided that the following conditions
11 1.1.6.2 mjf * are met:
12 1.1.6.2 mjf * 1. Redistributions of source code must retain the above copyright
13 1.1.6.2 mjf * notice, this list of conditions and the following disclaimer.
14 1.1.6.2 mjf * 2. Redistributions in binary form must reproduce the above copyright
15 1.1.6.2 mjf * notice, this list of conditions and the following disclaimer in the
16 1.1.6.2 mjf * documentation and/or other materials provided with the distribution.
17 1.1.6.2 mjf * 3. All advertising materials mentioning features or use of this software
18 1.1.6.2 mjf * must display the following acknowledgement:
19 1.1.6.2 mjf * This product includes software developed by the University of
20 1.1.6.2 mjf * California, Berkeley and its contributors.
21 1.1.6.2 mjf * 4. Neither the name of the University nor the names of its contributors
22 1.1.6.2 mjf * may be used to endorse or promote products derived from this software
23 1.1.6.2 mjf * without specific prior written permission.
24 1.1.6.2 mjf *
25 1.1.6.2 mjf * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
26 1.1.6.2 mjf * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27 1.1.6.2 mjf * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28 1.1.6.2 mjf * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
29 1.1.6.2 mjf * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30 1.1.6.2 mjf * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31 1.1.6.2 mjf * OR SERVICES; LOSS OF MIND, USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32 1.1.6.2 mjf * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33 1.1.6.2 mjf * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34 1.1.6.2 mjf * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35 1.1.6.2 mjf * SUCH DAMAGE.
36 1.1.6.2 mjf *
37 1.1.6.2 mjf */
38 1.1.6.2 mjf
39 1.1.6.2 mjf #include <sys/param.h>
40 1.1.6.2 mjf #include <sys/systm.h>
41 1.1.6.2 mjf #include <sys/kernel.h>
42 1.1.6.2 mjf #include <sys/kthread.h>
43 1.1.6.2 mjf #include <sys/lock.h>
44 1.1.6.2 mjf #include <sys/mount.h> /* for vfs_syncwait() */
45 1.1.6.2 mjf #include <sys/proc.h>
46 1.1.6.2 mjf #include <sys/device.h>
47 1.1.6.2 mjf #include <sys/fcntl.h>
48 1.1.6.2 mjf #include <sys/ioctl.h>
49 1.1.6.2 mjf #include <sys/event.h>
50 1.1.6.2 mjf
51 1.1.6.2 mjf #include <machine/cpu.h>
52 1.1.6.2 mjf #include <machine/apmvar.h>
53 1.1.6.2 mjf
54 1.1.6.2 mjf #include <arm/xscale/pxa2x0reg.h>
55 1.1.6.2 mjf #include <arm/xscale/pxa2x0var.h>
56 1.1.6.2 mjf #include <arm/xscale/pxa2x0_apm.h>
57 1.1.6.2 mjf #include <arm/xscale/pxa2x0_gpio.h>
58 1.1.6.2 mjf
59 1.1.6.2 mjf #if defined(APMDEBUG)
60 1.1.6.2 mjf #define DPRINTF(x) printf x
61 1.1.6.2 mjf #else
62 1.1.6.2 mjf #define DPRINTF(x) /**/
63 1.1.6.2 mjf #endif
64 1.1.6.2 mjf
65 1.1.6.2 mjf #define APM_LOCK(sc) lockmgr(&(sc)->sc_lock, LK_EXCLUSIVE, NULL)
66 1.1.6.2 mjf #define APM_UNLOCK(sc) lockmgr(&(sc)->sc_lock, LK_RELEASE, NULL)
67 1.1.6.2 mjf
68 1.1.6.2 mjf #define APMUNIT(dev) (minor(dev)&0xf0)
69 1.1.6.2 mjf #define APMDEV(dev) (minor(dev)&0x0f)
70 1.1.6.2 mjf #define APMDEV_NORMAL 0
71 1.1.6.2 mjf #define APMDEV_CTL 8
72 1.1.6.2 mjf
73 1.1.6.2 mjf int apm_userstandbys;
74 1.1.6.2 mjf int apm_suspends;
75 1.1.6.2 mjf int apm_battlow;
76 1.1.6.2 mjf
77 1.1.6.2 mjf extern struct cfdriver zapm_cd;
78 1.1.6.2 mjf
79 1.1.6.2 mjf /* battery percentage at which we get verbose in our warnings. This
80 1.1.6.2 mjf value can be changed using sysctl(8), value machdep.apmwarn.
81 1.1.6.2 mjf Setting it to zero kills all warnings */
82 1.1.6.2 mjf int cpu_apmwarn = 10;
83 1.1.6.2 mjf
84 1.1.6.2 mjf void apm_power_print(struct pxa2x0_apm_softc *, struct apm_power_info *);
85 1.1.6.2 mjf void apm_power_info(struct pxa2x0_apm_softc *, struct apm_power_info *);
86 1.1.6.2 mjf void apm_suspend(struct pxa2x0_apm_softc *);
87 1.1.6.2 mjf void apm_resume(struct pxa2x0_apm_softc *);
88 1.1.6.2 mjf int apm_get_event(struct pxa2x0_apm_softc *, u_int *);
89 1.1.6.2 mjf int apm_handle_event(struct pxa2x0_apm_softc *, u_int);
90 1.1.6.2 mjf void apm_thread_create(void *);
91 1.1.6.2 mjf void apm_thread(void *);
92 1.1.6.2 mjf
93 1.1.6.2 mjf #if 0
94 1.1.6.2 mjf extern int perflevel;
95 1.1.6.2 mjf #endif
96 1.1.6.2 mjf
97 1.1.6.2 mjf int freq;
98 1.1.6.2 mjf void pxa2x0_setperf(int speed);
99 1.1.6.2 mjf int pxa2x0_cpuspeed(int *speed);
100 1.1.6.2 mjf
101 1.1.6.2 mjf int apm_record_event(struct pxa2x0_apm_softc *, u_int);
102 1.1.6.2 mjf #if 0
103 1.1.6.2 mjf void filt_apmrdetach(struct knote *kn);
104 1.1.6.2 mjf int filt_apmread(struct knote *kn, long hint);
105 1.1.6.2 mjf int apmkqfilter(dev_t dev, struct knote *kn);
106 1.1.6.2 mjf
107 1.1.6.2 mjf struct filterops apmread_filtops =
108 1.1.6.2 mjf { 1, NULL, filt_apmrdetach, filt_apmread};
109 1.1.6.2 mjf #endif
110 1.1.6.2 mjf
111 1.1.6.2 mjf /*
112 1.1.6.2 mjf * Flags to control kernel display
113 1.1.6.2 mjf * SCFLAG_NOPRINT: do not output APM power messages due to
114 1.1.6.2 mjf * a power change event.
115 1.1.6.2 mjf *
116 1.1.6.2 mjf * SCFLAG_PCTPRINT: do not output APM power messages due to
117 1.1.6.2 mjf * to a power change event unless the battery
118 1.1.6.2 mjf * percentage changes.
119 1.1.6.2 mjf */
120 1.1.6.2 mjf
121 1.1.6.2 mjf #define SCFLAG_NOPRINT 0x0008000
122 1.1.6.2 mjf #define SCFLAG_PCTPRINT 0x0004000
123 1.1.6.2 mjf #define SCFLAG_PRINT (SCFLAG_NOPRINT|SCFLAG_PCTPRINT)
124 1.1.6.2 mjf
125 1.1.6.2 mjf #define SCFLAG_OREAD (1 << 0)
126 1.1.6.2 mjf #define SCFLAG_OWRITE (1 << 1)
127 1.1.6.2 mjf #define SCFLAG_OPEN (SCFLAG_OREAD|SCFLAG_OWRITE)
128 1.1.6.2 mjf
129 1.1.6.2 mjf /* This structure must be kept in sync with pxa2x0_apm_asm.S. */
130 1.1.6.2 mjf struct pxa2x0_memcfg {
131 1.1.6.2 mjf /* SDRAM refresh */
132 1.1.6.2 mjf u_int32_t mdrefr_high; /* 0x00 */
133 1.1.6.2 mjf u_int32_t mdrefr_low; /* 0x04 */
134 1.1.6.2 mjf u_int32_t mdrefr_low2; /* 0x08 */
135 1.1.6.2 mjf /* Synchronous, static, or VLIO interfaces */
136 1.1.6.2 mjf u_int32_t msc_high[3]; /* 0x0c */
137 1.1.6.2 mjf u_int32_t msc_low[3]; /* 0x18 */
138 1.1.6.2 mjf /* XXX move up */
139 1.1.6.2 mjf u_int32_t mdrefr_91; /* 0x24 */
140 1.1.6.2 mjf };
141 1.1.6.2 mjf
142 1.1.6.2 mjf /* XXX */
143 1.1.6.2 mjf #define MDREFR_C3000 (MDREFR_K0DB2 | MDREFR_E1PIN | MDREFR_K1RUN | \
144 1.1.6.2 mjf MDREFR_K1DB2 | MDREFR_K2DB2 | MDREFR_APD)
145 1.1.6.2 mjf #define MSC0_HIGH \
146 1.1.6.2 mjf ( 7 << MSC_RRR_SHIFT << 16) | \
147 1.1.6.2 mjf (15 << MSC_RDN_SHIFT << 16) | \
148 1.1.6.2 mjf (15 << MSC_RDF_SHIFT << 16) | \
149 1.1.6.2 mjf (MSC_RT_NONBURST << 16) | \
150 1.1.6.2 mjf ( 2 << MSC_RRR_SHIFT) | \
151 1.1.6.2 mjf (13 << MSC_RDN_SHIFT) | \
152 1.1.6.2 mjf (13 << MSC_RDF_SHIFT) | \
153 1.1.6.2 mjf MSC_RBW /* PXA271 */ | \
154 1.1.6.2 mjf MSC_RT_NONBURST
155 1.1.6.2 mjf #define MSC1_HIGH \
156 1.1.6.2 mjf ( 7 << MSC_RRR_SHIFT << 16) | \
157 1.1.6.2 mjf (15 << MSC_RDN_SHIFT << 16) | \
158 1.1.6.2 mjf (15 << MSC_RDF_SHIFT << 16) | \
159 1.1.6.2 mjf (MSC_RT_VLIO << 16) | \
160 1.1.6.2 mjf ( 3 << MSC_RRR_SHIFT) | \
161 1.1.6.2 mjf ( 4 << MSC_RDN_SHIFT) | \
162 1.1.6.2 mjf (13 << MSC_RDF_SHIFT) | \
163 1.1.6.2 mjf MSC_RT_VLIO
164 1.1.6.2 mjf #define MSC2_HIGH \
165 1.1.6.2 mjf ( 7 << MSC_RRR_SHIFT << 16) | \
166 1.1.6.2 mjf (15 << MSC_RDN_SHIFT << 16) | \
167 1.1.6.2 mjf (15 << MSC_RDF_SHIFT << 16) | \
168 1.1.6.2 mjf (MSC_RT_NONBURST << 16) | \
169 1.1.6.2 mjf ( 3 << MSC_RRR_SHIFT) | \
170 1.1.6.2 mjf ( 4 << MSC_RDN_SHIFT) | \
171 1.1.6.2 mjf (13 << MSC_RDF_SHIFT) | \
172 1.1.6.2 mjf MSC_RT_VLIO
173 1.1.6.2 mjf #define MSC0_LOW \
174 1.1.6.2 mjf ( 7 << MSC_RRR_SHIFT << 16) | \
175 1.1.6.2 mjf (15 << MSC_RDN_SHIFT << 16) | \
176 1.1.6.2 mjf (15 << MSC_RDF_SHIFT << 16) | \
177 1.1.6.2 mjf (MSC_RT_NONBURST << 16) | \
178 1.1.6.2 mjf ( 1 << MSC_RRR_SHIFT) | \
179 1.1.6.2 mjf ( 8 << MSC_RDN_SHIFT) | \
180 1.1.6.2 mjf ( 8 << MSC_RDF_SHIFT) | \
181 1.1.6.2 mjf MSC_RBW /* PXA271 */ | \
182 1.1.6.2 mjf MSC_RT_NONBURST
183 1.1.6.2 mjf #define MSC1_LOW \
184 1.1.6.2 mjf ( 7 << MSC_RRR_SHIFT << 16) | \
185 1.1.6.2 mjf (15 << MSC_RDN_SHIFT << 16) | \
186 1.1.6.2 mjf (15 << MSC_RDF_SHIFT << 16) | \
187 1.1.6.2 mjf (MSC_RT_VLIO << 16) | \
188 1.1.6.2 mjf ( 1 << MSC_RRR_SHIFT) | \
189 1.1.6.2 mjf ( 2 << MSC_RDN_SHIFT) | \
190 1.1.6.2 mjf ( 6 << MSC_RDF_SHIFT) | \
191 1.1.6.2 mjf MSC_RT_VLIO
192 1.1.6.2 mjf #define MSC2_LOW \
193 1.1.6.2 mjf ( 7 << MSC_RRR_SHIFT << 16) | \
194 1.1.6.2 mjf (15 << MSC_RDN_SHIFT << 16) | \
195 1.1.6.2 mjf (15 << MSC_RDF_SHIFT << 16) | \
196 1.1.6.2 mjf (MSC_RT_NONBURST << 16) | \
197 1.1.6.2 mjf ( 1 << MSC_RRR_SHIFT) | \
198 1.1.6.2 mjf ( 2 << MSC_RDN_SHIFT) | \
199 1.1.6.2 mjf ( 6 << MSC_RDF_SHIFT) | \
200 1.1.6.2 mjf MSC_RT_VLIO
201 1.1.6.2 mjf struct pxa2x0_memcfg pxa2x0_memcfg = {
202 1.1.6.2 mjf (MDREFR_C3000 | 0x030),
203 1.1.6.2 mjf (MDREFR_C3000 | 0x00b),
204 1.1.6.2 mjf (MDREFR_C3000 | 0x017),
205 1.1.6.2 mjf { MSC0_HIGH, MSC1_HIGH, MSC2_HIGH },
206 1.1.6.2 mjf { MSC1_LOW, MSC1_LOW, MSC2_LOW },
207 1.1.6.2 mjf (MDREFR_C3000 | 0x013)
208 1.1.6.2 mjf };
209 1.1.6.2 mjf
210 1.1.6.2 mjf #define PI2C_RETRY_COUNT 10
211 1.1.6.2 mjf /* XXX varies depending on voltage regulator IC. */
212 1.1.6.2 mjf #define PI2C_VOLTAGE_LOW 0x13 /* 1.00V */
213 1.1.6.2 mjf #define PI2C_VOLTAGE_HIGH 0x1a /* 1.35V */
214 1.1.6.2 mjf
215 1.1.6.2 mjf void pxa2x0_pi2c_open(bus_space_tag_t, bus_space_handle_t);
216 1.1.6.2 mjf void pxa2x0_pi2c_close(bus_space_tag_t, bus_space_handle_t);
217 1.1.6.2 mjf int pxa2x0_pi2c_read(bus_space_tag_t, bus_space_handle_t, u_char, u_char *);
218 1.1.6.2 mjf int pxa2x0_pi2c_write(bus_space_tag_t, bus_space_handle_t, u_char, u_char);
219 1.1.6.2 mjf int pxa2x0_pi2c_getvoltage(bus_space_tag_t, bus_space_handle_t, u_char *);
220 1.1.6.2 mjf int pxa2x0_pi2c_setvoltage(bus_space_tag_t, bus_space_handle_t, u_char);
221 1.1.6.2 mjf #if 0
222 1.1.6.2 mjf void pxa2x0_pi2c_print(struct pxa2x0_apm_softc *);
223 1.1.6.2 mjf #endif
224 1.1.6.2 mjf
225 1.1.6.2 mjf /* XXX used in pxa2x0_apm_asm.S */
226 1.1.6.2 mjf bus_space_handle_t pxa2x0_gpio_ioh;
227 1.1.6.2 mjf bus_space_handle_t pxa2x0_clkman_ioh;
228 1.1.6.2 mjf bus_space_handle_t pxa2x0_memctl_ioh;
229 1.1.6.2 mjf
230 1.1.6.2 mjf /* pxa2x0_apm_asm.S */
231 1.1.6.2 mjf void pxa27x_run_mode(void);
232 1.1.6.2 mjf void pxa27x_fastbus_run_mode(int, u_int32_t);
233 1.1.6.2 mjf void pxa27x_frequency_change(int, int, struct pxa2x0_memcfg *);
234 1.1.6.2 mjf void pxa2x0_cpu_suspend(void);
235 1.1.6.2 mjf void pxa2x0_cpu_resume(void);
236 1.1.6.2 mjf void pxa27x_cpu_speed_high(void);
237 1.1.6.2 mjf void pxa27x_cpu_speed_low(void);
238 1.1.6.2 mjf void pxa27x_cpu_speed_91(void);
239 1.1.6.2 mjf void pxa27x_cpu_speed_208(void);
240 1.1.6.2 mjf
241 1.1.6.2 mjf void
242 1.1.6.2 mjf apm_power_print(struct pxa2x0_apm_softc *sc, struct apm_power_info *powerp)
243 1.1.6.2 mjf {
244 1.1.6.2 mjf
245 1.1.6.2 mjf if (powerp->battery_life != APM_BATT_LIFE_UNKNOWN)
246 1.1.6.2 mjf printf("%s: battery life expectancy %d%%\n",
247 1.1.6.2 mjf sc->sc_dev.dv_xname, powerp->battery_life);
248 1.1.6.2 mjf
249 1.1.6.2 mjf printf("%s: AC ", sc->sc_dev.dv_xname);
250 1.1.6.2 mjf switch (powerp->ac_state) {
251 1.1.6.2 mjf case APM_AC_OFF:
252 1.1.6.2 mjf printf("off,");
253 1.1.6.2 mjf break;
254 1.1.6.2 mjf case APM_AC_ON:
255 1.1.6.2 mjf printf("on,");
256 1.1.6.2 mjf break;
257 1.1.6.2 mjf case APM_AC_BACKUP:
258 1.1.6.2 mjf printf("backup power,");
259 1.1.6.2 mjf break;
260 1.1.6.2 mjf default:
261 1.1.6.2 mjf case APM_AC_UNKNOWN:
262 1.1.6.2 mjf printf("unknown,");
263 1.1.6.2 mjf break;
264 1.1.6.2 mjf }
265 1.1.6.2 mjf
266 1.1.6.2 mjf printf(" battery is ");
267 1.1.6.2 mjf switch (powerp->battery_state) {
268 1.1.6.2 mjf case APM_BATT_HIGH:
269 1.1.6.2 mjf printf("high");
270 1.1.6.2 mjf break;
271 1.1.6.2 mjf case APM_BATT_LOW:
272 1.1.6.2 mjf printf("low");
273 1.1.6.2 mjf break;
274 1.1.6.2 mjf case APM_BATT_CRITICAL:
275 1.1.6.2 mjf printf("CRITICAL");
276 1.1.6.2 mjf break;
277 1.1.6.2 mjf case APM_BATT_CHARGING:
278 1.1.6.2 mjf printf("charging");
279 1.1.6.2 mjf break;
280 1.1.6.2 mjf case APM_BATT_UNKNOWN:
281 1.1.6.2 mjf printf("unknown");
282 1.1.6.2 mjf break;
283 1.1.6.2 mjf default:
284 1.1.6.2 mjf printf("undecoded (%x)", powerp->battery_state);
285 1.1.6.2 mjf break;
286 1.1.6.2 mjf }
287 1.1.6.2 mjf
288 1.1.6.2 mjf printf("\n");
289 1.1.6.2 mjf }
290 1.1.6.2 mjf
291 1.1.6.2 mjf void
292 1.1.6.2 mjf apm_power_info(struct pxa2x0_apm_softc *sc,
293 1.1.6.2 mjf struct apm_power_info *power)
294 1.1.6.2 mjf {
295 1.1.6.2 mjf
296 1.1.6.2 mjf power->ac_state = APM_AC_UNKNOWN;
297 1.1.6.2 mjf power->battery_state = APM_BATT_UNKNOWN;
298 1.1.6.2 mjf power->battery_life = 0 /* APM_BATT_LIFE_UNKNOWN */;
299 1.1.6.2 mjf power->minutes_left = 0;
300 1.1.6.2 mjf
301 1.1.6.2 mjf if (sc->sc_power_info != NULL)
302 1.1.6.2 mjf sc->sc_power_info(sc, power);
303 1.1.6.2 mjf }
304 1.1.6.2 mjf
305 1.1.6.2 mjf void
306 1.1.6.2 mjf apm_suspend(struct pxa2x0_apm_softc *sc)
307 1.1.6.2 mjf {
308 1.1.6.2 mjf
309 1.1.6.2 mjf resettodr();
310 1.1.6.2 mjf
311 1.1.6.2 mjf dopowerhooks(PWR_SUSPEND);
312 1.1.6.2 mjf
313 1.1.6.2 mjf #if 0
314 1.1.6.2 mjf if (cold)
315 1.1.6.2 mjf vfs_syncwait(0);
316 1.1.6.2 mjf #endif
317 1.1.6.2 mjf
318 1.1.6.2 mjf if (sc->sc_suspend == NULL)
319 1.1.6.2 mjf pxa2x0_wakeup_config(PXA2X0_WAKEUP_ALL, 1);
320 1.1.6.2 mjf else
321 1.1.6.2 mjf sc->sc_suspend(sc);
322 1.1.6.2 mjf
323 1.1.6.2 mjf pxa2x0_apm_sleep(sc);
324 1.1.6.2 mjf }
325 1.1.6.2 mjf
326 1.1.6.2 mjf void
327 1.1.6.2 mjf apm_resume(struct pxa2x0_apm_softc *sc)
328 1.1.6.2 mjf {
329 1.1.6.2 mjf
330 1.1.6.2 mjf dopowerhooks(PWR_RESUME);
331 1.1.6.2 mjf
332 1.1.6.2 mjf inittodr(0);
333 1.1.6.2 mjf
334 1.1.6.2 mjf /*
335 1.1.6.2 mjf * Clear the OTG Peripheral hold after running the pxaudc and pxaohci
336 1.1.6.2 mjf * powerhooks to re-enable their operation. See 3.8.1.2
337 1.1.6.2 mjf */
338 1.1.6.2 mjf /* XXX ifdef NPXAUDC > 0 */
339 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PSSR, PSSR_OTGPH);
340 1.1.6.2 mjf }
341 1.1.6.2 mjf
342 1.1.6.2 mjf #if 0
343 1.1.6.2 mjf int
344 1.1.6.2 mjf apm_get_event(struct pxa2x0_apm_softc *sc, u_int *typep)
345 1.1.6.2 mjf {
346 1.1.6.2 mjf
347 1.1.6.2 mjf if (sc->sc_get_event != NULL)
348 1.1.6.2 mjf return (sc->sc_get_event(sc, typep));
349 1.1.6.2 mjf
350 1.1.6.2 mjf *typep = APM_NOEVENT;
351 1.1.6.2 mjf return (1);
352 1.1.6.2 mjf }
353 1.1.6.2 mjf
354 1.1.6.2 mjf int
355 1.1.6.2 mjf apm_handle_event(struct pxa2x0_apm_softc *sc, u_int type)
356 1.1.6.2 mjf {
357 1.1.6.2 mjf struct apm_power_info power;
358 1.1.6.2 mjf int ret = 0;
359 1.1.6.2 mjf
360 1.1.6.2 mjf switch (type) {
361 1.1.6.2 mjf case APM_NOEVENT:
362 1.1.6.2 mjf ret = 1;
363 1.1.6.2 mjf break;
364 1.1.6.2 mjf case APM_CRIT_SUSPEND_REQ:
365 1.1.6.2 mjf DPRINTF(("suspend required immediately\n"));
366 1.1.6.2 mjf #if 0
367 1.1.6.2 mjf /* XXX apmd would make us suspend again after resume. */
368 1.1.6.2 mjf (void)apm_record_event(sc, type);
369 1.1.6.2 mjf #endif
370 1.1.6.2 mjf /*
371 1.1.6.2 mjf * We ignore APM_CRIT_RESUME and just suspend here as usual
372 1.1.6.2 mjf * to simplify the actual apm_get_event() implementation.
373 1.1.6.2 mjf */
374 1.1.6.2 mjf apm_suspends++;
375 1.1.6.2 mjf ret = 1;
376 1.1.6.2 mjf break;
377 1.1.6.2 mjf case APM_USER_SUSPEND_REQ:
378 1.1.6.2 mjf case APM_SUSPEND_REQ:
379 1.1.6.2 mjf DPRINTF(("suspend requested\n"));
380 1.1.6.2 mjf if (apm_record_event(sc, type)) {
381 1.1.6.2 mjf DPRINTF(("suspend ourselves\n"));
382 1.1.6.2 mjf apm_suspends++;
383 1.1.6.2 mjf }
384 1.1.6.2 mjf break;
385 1.1.6.2 mjf case APM_POWER_CHANGE:
386 1.1.6.2 mjf DPRINTF(("power status change\n"));
387 1.1.6.2 mjf apm_power_info(sc, &power);
388 1.1.6.2 mjf if (power.battery_life != APM_BATT_LIFE_UNKNOWN &&
389 1.1.6.2 mjf power.battery_life < cpu_apmwarn &&
390 1.1.6.2 mjf (sc->sc_flags & SCFLAG_PRINT) != SCFLAG_NOPRINT &&
391 1.1.6.2 mjf ((sc->sc_flags & SCFLAG_PRINT) != SCFLAG_PCTPRINT ||
392 1.1.6.2 mjf sc->sc_batt_life != power.battery_life)) {
393 1.1.6.2 mjf sc->sc_batt_life = power.battery_life;
394 1.1.6.2 mjf apm_power_print(sc, &power);
395 1.1.6.2 mjf }
396 1.1.6.2 mjf apm_record_event(sc, type);
397 1.1.6.2 mjf break;
398 1.1.6.2 mjf case APM_BATTERY_LOW:
399 1.1.6.2 mjf DPRINTF(("Battery low!\n"));
400 1.1.6.2 mjf apm_battlow++;
401 1.1.6.2 mjf apm_record_event(sc, type);
402 1.1.6.2 mjf break;
403 1.1.6.2 mjf default:
404 1.1.6.2 mjf DPRINTF(("apm_handle_event: unsupported event, code %d\n",
405 1.1.6.2 mjf type));
406 1.1.6.2 mjf }
407 1.1.6.2 mjf
408 1.1.6.2 mjf return (ret);
409 1.1.6.2 mjf }
410 1.1.6.2 mjf
411 1.1.6.2 mjf void
412 1.1.6.2 mjf apm_thread_create(void *v)
413 1.1.6.2 mjf {
414 1.1.6.2 mjf struct pxa2x0_apm_softc *sc = v;
415 1.1.6.2 mjf
416 1.1.6.2 mjf if (kthread_create(apm_thread, sc, &sc->sc_thread,
417 1.1.6.2 mjf "%s", sc->sc_dev.dv_xname)) {
418 1.1.6.2 mjf /* apm_disconnect(sc); */
419 1.1.6.2 mjf printf("%s: failed to create kernel thread, disabled",
420 1.1.6.2 mjf sc->sc_dev.dv_xname);
421 1.1.6.2 mjf }
422 1.1.6.2 mjf }
423 1.1.6.2 mjf
424 1.1.6.2 mjf void
425 1.1.6.2 mjf apm_thread(void *v)
426 1.1.6.2 mjf {
427 1.1.6.2 mjf struct pxa2x0_apm_softc *sc = v;
428 1.1.6.2 mjf u_int type;
429 1.1.6.2 mjf
430 1.1.6.2 mjf for (;;) {
431 1.1.6.2 mjf APM_LOCK(sc);
432 1.1.6.2 mjf
433 1.1.6.2 mjf while (1) {
434 1.1.6.2 mjf if (apm_get_event(sc, &type) != 0)
435 1.1.6.2 mjf break;
436 1.1.6.2 mjf if (apm_handle_event(sc, type) != 0)
437 1.1.6.2 mjf break;
438 1.1.6.2 mjf }
439 1.1.6.2 mjf if (apm_suspends || apm_userstandbys /* || apm_battlow*/) {
440 1.1.6.2 mjf apm_suspend(sc);
441 1.1.6.2 mjf apm_resume(sc);
442 1.1.6.2 mjf }
443 1.1.6.2 mjf apm_battlow = apm_suspends = apm_userstandbys = 0;
444 1.1.6.2 mjf
445 1.1.6.2 mjf APM_UNLOCK(sc);
446 1.1.6.2 mjf tsleep(&lbolt, PWAIT, "apmev", 0);
447 1.1.6.2 mjf }
448 1.1.6.2 mjf }
449 1.1.6.2 mjf
450 1.1.6.2 mjf int
451 1.1.6.2 mjf apmopen(dev_t dev, int flag, int mode, struct proc *p)
452 1.1.6.2 mjf {
453 1.1.6.2 mjf struct pxa2x0_apm_softc *sc;
454 1.1.6.2 mjf int error = 0;
455 1.1.6.2 mjf
456 1.1.6.2 mjf /* apm0 only */
457 1.1.6.2 mjf if (!zapm_cd.cd_ndevs || APMUNIT(dev) != 0 ||
458 1.1.6.2 mjf !(sc = zapm_cd.cd_devs[APMUNIT(dev)]))
459 1.1.6.2 mjf return (ENXIO);
460 1.1.6.2 mjf
461 1.1.6.2 mjf DPRINTF(("apmopen: dev %d pid %d flag %x mode %x\n",
462 1.1.6.2 mjf APMDEV(dev), p->p_pid, flag, mode));
463 1.1.6.2 mjf
464 1.1.6.2 mjf switch (APMDEV(dev)) {
465 1.1.6.2 mjf case APMDEV_CTL:
466 1.1.6.2 mjf if (!(flag & FWRITE)) {
467 1.1.6.2 mjf error = EINVAL;
468 1.1.6.2 mjf break;
469 1.1.6.2 mjf }
470 1.1.6.2 mjf if (sc->sc_flags & SCFLAG_OWRITE) {
471 1.1.6.2 mjf error = EBUSY;
472 1.1.6.2 mjf break;
473 1.1.6.2 mjf }
474 1.1.6.2 mjf sc->sc_flags |= SCFLAG_OWRITE;
475 1.1.6.2 mjf break;
476 1.1.6.2 mjf case APMDEV_NORMAL:
477 1.1.6.2 mjf if (!(flag & FREAD) || (flag & FWRITE)) {
478 1.1.6.2 mjf error = EINVAL;
479 1.1.6.2 mjf break;
480 1.1.6.2 mjf }
481 1.1.6.2 mjf sc->sc_flags |= SCFLAG_OREAD;
482 1.1.6.2 mjf break;
483 1.1.6.2 mjf default:
484 1.1.6.2 mjf error = ENXIO;
485 1.1.6.2 mjf break;
486 1.1.6.2 mjf }
487 1.1.6.2 mjf return (error);
488 1.1.6.2 mjf }
489 1.1.6.2 mjf
490 1.1.6.2 mjf int
491 1.1.6.2 mjf apmclose(dev_t dev, int flag, int mode, struct proc *p)
492 1.1.6.2 mjf {
493 1.1.6.2 mjf struct pxa2x0_apm_softc *sc;
494 1.1.6.2 mjf
495 1.1.6.2 mjf /* apm0 only */
496 1.1.6.2 mjf if (!apm_cd.cd_ndevs || APMUNIT(dev) != 0 ||
497 1.1.6.2 mjf !(sc = apm_cd.cd_devs[APMUNIT(dev)]))
498 1.1.6.2 mjf return (ENXIO);
499 1.1.6.2 mjf
500 1.1.6.2 mjf DPRINTF(("apmclose: pid %d flag %x mode %x\n", p->p_pid, flag, mode));
501 1.1.6.2 mjf
502 1.1.6.2 mjf switch (APMDEV(dev)) {
503 1.1.6.2 mjf case APMDEV_CTL:
504 1.1.6.2 mjf sc->sc_flags &= ~SCFLAG_OWRITE;
505 1.1.6.2 mjf break;
506 1.1.6.2 mjf case APMDEV_NORMAL:
507 1.1.6.2 mjf sc->sc_flags &= ~SCFLAG_OREAD;
508 1.1.6.2 mjf break;
509 1.1.6.2 mjf }
510 1.1.6.2 mjf return (0);
511 1.1.6.2 mjf }
512 1.1.6.2 mjf
513 1.1.6.2 mjf int
514 1.1.6.2 mjf apmioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
515 1.1.6.2 mjf {
516 1.1.6.2 mjf struct pxa2x0_apm_softc *sc;
517 1.1.6.2 mjf struct apm_power_info *power;
518 1.1.6.2 mjf int error = 0;
519 1.1.6.2 mjf
520 1.1.6.2 mjf /* apm0 only */
521 1.1.6.2 mjf if (!apm_cd.cd_ndevs || APMUNIT(dev) != 0 ||
522 1.1.6.2 mjf !(sc = apm_cd.cd_devs[APMUNIT(dev)]))
523 1.1.6.2 mjf return (ENXIO);
524 1.1.6.2 mjf
525 1.1.6.2 mjf switch (cmd) {
526 1.1.6.2 mjf /* some ioctl names from linux */
527 1.1.6.2 mjf case APM_IOC_STANDBY:
528 1.1.6.2 mjf if ((flag & FWRITE) == 0)
529 1.1.6.2 mjf error = EBADF;
530 1.1.6.2 mjf else
531 1.1.6.2 mjf apm_userstandbys++;
532 1.1.6.2 mjf break;
533 1.1.6.2 mjf case APM_IOC_SUSPEND:
534 1.1.6.2 mjf if ((flag & FWRITE) == 0)
535 1.1.6.2 mjf error = EBADF;
536 1.1.6.2 mjf else
537 1.1.6.2 mjf apm_suspends++; /* XXX */
538 1.1.6.2 mjf break;
539 1.1.6.2 mjf case APM_IOC_PRN_CTL:
540 1.1.6.2 mjf if ((flag & FWRITE) == 0)
541 1.1.6.2 mjf error = EBADF;
542 1.1.6.2 mjf else {
543 1.1.6.2 mjf int flag = *(int *)data;
544 1.1.6.2 mjf DPRINTF(( "APM_IOC_PRN_CTL: %d\n", flag ));
545 1.1.6.2 mjf switch (flag) {
546 1.1.6.2 mjf case APM_PRINT_ON: /* enable printing */
547 1.1.6.2 mjf sc->sc_flags &= ~SCFLAG_PRINT;
548 1.1.6.2 mjf break;
549 1.1.6.2 mjf case APM_PRINT_OFF: /* disable printing */
550 1.1.6.2 mjf sc->sc_flags &= ~SCFLAG_PRINT;
551 1.1.6.2 mjf sc->sc_flags |= SCFLAG_NOPRINT;
552 1.1.6.2 mjf break;
553 1.1.6.2 mjf case APM_PRINT_PCT: /* disable some printing */
554 1.1.6.2 mjf sc->sc_flags &= ~SCFLAG_PRINT;
555 1.1.6.2 mjf sc->sc_flags |= SCFLAG_PCTPRINT;
556 1.1.6.2 mjf break;
557 1.1.6.2 mjf default:
558 1.1.6.2 mjf error = EINVAL;
559 1.1.6.2 mjf break;
560 1.1.6.2 mjf }
561 1.1.6.2 mjf }
562 1.1.6.2 mjf break;
563 1.1.6.2 mjf case APM_IOC_DEV_CTL:
564 1.1.6.2 mjf if ((flag & FWRITE) == 0)
565 1.1.6.2 mjf error = EBADF;
566 1.1.6.2 mjf break;
567 1.1.6.2 mjf case APM_IOC_GETPOWER:
568 1.1.6.2 mjf power = (struct apm_power_info *)data;
569 1.1.6.2 mjf apm_power_info(sc, power);
570 1.1.6.2 mjf break;
571 1.1.6.2 mjf
572 1.1.6.2 mjf default:
573 1.1.6.2 mjf error = ENOTTY;
574 1.1.6.2 mjf }
575 1.1.6.2 mjf
576 1.1.6.2 mjf return (error);
577 1.1.6.2 mjf }
578 1.1.6.2 mjf
579 1.1.6.2 mjf int
580 1.1.6.2 mjf apm_record_event(struct pxa2x0_apm_softc *sc, u_int type)
581 1.1.6.2 mjf {
582 1.1.6.2 mjf static int apm_evindex;
583 1.1.6.2 mjf
584 1.1.6.2 mjf /* skip if no user waiting */
585 1.1.6.2 mjf if ((sc->sc_flags & SCFLAG_OPEN) == 0)
586 1.1.6.2 mjf return (1);
587 1.1.6.2 mjf
588 1.1.6.2 mjf apm_evindex++;
589 1.1.6.2 mjf KNOTE(&sc->sc_note, APM_EVENT_COMPOSE(type, apm_evindex));
590 1.1.6.2 mjf
591 1.1.6.2 mjf return (0);
592 1.1.6.2 mjf }
593 1.1.6.2 mjf
594 1.1.6.2 mjf void
595 1.1.6.2 mjf filt_apmrdetach(struct knote *kn)
596 1.1.6.2 mjf {
597 1.1.6.2 mjf struct pxa2x0_apm_softc *sc =
598 1.1.6.2 mjf (struct pxa2x0_apm_softc *)kn->kn_hook;
599 1.1.6.2 mjf
600 1.1.6.2 mjf SLIST_REMOVE(&sc->sc_note, kn, knote, kn_selnext);
601 1.1.6.2 mjf }
602 1.1.6.2 mjf
603 1.1.6.2 mjf int
604 1.1.6.2 mjf filt_apmread(struct knote *kn, long hint)
605 1.1.6.2 mjf {
606 1.1.6.2 mjf /* XXX weird kqueue_scan() semantics */
607 1.1.6.2 mjf if (hint && !kn->kn_data)
608 1.1.6.2 mjf kn->kn_data = (int)hint;
609 1.1.6.2 mjf
610 1.1.6.2 mjf return (1);
611 1.1.6.2 mjf }
612 1.1.6.2 mjf
613 1.1.6.2 mjf int
614 1.1.6.2 mjf apmkqfilter(dev_t dev, struct knote *kn)
615 1.1.6.2 mjf {
616 1.1.6.2 mjf struct pxa2x0_apm_softc *sc;
617 1.1.6.2 mjf
618 1.1.6.2 mjf /* apm0 only */
619 1.1.6.2 mjf if (!apm_cd.cd_ndevs || APMUNIT(dev) != 0 ||
620 1.1.6.2 mjf !(sc = apm_cd.cd_devs[APMUNIT(dev)]))
621 1.1.6.2 mjf return (ENXIO);
622 1.1.6.2 mjf
623 1.1.6.2 mjf switch (kn->kn_filter) {
624 1.1.6.2 mjf case EVFILT_READ:
625 1.1.6.2 mjf kn->kn_fop = &apmread_filtops;
626 1.1.6.2 mjf break;
627 1.1.6.2 mjf default:
628 1.1.6.2 mjf return (1);
629 1.1.6.2 mjf }
630 1.1.6.2 mjf
631 1.1.6.2 mjf kn->kn_hook = (caddr_t)sc;
632 1.1.6.2 mjf SLIST_INSERT_HEAD(&sc->sc_note, kn, kn_selnext);
633 1.1.6.2 mjf
634 1.1.6.2 mjf return (0);
635 1.1.6.2 mjf }
636 1.1.6.2 mjf
637 1.1.6.2 mjf void
638 1.1.6.2 mjf pxa2x0_apm_attach_sub(struct pxa2x0_apm_softc *sc)
639 1.1.6.2 mjf {
640 1.1.6.2 mjf
641 1.1.6.2 mjf sc->sc_iot = &pxa2x0_bs_tag;
642 1.1.6.2 mjf
643 1.1.6.2 mjf if (bus_space_map(sc->sc_iot, PXA2X0_POWMAN_BASE,
644 1.1.6.2 mjf PXA2X0_POWMAN_SIZE, 0, &sc->sc_pm_ioh)) {
645 1.1.6.2 mjf printf("pxa2x0_apm_attach_sub: failed to map POWMAN\n");
646 1.1.6.2 mjf return;
647 1.1.6.2 mjf }
648 1.1.6.2 mjf
649 1.1.6.2 mjf lockinit(&sc->sc_lock, PWAIT, "apmlk", 0, 0);
650 1.1.6.2 mjf
651 1.1.6.2 mjf kthread_create_deferred(apm_thread_create, sc);
652 1.1.6.2 mjf
653 1.1.6.2 mjf printf("\n");
654 1.1.6.2 mjf
655 1.1.6.2 mjf if (bus_space_map(sc->sc_iot, PXA2X0_CLKMAN_BASE, PXA2X0_CLKMAN_SIZE,
656 1.1.6.2 mjf 0, &pxa2x0_clkman_ioh)) {
657 1.1.6.2 mjf printf("%s: failed to map CLKMAN\n", sc->sc_dev.dv_xname);
658 1.1.6.2 mjf return;
659 1.1.6.2 mjf }
660 1.1.6.2 mjf
661 1.1.6.2 mjf if (bus_space_map(sc->sc_iot, PXA2X0_MEMCTL_BASE, PXA2X0_MEMCTL_SIZE,
662 1.1.6.2 mjf 0, &pxa2x0_memctl_ioh)) {
663 1.1.6.2 mjf printf("%s: failed to map MEMCTL\n", sc->sc_dev.dv_xname);
664 1.1.6.2 mjf return;
665 1.1.6.2 mjf }
666 1.1.6.2 mjf sc->sc_memctl_ioh = pxa2x0_memctl_ioh;
667 1.1.6.2 mjf
668 1.1.6.2 mjf if (bus_space_map(sc->sc_iot, PXA2X0_GPIO_BASE, PXA2X0_GPIO_SIZE,
669 1.1.6.2 mjf 0, &pxa2x0_gpio_ioh)) {
670 1.1.6.2 mjf printf("%s: can't map GPIO\n", sc->sc_dev.dv_xname);
671 1.1.6.2 mjf return;
672 1.1.6.2 mjf }
673 1.1.6.2 mjf
674 1.1.6.2 mjf /* Clear all reset status flags. */
675 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_RCSR,
676 1.1.6.2 mjf RCSR_GPR | RCSR_SMR | RCSR_WDR | RCSR_HWR);
677 1.1.6.2 mjf }
678 1.1.6.2 mjf #endif /* 0 */
679 1.1.6.2 mjf
680 1.1.6.2 mjf void
681 1.1.6.2 mjf pxa2x0_wakeup_config(u_int wsrc, int enable)
682 1.1.6.2 mjf {
683 1.1.6.2 mjf struct pxa2x0_apm_softc *sc;
684 1.1.6.2 mjf u_int32_t prer;
685 1.1.6.2 mjf u_int32_t pfer;
686 1.1.6.2 mjf u_int32_t pkwr;
687 1.1.6.2 mjf
688 1.1.6.2 mjf if (zapm_cd.cd_ndevs < 1 || zapm_cd.cd_devs[0] == NULL)
689 1.1.6.2 mjf return;
690 1.1.6.2 mjf sc = device_private(zapm_cd.cd_devs[0]);
691 1.1.6.2 mjf
692 1.1.6.2 mjf prer = pfer = pkwr = 0;
693 1.1.6.2 mjf
694 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_POWERON) != 0) {
695 1.1.6.2 mjf prer |= (1<<0);
696 1.1.6.2 mjf pfer |= (1<<0);
697 1.1.6.2 mjf pkwr |= (1<<12); /* XXX */
698 1.1.6.2 mjf }
699 1.1.6.2 mjf
700 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_GPIORST) != 0)
701 1.1.6.2 mjf pfer |= (1<<1);
702 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_SD) != 0)
703 1.1.6.2 mjf prer |= (1<<9);
704 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_RC) != 0)
705 1.1.6.2 mjf prer |= (1<<13);
706 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_SYNC) != 0)
707 1.1.6.2 mjf pkwr |= (1<<1);
708 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_KEYNS0) != 0)
709 1.1.6.2 mjf prer |= (1<<12);
710 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_KEYNS1) != 0)
711 1.1.6.2 mjf pkwr |= (1<<2);
712 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_KEYNS2) != 0)
713 1.1.6.2 mjf pkwr |= (1<<9);
714 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_KEYNS3) != 0)
715 1.1.6.2 mjf pkwr |= (1<<3);
716 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_KEYNS4) != 0)
717 1.1.6.2 mjf pkwr |= (1<<4);
718 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_KEYNS5) != 0)
719 1.1.6.2 mjf pkwr |= (1<<6);
720 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_KEYNS6) != 0)
721 1.1.6.2 mjf pkwr |= (1<<7);
722 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_CF0) != 0)
723 1.1.6.2 mjf pkwr |= (1<<11);
724 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_CF1) != 0)
725 1.1.6.2 mjf pkwr |= (1<<10);
726 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_USBD) != 0)
727 1.1.6.2 mjf prer |= (1<<24);
728 1.1.6.2 mjf
729 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_LOCKSW) != 0) {
730 1.1.6.2 mjf prer |= (1<<15);
731 1.1.6.2 mjf pfer |= (1<<15);
732 1.1.6.2 mjf }
733 1.1.6.2 mjf
734 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_JACKIN) != 0) {
735 1.1.6.2 mjf prer |= (1<<23);
736 1.1.6.2 mjf pfer |= (1<<23);
737 1.1.6.2 mjf }
738 1.1.6.2 mjf
739 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_CHRGFULL) != 0)
740 1.1.6.2 mjf pkwr |= (1<<18);
741 1.1.6.2 mjf if ((wsrc & PXA2X0_WAKEUP_RTC) != 0)
742 1.1.6.2 mjf prer |= (1<<31);
743 1.1.6.2 mjf
744 1.1.6.2 mjf if (enable) {
745 1.1.6.2 mjf sc->sc_wakeon |= wsrc;
746 1.1.6.2 mjf prer |= bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh,
747 1.1.6.2 mjf POWMAN_PRER);
748 1.1.6.2 mjf pfer |= bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh,
749 1.1.6.2 mjf POWMAN_PFER);
750 1.1.6.2 mjf pkwr |= bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh,
751 1.1.6.2 mjf POWMAN_PKWR);
752 1.1.6.2 mjf } else {
753 1.1.6.2 mjf sc->sc_wakeon &= ~wsrc;
754 1.1.6.2 mjf prer = bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh,
755 1.1.6.2 mjf POWMAN_PRER) & ~prer;
756 1.1.6.2 mjf pfer = bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh,
757 1.1.6.2 mjf POWMAN_PFER) & ~pfer;
758 1.1.6.2 mjf pkwr = bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh,
759 1.1.6.2 mjf POWMAN_PKWR) & ~pkwr;
760 1.1.6.2 mjf }
761 1.1.6.2 mjf
762 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PKWR, pkwr);
763 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PRER, prer);
764 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PFER, pfer);
765 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PWER,
766 1.1.6.2 mjf prer | pfer);
767 1.1.6.2 mjf }
768 1.1.6.2 mjf
769 1.1.6.2 mjf u_int
770 1.1.6.2 mjf pxa2x0_wakeup_status(void)
771 1.1.6.2 mjf {
772 1.1.6.2 mjf struct pxa2x0_apm_softc *sc;
773 1.1.6.2 mjf u_int32_t rv;
774 1.1.6.2 mjf u_int wsrc;
775 1.1.6.2 mjf
776 1.1.6.2 mjf if (zapm_cd.cd_ndevs < 1 || zapm_cd.cd_devs[0] == NULL)
777 1.1.6.2 mjf return (0);
778 1.1.6.2 mjf
779 1.1.6.2 mjf sc = device_private(zapm_cd.cd_devs[0]);
780 1.1.6.2 mjf wsrc = 0;
781 1.1.6.2 mjf
782 1.1.6.2 mjf rv = bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PEDR);
783 1.1.6.2 mjf if ((rv & (1<<0)) != 0)
784 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_POWERON;
785 1.1.6.2 mjf if ((rv & (1<<1)) != 0)
786 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_GPIORST;
787 1.1.6.2 mjf if ((rv & (1<<9)) != 0)
788 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_SD;
789 1.1.6.2 mjf if ((rv & (1<<12)) != 0)
790 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_KEYNS0;
791 1.1.6.2 mjf if ((rv & (1<<13)) != 0)
792 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_RC;
793 1.1.6.2 mjf if ((rv & (1<<15)) != 0)
794 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_LOCKSW;
795 1.1.6.2 mjf if ((rv & (1<<23)) != 0)
796 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_JACKIN;
797 1.1.6.2 mjf if ((rv & (1<<24)) != 0)
798 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_USBD;
799 1.1.6.2 mjf if ((rv & (1<<31)) != 0)
800 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_RTC;
801 1.1.6.2 mjf
802 1.1.6.2 mjf rv = bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PKSR);
803 1.1.6.2 mjf if ((rv & (1<<1)) != 0)
804 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_SYNC;
805 1.1.6.2 mjf if ((rv & (1<<2)) != 0)
806 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_KEYNS1;
807 1.1.6.2 mjf if ((rv & (1<<9)) != 0)
808 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_KEYNS2;
809 1.1.6.2 mjf if ((rv & (1<<3)) != 0)
810 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_KEYNS3;
811 1.1.6.2 mjf if ((rv & (1<<4)) != 0)
812 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_KEYNS4;
813 1.1.6.2 mjf if ((rv & (1<<6)) != 0)
814 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_KEYNS5;
815 1.1.6.2 mjf if ((rv & (1<<7)) != 0)
816 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_KEYNS6;
817 1.1.6.2 mjf if ((rv & (1<<10)) != 0)
818 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_CF1;
819 1.1.6.2 mjf if ((rv & (1<<11)) != 0)
820 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_CF0;
821 1.1.6.2 mjf if ((rv & (1<<12)) != 0)
822 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_POWERON;
823 1.1.6.2 mjf if ((rv & (1<<18)) != 0)
824 1.1.6.2 mjf wsrc |= PXA2X0_WAKEUP_CHRGFULL;
825 1.1.6.2 mjf
826 1.1.6.2 mjf return (wsrc);
827 1.1.6.2 mjf }
828 1.1.6.2 mjf
829 1.1.6.2 mjf struct pxa2x0_sleep_data {
830 1.1.6.2 mjf /* OS timer registers */
831 1.1.6.2 mjf u_int32_t sd_osmr0, sd_osmr1, sd_osmr2, sd_osmr3;
832 1.1.6.2 mjf u_int32_t sd_oscr0;
833 1.1.6.2 mjf u_int32_t sd_osmr4, sd_osmr5;
834 1.1.6.2 mjf u_int32_t sd_oscr4;
835 1.1.6.2 mjf u_int32_t sd_omcr4, sd_omcr5;
836 1.1.6.2 mjf u_int32_t sd_oier;
837 1.1.6.2 mjf /* GPIO registers */
838 1.1.6.2 mjf u_int32_t sd_gpdr0, sd_gpdr1, sd_gpdr2, sd_gpdr3;
839 1.1.6.2 mjf u_int32_t sd_grer0, sd_grer1, sd_grer2, sd_grer3;
840 1.1.6.2 mjf u_int32_t sd_gfer0, sd_gfer1, sd_gfer2, sd_gfer3;
841 1.1.6.2 mjf u_int32_t sd_gafr0_l, sd_gafr1_l, sd_gafr2_l, sd_gafr3_l;
842 1.1.6.2 mjf u_int32_t sd_gafr0_u, sd_gafr1_u, sd_gafr2_u, sd_gafr3_u;
843 1.1.6.2 mjf u_int32_t sd_gplr0, sd_gplr1, sd_gplr2, sd_gplr3;
844 1.1.6.2 mjf /* Interrupt controller registers */
845 1.1.6.2 mjf u_int32_t sd_iclr;
846 1.1.6.2 mjf u_int32_t sd_icmr;
847 1.1.6.2 mjf u_int32_t sd_iccr;
848 1.1.6.2 mjf /* Memory controller registers */
849 1.1.6.2 mjf u_int32_t sd_mecr;
850 1.1.6.2 mjf u_int32_t sd_mcmem0, sd_mcmem1;
851 1.1.6.2 mjf u_int32_t sd_mcatt0, sd_mcatt1;
852 1.1.6.2 mjf u_int32_t sd_mcio0, sd_mcio1;
853 1.1.6.2 mjf /* Clocks manager registers */
854 1.1.6.2 mjf u_int32_t sd_cken;
855 1.1.6.2 mjf };
856 1.1.6.2 mjf
857 1.1.6.2 mjf void
858 1.1.6.2 mjf pxa2x0_apm_sleep(struct pxa2x0_apm_softc *sc)
859 1.1.6.2 mjf {
860 1.1.6.2 mjf struct pxa2x0_sleep_data sd;
861 1.1.6.2 mjf bus_space_handle_t ost_ioh;
862 1.1.6.2 mjf int save;
863 1.1.6.2 mjf u_int32_t rv;
864 1.1.6.2 mjf
865 1.1.6.2 mjf ost_ioh = (bus_space_handle_t)0;
866 1.1.6.2 mjf if (bus_space_map(sc->sc_iot, PXA2X0_OST_BASE, PXA2X0_OST_SIZE, 0,
867 1.1.6.2 mjf &ost_ioh)) {
868 1.1.6.2 mjf printf("pxa2x0_apm_sleep: can't map OST\n");
869 1.1.6.2 mjf goto out;
870 1.1.6.2 mjf }
871 1.1.6.2 mjf
872 1.1.6.2 mjf save = disable_interrupts(I32_bit|F32_bit);
873 1.1.6.2 mjf
874 1.1.6.2 mjf sd.sd_oscr0 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSCR0);
875 1.1.6.2 mjf sd.sd_oscr4 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSCR4);
876 1.1.6.2 mjf sd.sd_omcr4 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OMCR4);
877 1.1.6.2 mjf sd.sd_omcr5 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OMCR5);
878 1.1.6.2 mjf sd.sd_osmr0 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSMR0);
879 1.1.6.2 mjf sd.sd_osmr1 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSMR1);
880 1.1.6.2 mjf sd.sd_osmr2 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSMR2);
881 1.1.6.2 mjf sd.sd_osmr3 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSMR3);
882 1.1.6.2 mjf sd.sd_osmr4 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSMR4);
883 1.1.6.2 mjf sd.sd_osmr5 = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OSMR5);
884 1.1.6.2 mjf sd.sd_oier = bus_space_read_4(sc->sc_iot, ost_ioh, OST_OIER);
885 1.1.6.2 mjf
886 1.1.6.2 mjf /* Bring the PXA27x into 416MHz turbo mode. */
887 1.1.6.2 mjf if ((cputype & ~CPU_ID_XSCALE_COREREV_MASK) == CPU_ID_PXA27X &&
888 1.1.6.2 mjf bus_space_read_4(sc->sc_iot, pxa2x0_clkman_ioh, CLKMAN_CCCR) !=
889 1.1.6.2 mjf (CCCR_A | CCCR_TURBO_X2 | CCCR_RUN_X16)) {
890 1.1.6.2 mjf #if 0
891 1.1.6.2 mjf pxa27x_cpu_speed_high();
892 1.1.6.2 mjf #else
893 1.1.6.2 mjf #define CLKCFG_T (1<<0) /* turbo */
894 1.1.6.2 mjf #define CLKCFG_F (1<<1) /* frequency change */
895 1.1.6.2 mjf #define CLKCFG_B (1<<3) /* fast-bus */
896 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 |
897 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_B | CLKCFG_F | CLKCFG_T,
898 1.1.6.2 mjf &pxa2x0_memcfg);
899 1.1.6.2 mjf #endif
900 1.1.6.2 mjf delay(500000); /* XXX */
901 1.1.6.2 mjf }
902 1.1.6.2 mjf
903 1.1.6.2 mjf suspend_again:
904 1.1.6.2 mjf /* Clear wake-up status. */
905 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PEDR,
906 1.1.6.2 mjf 0xffffffff);
907 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PKSR,
908 1.1.6.2 mjf 0xffffffff);
909 1.1.6.2 mjf
910 1.1.6.2 mjf /* XXX control battery charging in sleep mode. */
911 1.1.6.2 mjf
912 1.1.6.2 mjf /* XXX schedule RTC alarm to check the battery, or schedule
913 1.1.6.2 mjf XXX wake-up shortly before an already programmed alarm? */
914 1.1.6.2 mjf
915 1.1.6.2 mjf pxa27x_run_mode();
916 1.1.6.2 mjf #define MDREFR_LOW (MDREFR_C3000 | 0x00b)
917 1.1.6.2 mjf pxa27x_fastbus_run_mode(0, MDREFR_LOW);
918 1.1.6.2 mjf delay(1);
919 1.1.6.2 mjf #if 1
920 1.1.6.2 mjf pxa27x_cpu_speed_91();
921 1.1.6.2 mjf #else
922 1.1.6.2 mjf pxa27x_frequency_change(CCCR_TURBO_X1 | CCCR_RUN_X7, CLKCFG_F,
923 1.1.6.2 mjf &pxa2x0_memcfg);
924 1.1.6.2 mjf #endif
925 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(sc->sc_iot, sc->sc_pm_ioh, PI2C_VOLTAGE_LOW);
926 1.1.6.2 mjf
927 1.1.6.2 mjf sd.sd_gpdr0 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR0);
928 1.1.6.2 mjf sd.sd_gpdr1 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR1);
929 1.1.6.2 mjf sd.sd_gpdr2 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR2);
930 1.1.6.2 mjf sd.sd_gpdr3 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR3);
931 1.1.6.2 mjf
932 1.1.6.2 mjf sd.sd_grer0 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER0);
933 1.1.6.2 mjf sd.sd_grer1 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER1);
934 1.1.6.2 mjf sd.sd_grer2 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER2);
935 1.1.6.2 mjf sd.sd_grer3 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER3);
936 1.1.6.2 mjf
937 1.1.6.2 mjf sd.sd_gfer0 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER0);
938 1.1.6.2 mjf sd.sd_gfer1 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER1);
939 1.1.6.2 mjf sd.sd_gfer2 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER2);
940 1.1.6.2 mjf sd.sd_gfer3 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER3);
941 1.1.6.2 mjf
942 1.1.6.2 mjf sd.sd_gafr0_l = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR0_L);
943 1.1.6.2 mjf sd.sd_gafr1_l = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR1_L);
944 1.1.6.2 mjf sd.sd_gafr2_l = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR2_L);
945 1.1.6.2 mjf sd.sd_gafr3_l = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR3_L);
946 1.1.6.2 mjf
947 1.1.6.2 mjf sd.sd_gafr0_u = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR0_U);
948 1.1.6.2 mjf sd.sd_gafr1_u = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR1_U);
949 1.1.6.2 mjf sd.sd_gafr2_u = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR2_U);
950 1.1.6.2 mjf sd.sd_gafr3_u = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR3_U);
951 1.1.6.2 mjf
952 1.1.6.2 mjf sd.sd_gplr0 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPLR0);
953 1.1.6.2 mjf sd.sd_gplr1 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPLR1);
954 1.1.6.2 mjf sd.sd_gplr2 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPLR2);
955 1.1.6.2 mjf sd.sd_gplr3 = bus_space_read_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPLR3);
956 1.1.6.2 mjf
957 1.1.6.2 mjf sd.sd_iclr = read_icu(INTCTL_ICLR);
958 1.1.6.2 mjf sd.sd_icmr = read_icu(INTCTL_ICMR);
959 1.1.6.2 mjf sd.sd_iccr = read_icu(INTCTL_ICCR);
960 1.1.6.2 mjf write_icu(INTCTL_ICMR, 0);
961 1.1.6.2 mjf
962 1.1.6.2 mjf sd.sd_mecr = bus_space_read_4(sc->sc_iot, pxa2x0_memctl_ioh,
963 1.1.6.2 mjf MEMCTL_MECR);
964 1.1.6.2 mjf sd.sd_mcmem0 = bus_space_read_4(sc->sc_iot, pxa2x0_memctl_ioh,
965 1.1.6.2 mjf MEMCTL_MCMEM(0));
966 1.1.6.2 mjf sd.sd_mcmem1 = bus_space_read_4(sc->sc_iot, pxa2x0_memctl_ioh,
967 1.1.6.2 mjf MEMCTL_MCMEM(1));
968 1.1.6.2 mjf sd.sd_mcatt0 = bus_space_read_4(sc->sc_iot, pxa2x0_memctl_ioh,
969 1.1.6.2 mjf MEMCTL_MCATT(0));
970 1.1.6.2 mjf sd.sd_mcatt1 = bus_space_read_4(sc->sc_iot, pxa2x0_memctl_ioh,
971 1.1.6.2 mjf MEMCTL_MCATT(1));
972 1.1.6.2 mjf sd.sd_mcio0 = bus_space_read_4(sc->sc_iot, pxa2x0_memctl_ioh,
973 1.1.6.2 mjf MEMCTL_MCIO(0));
974 1.1.6.2 mjf sd.sd_mcio1 = bus_space_read_4(sc->sc_iot, pxa2x0_memctl_ioh,
975 1.1.6.2 mjf MEMCTL_MCIO(1));
976 1.1.6.2 mjf
977 1.1.6.2 mjf sd.sd_cken = bus_space_read_4(sc->sc_iot, pxa2x0_clkman_ioh,
978 1.1.6.2 mjf CLKMAN_CKEN);
979 1.1.6.2 mjf
980 1.1.6.2 mjf /*
981 1.1.6.2 mjf * Stop clocks to all units except to the memory controller, and
982 1.1.6.2 mjf * to the keypad controller if it is enabled as a wake-up source.
983 1.1.6.2 mjf */
984 1.1.6.2 mjf rv = CKEN_MEM;
985 1.1.6.2 mjf if ((sc->sc_wakeon & PXA2X0_WAKEUP_KEYNS_ALL) != 0)
986 1.1.6.2 mjf rv |= CKEN_KEY;
987 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_clkman_ioh, CLKMAN_CKEN, rv);
988 1.1.6.2 mjf
989 1.1.6.2 mjf /* Disable nRESET_OUT. */
990 1.1.6.2 mjf rv = bus_space_read_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PSLR);
991 1.1.6.2 mjf #define PSLR_SL_ROD (1<<20)
992 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PSLR,
993 1.1.6.2 mjf rv | PSLR_SL_ROD);
994 1.1.6.2 mjf
995 1.1.6.2 mjf /* Clear all reset status flags. */
996 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_RCSR,
997 1.1.6.2 mjf RCSR_GPR | RCSR_SMR | RCSR_WDR | RCSR_HWR);
998 1.1.6.2 mjf
999 1.1.6.2 mjf /* Stop 3/13MHz oscillator; do not float PCMCIA and chip-selects. */
1000 1.1.6.2 mjf rv = PCFR_OPDE;
1001 1.1.6.2 mjf if ((cputype & ~CPU_ID_XSCALE_COREREV_MASK) == CPU_ID_PXA27X)
1002 1.1.6.2 mjf /* Enable nRESET_GPIO as a GPIO reset input. */
1003 1.1.6.2 mjf rv |= PCFR_GPR_EN;
1004 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PCFR, rv);
1005 1.1.6.2 mjf
1006 1.1.6.2 mjf /* XXX C3000 */
1007 1.1.6.2 mjf #define GPIO_G0_STROBE_BIT 0x0f800000
1008 1.1.6.2 mjf #define GPIO_G1_STROBE_BIT 0x00100000
1009 1.1.6.2 mjf #define GPIO_G2_STROBE_BIT 0x01000000
1010 1.1.6.2 mjf #define GPIO_G3_STROBE_BIT 0x00041880
1011 1.1.6.2 mjf #define GPIO_KEY_STROBE0 88
1012 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR0,
1013 1.1.6.2 mjf 0x00144018);
1014 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR1,
1015 1.1.6.2 mjf 0x00ef0000);
1016 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR2,
1017 1.1.6.2 mjf 0x0121c000);
1018 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR3,
1019 1.1.6.2 mjf 0x00600000);
1020 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR0,
1021 1.1.6.2 mjf 0x00144018 & ~GPIO_G0_STROBE_BIT);
1022 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR1,
1023 1.1.6.2 mjf 0x00ef0000 & ~GPIO_G1_STROBE_BIT);
1024 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR2,
1025 1.1.6.2 mjf 0x0121c000 & ~GPIO_G2_STROBE_BIT);
1026 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR3,
1027 1.1.6.2 mjf 0x00600000 & ~GPIO_G3_STROBE_BIT);
1028 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PGSR2,
1029 1.1.6.2 mjf (0x0121c000 & ~GPIO_G2_STROBE_BIT) |
1030 1.1.6.2 mjf GPIO_BIT(GPIO_KEY_STROBE0));
1031 1.1.6.2 mjf
1032 1.1.6.2 mjf /* C3000 */
1033 1.1.6.2 mjf #define GPIO_EXT_BUS_READY 18
1034 1.1.6.2 mjf pxa2x0_gpio_set_function(GPIO_EXT_BUS_READY, GPIO_SET | GPIO_OUT);
1035 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR0, 0xd01c4418);
1036 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR1, 0xfcefbd21);
1037 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR2, 0x13a5ffff);
1038 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR3, 0x01e3e10c);
1039 1.1.6.2 mjf
1040 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PSPR,
1041 1.1.6.2 mjf (u_int32_t)&pxa2x0_cpu_resume - 0xc0200000 + 0xa0200000);
1042 1.1.6.2 mjf
1043 1.1.6.2 mjf pxa2x0_cpu_suspend();
1044 1.1.6.2 mjf
1045 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PSPR, 0);
1046 1.1.6.2 mjf
1047 1.1.6.2 mjf pxa2x0_clkman_config(CKEN_SSP|CKEN_PWM0|CKEN_PWM1, 1);
1048 1.1.6.2 mjf pxa2x0_clkman_config(CKEN_KEY, 0);
1049 1.1.6.2 mjf
1050 1.1.6.2 mjf #if 1
1051 1.1.6.2 mjf /* Clear all GPIO interrupt sources. */
1052 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GEDR0, 0xffffffff);
1053 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GEDR1, 0xffffffff);
1054 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GEDR2, 0xffffffff);
1055 1.1.6.2 mjf #endif
1056 1.1.6.2 mjf
1057 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR0, sd.sd_gpdr0);
1058 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR1, sd.sd_gpdr1);
1059 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR2, sd.sd_gpdr2);
1060 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER0, sd.sd_grer0);
1061 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER1, sd.sd_grer1);
1062 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER2, sd.sd_grer2);
1063 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER0, sd.sd_gfer0);
1064 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER1, sd.sd_gfer1);
1065 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER2, sd.sd_gfer2);
1066 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR0_L, sd.sd_gafr0_l);
1067 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR1_L, sd.sd_gafr1_l);
1068 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR2_L, sd.sd_gafr2_l);
1069 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR0_U, sd.sd_gafr0_u);
1070 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR1_U, sd.sd_gafr1_u);
1071 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR2_U, sd.sd_gafr2_u);
1072 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPSR0, sd.sd_gplr0 &
1073 1.1.6.2 mjf sd.sd_gpdr0);
1074 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPSR1, sd.sd_gplr1 &
1075 1.1.6.2 mjf sd.sd_gpdr1);
1076 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPSR2, sd.sd_gplr2 &
1077 1.1.6.2 mjf sd.sd_gpdr2);
1078 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPCR0, ~sd.sd_gplr0 &
1079 1.1.6.2 mjf sd.sd_gpdr0);
1080 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPCR1, ~sd.sd_gplr1 &
1081 1.1.6.2 mjf sd.sd_gpdr1);
1082 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPCR2, ~sd.sd_gplr2 &
1083 1.1.6.2 mjf sd.sd_gpdr2);
1084 1.1.6.2 mjf
1085 1.1.6.2 mjf /* PXA27x */
1086 1.1.6.2 mjf #if 0
1087 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GEDR3, 0xffffffff);
1088 1.1.6.2 mjf #endif
1089 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPDR3, sd.sd_gpdr3);
1090 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GRER3, sd.sd_grer3);
1091 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GFER3, sd.sd_gfer3);
1092 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR3_L, sd.sd_gafr3_l);
1093 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GAFR3_U, sd.sd_gafr3_u);
1094 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPSR3, sd.sd_gplr3 &
1095 1.1.6.2 mjf sd.sd_gpdr3);
1096 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_gpio_ioh, GPIO_GPCR3, ~sd.sd_gplr3 &
1097 1.1.6.2 mjf sd.sd_gpdr3);
1098 1.1.6.2 mjf
1099 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_memctl_ioh, MEMCTL_MECR,
1100 1.1.6.2 mjf sd.sd_mecr);
1101 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_memctl_ioh, MEMCTL_MCMEM(0),
1102 1.1.6.2 mjf sd.sd_mcmem0);
1103 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_memctl_ioh, MEMCTL_MCMEM(1),
1104 1.1.6.2 mjf sd.sd_mcmem1);
1105 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_memctl_ioh, MEMCTL_MCATT(0),
1106 1.1.6.2 mjf sd.sd_mcatt0);
1107 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_memctl_ioh, MEMCTL_MCATT(1),
1108 1.1.6.2 mjf sd.sd_mcatt1);
1109 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_memctl_ioh, MEMCTL_MCIO(0),
1110 1.1.6.2 mjf sd.sd_mcio0);
1111 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_memctl_ioh, MEMCTL_MCIO(1),
1112 1.1.6.2 mjf sd.sd_mcio1);
1113 1.1.6.2 mjf
1114 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, pxa2x0_clkman_ioh, CLKMAN_CKEN,
1115 1.1.6.2 mjf sd.sd_cken);
1116 1.1.6.2 mjf
1117 1.1.6.2 mjf write_icu(INTCTL_ICLR, sd.sd_iclr);
1118 1.1.6.2 mjf write_icu(INTCTL_ICCR, sd.sd_iccr);
1119 1.1.6.2 mjf write_icu(INTCTL_ICMR, sd.sd_icmr);
1120 1.1.6.2 mjf
1121 1.1.6.2 mjf if ((read_icu(INTCTL_ICIP) & 0x1) != 0)
1122 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PEDR, 0x1);
1123 1.1.6.2 mjf
1124 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSMR0, sd.sd_osmr0);
1125 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSMR1, sd.sd_osmr1);
1126 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSMR2, sd.sd_osmr2);
1127 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSMR3, sd.sd_osmr3);
1128 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSMR4, sd.sd_osmr4);
1129 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSMR5, sd.sd_osmr5);
1130 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OMCR4, sd.sd_omcr4);
1131 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OMCR5, sd.sd_omcr5);
1132 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSCR0, sd.sd_oscr0);
1133 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OSCR4, sd.sd_oscr4);
1134 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, ost_ioh, OST_OIER, sd.sd_oier);
1135 1.1.6.2 mjf
1136 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(sc->sc_iot, sc->sc_pm_ioh, PI2C_VOLTAGE_HIGH);
1137 1.1.6.2 mjf
1138 1.1.6.2 mjf /* Change to 208MHz run mode with fast-bus still disabled. */
1139 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 | CCCR_RUN_X16,
1140 1.1.6.2 mjf CLKCFG_F, &pxa2x0_memcfg);
1141 1.1.6.2 mjf delay(1); /* XXX is the delay long enough, and necessary at all? */
1142 1.1.6.2 mjf pxa27x_fastbus_run_mode(1, pxa2x0_memcfg.mdrefr_high);
1143 1.1.6.2 mjf
1144 1.1.6.2 mjf /* Change to 416MHz turbo mode with fast-bus enabled. */
1145 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 | CCCR_RUN_X16,
1146 1.1.6.2 mjf CLKCFG_B | CLKCFG_F | CLKCFG_T, &pxa2x0_memcfg);
1147 1.1.6.2 mjf
1148 1.1.6.2 mjf if (sc->sc_resume != NULL) {
1149 1.1.6.2 mjf if (!sc->sc_resume(sc))
1150 1.1.6.2 mjf goto suspend_again;
1151 1.1.6.2 mjf }
1152 1.1.6.2 mjf
1153 1.1.6.2 mjf /*
1154 1.1.6.2 mjf * Allow immediate entry into deep-sleep mode if power fails.
1155 1.1.6.2 mjf * Resume from immediate deep-sleep is not implemented yet.
1156 1.1.6.2 mjf */
1157 1.1.6.2 mjf bus_space_write_4(sc->sc_iot, sc->sc_pm_ioh, POWMAN_PMCR, 0);
1158 1.1.6.2 mjf
1159 1.1.6.2 mjf
1160 1.1.6.2 mjf restore_interrupts(save);
1161 1.1.6.2 mjf
1162 1.1.6.2 mjf #if 0
1163 1.1.6.2 mjf pxa2x0_setperf(perflevel);
1164 1.1.6.2 mjf #endif
1165 1.1.6.2 mjf
1166 1.1.6.2 mjf out:
1167 1.1.6.2 mjf if (ost_ioh != (bus_space_handle_t)0)
1168 1.1.6.2 mjf bus_space_unmap(sc->sc_iot, ost_ioh, PXA2X0_OST_SIZE);
1169 1.1.6.2 mjf }
1170 1.1.6.2 mjf
1171 1.1.6.2 mjf void
1172 1.1.6.2 mjf pxa2x0_pi2c_open(bus_space_tag_t iot, bus_space_handle_t ioh)
1173 1.1.6.2 mjf {
1174 1.1.6.2 mjf u_int32_t rv;
1175 1.1.6.2 mjf
1176 1.1.6.2 mjf /* Enable the I2C unit, and disable automatic voltage change. */
1177 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PCFR);
1178 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PCFR, rv | PCFR_PI2C_EN);
1179 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PCFR);
1180 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PCFR, rv & ~PCFR_FVC);
1181 1.1.6.2 mjf delay(1);
1182 1.1.6.2 mjf
1183 1.1.6.2 mjf /* Enable the clock to the power manager I2C unit. */
1184 1.1.6.2 mjf pxa2x0_clkman_config(CKEN_PI2C, 1);
1185 1.1.6.2 mjf delay(1);
1186 1.1.6.2 mjf }
1187 1.1.6.2 mjf
1188 1.1.6.2 mjf void
1189 1.1.6.2 mjf pxa2x0_pi2c_close(bus_space_tag_t iot, bus_space_handle_t ioh)
1190 1.1.6.2 mjf {
1191 1.1.6.2 mjf u_int32_t rv;
1192 1.1.6.2 mjf
1193 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_UR);
1194 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISAR, 0);
1195 1.1.6.2 mjf delay(1);
1196 1.1.6.2 mjf
1197 1.1.6.2 mjf /* Disable the clock to the power manager I2C unit. */
1198 1.1.6.2 mjf pxa2x0_clkman_config(CKEN_PI2C, 0);
1199 1.1.6.2 mjf delay(1);
1200 1.1.6.2 mjf
1201 1.1.6.2 mjf /* Disable the I2C unit, and disable automatic voltage change. */
1202 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PCFR);
1203 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PCFR,
1204 1.1.6.2 mjf rv & ~(PCFR_PI2C_EN | PCFR_FVC));
1205 1.1.6.2 mjf delay(1);
1206 1.1.6.2 mjf }
1207 1.1.6.2 mjf
1208 1.1.6.2 mjf int
1209 1.1.6.2 mjf pxa2x0_pi2c_read(bus_space_tag_t iot, bus_space_handle_t ioh,
1210 1.1.6.2 mjf u_char slave, u_char *valuep)
1211 1.1.6.2 mjf {
1212 1.1.6.2 mjf u_int32_t rv;
1213 1.1.6.2 mjf int timeout;
1214 1.1.6.2 mjf int tries = PI2C_RETRY_COUNT;
1215 1.1.6.2 mjf
1216 1.1.6.2 mjf retry:
1217 1.1.6.2 mjf
1218 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_UR);
1219 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISAR, 0x00);
1220 1.1.6.2 mjf delay(1);
1221 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_IUE | PICR_SCLE);
1222 1.1.6.2 mjf
1223 1.1.6.2 mjf /* Write slave device address. */
1224 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PIDBR, (slave<<1) | 0x1);
1225 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1226 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv | PICR_START);
1227 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1228 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv & ~PICR_STOP);
1229 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1230 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv | PICR_TB);
1231 1.1.6.2 mjf
1232 1.1.6.2 mjf timeout = 10000;
1233 1.1.6.2 mjf while ((bus_space_read_4(iot, ioh, POWMAN_PISR) & PISR_ITE) == 0) {
1234 1.1.6.2 mjf if (timeout-- == 0) {
1235 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_ITE);
1236 1.1.6.2 mjf goto err;
1237 1.1.6.2 mjf }
1238 1.1.6.2 mjf delay(1);
1239 1.1.6.2 mjf }
1240 1.1.6.2 mjf
1241 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_ITE);
1242 1.1.6.2 mjf
1243 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1244 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv & ~PICR_START);
1245 1.1.6.2 mjf
1246 1.1.6.2 mjf /* Read data value. */
1247 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1248 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv |
1249 1.1.6.2 mjf (PICR_STOP | PICR_ACKNAK));
1250 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1251 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv | PICR_TB);
1252 1.1.6.2 mjf
1253 1.1.6.2 mjf timeout = 10000;
1254 1.1.6.2 mjf while ((bus_space_read_4(iot, ioh, POWMAN_PISR) & PISR_IRF) == 0) {
1255 1.1.6.2 mjf if (timeout-- == 0) {
1256 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_IRF);
1257 1.1.6.2 mjf goto err;
1258 1.1.6.2 mjf }
1259 1.1.6.2 mjf delay(1);
1260 1.1.6.2 mjf }
1261 1.1.6.2 mjf
1262 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_IRF);
1263 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PIDBR);
1264 1.1.6.2 mjf *valuep = (u_char)rv;
1265 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1266 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv &
1267 1.1.6.2 mjf ~(PICR_STOP | PICR_ACKNAK));
1268 1.1.6.2 mjf
1269 1.1.6.2 mjf return (0);
1270 1.1.6.2 mjf err:
1271 1.1.6.2 mjf if (tries-- >= 0)
1272 1.1.6.2 mjf goto retry;
1273 1.1.6.2 mjf
1274 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_UR);
1275 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISAR, 0x00);
1276 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_IUE | PICR_SCLE);
1277 1.1.6.2 mjf
1278 1.1.6.2 mjf return (-EIO);
1279 1.1.6.2 mjf }
1280 1.1.6.2 mjf
1281 1.1.6.2 mjf int
1282 1.1.6.2 mjf pxa2x0_pi2c_write(bus_space_tag_t iot, bus_space_handle_t ioh,
1283 1.1.6.2 mjf u_char slave, u_char value)
1284 1.1.6.2 mjf {
1285 1.1.6.2 mjf u_int32_t rv;
1286 1.1.6.2 mjf int timeout;
1287 1.1.6.2 mjf int tries = PI2C_RETRY_COUNT;
1288 1.1.6.2 mjf
1289 1.1.6.2 mjf retry:
1290 1.1.6.2 mjf
1291 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_UR);
1292 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISAR, 0x00);
1293 1.1.6.2 mjf delay(1);
1294 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_IUE | PICR_SCLE);
1295 1.1.6.2 mjf
1296 1.1.6.2 mjf /* Write slave device address. */
1297 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PIDBR, (slave<<1));
1298 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1299 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv | PICR_START);
1300 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1301 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv & ~PICR_STOP);
1302 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1303 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv | PICR_TB);
1304 1.1.6.2 mjf
1305 1.1.6.2 mjf timeout = 10000;
1306 1.1.6.2 mjf while ((bus_space_read_4(iot, ioh, POWMAN_PISR) & PISR_ITE) == 0) {
1307 1.1.6.2 mjf if (timeout-- == 0) {
1308 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_ITE);
1309 1.1.6.2 mjf goto err;
1310 1.1.6.2 mjf }
1311 1.1.6.2 mjf delay(1);
1312 1.1.6.2 mjf }
1313 1.1.6.2 mjf if ((bus_space_read_4(iot, ioh, POWMAN_PISR) & PISR_ACKNAK) != 0)
1314 1.1.6.2 mjf goto err;
1315 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_ITE);
1316 1.1.6.2 mjf
1317 1.1.6.2 mjf /* Write data. */
1318 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1319 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv & ~PICR_START);
1320 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1321 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv | PICR_STOP);
1322 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PIDBR, value);
1323 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1324 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv | PICR_TB);
1325 1.1.6.2 mjf
1326 1.1.6.2 mjf timeout = 10000;
1327 1.1.6.2 mjf while ((bus_space_read_4(iot, ioh, POWMAN_PISR) & PISR_ITE) == 0) {
1328 1.1.6.2 mjf if (timeout-- == 0) {
1329 1.1.6.2 mjf #if 0
1330 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_ITE);
1331 1.1.6.2 mjf #endif
1332 1.1.6.2 mjf goto err;
1333 1.1.6.2 mjf }
1334 1.1.6.2 mjf delay(1);
1335 1.1.6.2 mjf }
1336 1.1.6.2 mjf if ((bus_space_read_4(iot, ioh, POWMAN_PISR) & PISR_ACKNAK) != 0)
1337 1.1.6.2 mjf goto err;
1338 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_ITE);
1339 1.1.6.2 mjf
1340 1.1.6.2 mjf rv = bus_space_read_4(iot, ioh, POWMAN_PICR);
1341 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, rv & ~PICR_STOP);
1342 1.1.6.2 mjf
1343 1.1.6.2 mjf return (0);
1344 1.1.6.2 mjf err:
1345 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISR, PISR_ITE);
1346 1.1.6.2 mjf if (tries-- >= 0)
1347 1.1.6.2 mjf goto retry;
1348 1.1.6.2 mjf
1349 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_UR);
1350 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PISAR, 0x00);
1351 1.1.6.2 mjf bus_space_write_4(iot, ioh, POWMAN_PICR, PICR_IUE | PICR_SCLE);
1352 1.1.6.2 mjf
1353 1.1.6.2 mjf return (-EIO);
1354 1.1.6.2 mjf }
1355 1.1.6.2 mjf
1356 1.1.6.2 mjf int
1357 1.1.6.2 mjf pxa2x0_pi2c_getvoltage(bus_space_tag_t iot, bus_space_handle_t ioh,
1358 1.1.6.2 mjf u_char *valuep)
1359 1.1.6.2 mjf {
1360 1.1.6.2 mjf int res;
1361 1.1.6.2 mjf
1362 1.1.6.2 mjf pxa2x0_pi2c_open(iot, ioh);
1363 1.1.6.2 mjf res = pxa2x0_pi2c_read(iot, ioh, 0x0c, valuep);
1364 1.1.6.2 mjf pxa2x0_pi2c_close(iot, ioh);
1365 1.1.6.2 mjf return (res);
1366 1.1.6.2 mjf }
1367 1.1.6.2 mjf
1368 1.1.6.2 mjf int
1369 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(bus_space_tag_t iot, bus_space_handle_t ioh,
1370 1.1.6.2 mjf u_char value)
1371 1.1.6.2 mjf {
1372 1.1.6.2 mjf int res;
1373 1.1.6.2 mjf
1374 1.1.6.2 mjf pxa2x0_pi2c_open(iot, ioh);
1375 1.1.6.2 mjf res = pxa2x0_pi2c_write(iot, ioh, 0x0c, value);
1376 1.1.6.2 mjf pxa2x0_pi2c_close(iot, ioh);
1377 1.1.6.2 mjf return (res);
1378 1.1.6.2 mjf }
1379 1.1.6.2 mjf
1380 1.1.6.2 mjf #if 0
1381 1.1.6.2 mjf void
1382 1.1.6.2 mjf pxa2x0_pi2c_print(struct pxa2x0_apm_softc *sc)
1383 1.1.6.2 mjf {
1384 1.1.6.2 mjf u_char value = 0;
1385 1.1.6.2 mjf
1386 1.1.6.2 mjf (void)pxa2x0_pi2c_getvoltage(sc->sc_iot, sc->sc_pm_ioh, &value);
1387 1.1.6.2 mjf printf("xscale core voltage: %s\n", value == PI2C_VOLTAGE_HIGH ?
1388 1.1.6.2 mjf "high" : (value == PI2C_VOLTAGE_LOW ? "low" : "unknown"));
1389 1.1.6.2 mjf }
1390 1.1.6.2 mjf #endif
1391 1.1.6.2 mjf
1392 1.1.6.2 mjf struct {
1393 1.1.6.2 mjf int maxspeed;
1394 1.1.6.2 mjf int numspeeds;
1395 1.1.6.2 mjf int hz [6];
1396 1.1.6.2 mjf int rate [6]; /* could this be simplfied by not having 100% in table? */
1397 1.1.6.2 mjf }
1398 1.1.6.2 mjf speedtables[] = {
1399 1.1.6.2 mjf { 91, 1, { 91 }, { 100 }},
1400 1.1.6.2 mjf { 208, 2, { 91, 208}, {50, 100}},
1401 1.1.6.2 mjf { 416, 3, { 91, 208, 416}, {25, 50, 100}},
1402 1.1.6.2 mjf { 520, 4, { 91, 208, 416, 520}, {18, 40 ,80, 100}},
1403 1.1.6.2 mjf { 624, 5, { 91, 208, 416, 520, 624}, {15, 34, 67, 82, 100}},
1404 1.1.6.2 mjf { 0 }
1405 1.1.6.2 mjf };
1406 1.1.6.2 mjf int xscale_maxspeed = 416; /* XXX */
1407 1.1.6.2 mjf
1408 1.1.6.2 mjf int speed_to_freq(int speed);
1409 1.1.6.2 mjf
1410 1.1.6.2 mjf int
1411 1.1.6.2 mjf speed_to_freq(int speed)
1412 1.1.6.2 mjf {
1413 1.1.6.2 mjf int i, j;
1414 1.1.6.2 mjf int newspeed = 0;
1415 1.1.6.2 mjf int numspeeds;
1416 1.1.6.2 mjf for (i = 0; speedtables[i].maxspeed != 0; i++) {
1417 1.1.6.2 mjf if (speedtables[i].maxspeed != xscale_maxspeed)
1418 1.1.6.2 mjf continue;
1419 1.1.6.2 mjf
1420 1.1.6.2 mjf if (speed <= speedtables[i].rate[0]) {
1421 1.1.6.2 mjf return speedtables[i].hz[0];
1422 1.1.6.2 mjf
1423 1.1.6.2 mjf }
1424 1.1.6.2 mjf numspeeds = speedtables[i].numspeeds;
1425 1.1.6.2 mjf if (speed == speedtables[i].rate[numspeeds-1]) {
1426 1.1.6.2 mjf return speedtables[i].hz[numspeeds-1];
1427 1.1.6.2 mjf }
1428 1.1.6.2 mjf for (j = 1; j < numspeeds; j++) {
1429 1.1.6.2 mjf if (speed < speedtables[i].rate[j]) {
1430 1.1.6.2 mjf return speedtables[i].hz[j-1];
1431 1.1.6.2 mjf }
1432 1.1.6.2 mjf }
1433 1.1.6.2 mjf }
1434 1.1.6.2 mjf return newspeed;
1435 1.1.6.2 mjf }
1436 1.1.6.2 mjf
1437 1.1.6.2 mjf
1438 1.1.6.2 mjf void
1439 1.1.6.2 mjf pxa2x0_setperf(int speed)
1440 1.1.6.2 mjf {
1441 1.1.6.2 mjf struct pxa2x0_apm_softc *sc;
1442 1.1.6.2 mjf int s;
1443 1.1.6.2 mjf int newfreq;
1444 1.1.6.2 mjf
1445 1.1.6.2 mjf sc = device_private(zapm_cd.cd_devs[0]);
1446 1.1.6.2 mjf
1447 1.1.6.2 mjf newfreq = speed_to_freq(speed);
1448 1.1.6.2 mjf
1449 1.1.6.2 mjf if (newfreq == 0) {
1450 1.1.6.2 mjf printf("bogus new frequency 0 for rate %d maxclock %d\n",
1451 1.1.6.2 mjf speed, xscale_maxspeed);
1452 1.1.6.2 mjf }
1453 1.1.6.2 mjf
1454 1.1.6.2 mjf DPRINTF(("setperf speed %d newfreq %d, maxfreq %d\n",
1455 1.1.6.2 mjf speed, newfreq, xscale_maxspeed));
1456 1.1.6.2 mjf
1457 1.1.6.2 mjf s = disable_interrupts(I32_bit|F32_bit);
1458 1.1.6.2 mjf
1459 1.1.6.2 mjf if (newfreq == 91) {
1460 1.1.6.2 mjf if (freq > 91) {
1461 1.1.6.2 mjf pxa27x_run_mode();
1462 1.1.6.2 mjf pxa27x_fastbus_run_mode(0, MDREFR_LOW);
1463 1.1.6.2 mjf pxa27x_cpu_speed_91();
1464 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(sc->sc_iot, sc->sc_pm_ioh,
1465 1.1.6.2 mjf PI2C_VOLTAGE_LOW);
1466 1.1.6.2 mjf freq = 91;
1467 1.1.6.2 mjf }
1468 1.1.6.2 mjf } else if (newfreq == 208) {
1469 1.1.6.2 mjf if (freq < 208)
1470 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(sc->sc_iot, sc->sc_pm_ioh,
1471 1.1.6.2 mjf PI2C_VOLTAGE_HIGH);
1472 1.1.6.2 mjf if (freq != 208) {
1473 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 |
1474 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_F, &pxa2x0_memcfg);
1475 1.1.6.2 mjf pxa27x_fastbus_run_mode(1, pxa2x0_memcfg.mdrefr_high);
1476 1.1.6.2 mjf freq = 208;
1477 1.1.6.2 mjf }
1478 1.1.6.2 mjf } else if (newfreq == 416) {
1479 1.1.6.2 mjf if (freq < 208) {
1480 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(sc->sc_iot, sc->sc_pm_ioh,
1481 1.1.6.2 mjf PI2C_VOLTAGE_HIGH);
1482 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 |
1483 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_F, &pxa2x0_memcfg);
1484 1.1.6.2 mjf pxa27x_fastbus_run_mode(1, pxa2x0_memcfg.mdrefr_high);
1485 1.1.6.2 mjf }
1486 1.1.6.2 mjf if (freq != 416) {
1487 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 |
1488 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_B | CLKCFG_F | CLKCFG_T,
1489 1.1.6.2 mjf &pxa2x0_memcfg);
1490 1.1.6.2 mjf freq = 416;
1491 1.1.6.2 mjf }
1492 1.1.6.2 mjf } else if (newfreq == 520) {
1493 1.1.6.2 mjf if (freq < 208) {
1494 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(sc->sc_iot, sc->sc_pm_ioh,
1495 1.1.6.2 mjf PI2C_VOLTAGE_HIGH);
1496 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 |
1497 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_F, &pxa2x0_memcfg);
1498 1.1.6.2 mjf pxa27x_fastbus_run_mode(1, pxa2x0_memcfg.mdrefr_high);
1499 1.1.6.2 mjf }
1500 1.1.6.2 mjf if (freq != 520) {
1501 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X25 |
1502 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_B | CLKCFG_F | CLKCFG_T,
1503 1.1.6.2 mjf &pxa2x0_memcfg);
1504 1.1.6.2 mjf freq = 520;
1505 1.1.6.2 mjf }
1506 1.1.6.2 mjf } else if (newfreq == 624) {
1507 1.1.6.2 mjf if (freq < 208) {
1508 1.1.6.2 mjf pxa2x0_pi2c_setvoltage(sc->sc_iot, sc->sc_pm_ioh,
1509 1.1.6.2 mjf PI2C_VOLTAGE_HIGH);
1510 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X2 |
1511 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_F, &pxa2x0_memcfg);
1512 1.1.6.2 mjf pxa27x_fastbus_run_mode(1, pxa2x0_memcfg.mdrefr_high);
1513 1.1.6.2 mjf }
1514 1.1.6.2 mjf if (freq != 624) {
1515 1.1.6.2 mjf pxa27x_frequency_change(CCCR_A | CCCR_TURBO_X3 |
1516 1.1.6.2 mjf CCCR_RUN_X16, CLKCFG_B | CLKCFG_F | CLKCFG_T,
1517 1.1.6.2 mjf &pxa2x0_memcfg);
1518 1.1.6.2 mjf freq = 624;
1519 1.1.6.2 mjf }
1520 1.1.6.2 mjf }
1521 1.1.6.2 mjf
1522 1.1.6.2 mjf restore_interrupts(s);
1523 1.1.6.2 mjf }
1524 1.1.6.2 mjf
1525 1.1.6.2 mjf int
1526 1.1.6.2 mjf pxa2x0_cpuspeed(int *freqp)
1527 1.1.6.2 mjf {
1528 1.1.6.2 mjf *freqp = freq;
1529 1.1.6.2 mjf return 0;
1530 1.1.6.2 mjf }
1531 1.1.6.2 mjf
1532 1.1.6.2 mjf void pxa2x0_maxspeed(int *speedp);
1533 1.1.6.2 mjf
1534 1.1.6.2 mjf void
1535 1.1.6.2 mjf pxa2x0_maxspeed(int *speedp)
1536 1.1.6.2 mjf {
1537 1.1.6.2 mjf /* XXX assumes a pxa270 */
1538 1.1.6.2 mjf
1539 1.1.6.2 mjf if (*speedp < 207) {
1540 1.1.6.2 mjf *speedp = 91;
1541 1.1.6.2 mjf } else if (*speedp < 415) {
1542 1.1.6.2 mjf *speedp = 208;
1543 1.1.6.2 mjf } else if (*speedp < 519) {
1544 1.1.6.2 mjf *speedp = 416;
1545 1.1.6.2 mjf } else if (*speedp < 624) {
1546 1.1.6.2 mjf *speedp = 520;
1547 1.1.6.2 mjf #if 0
1548 1.1.6.2 mjf } else if (*speedp < 651) {
1549 1.1.6.2 mjf *speedp = 624;
1550 1.1.6.2 mjf #endif
1551 1.1.6.2 mjf } else {
1552 1.1.6.2 mjf *speedp = 520; /* hope this is safe. */
1553 1.1.6.2 mjf }
1554 1.1.6.2 mjf xscale_maxspeed = *speedp;
1555 1.1.6.2 mjf #if 0
1556 1.1.6.2 mjf pxa2x0_setperf(perflevel);
1557 1.1.6.2 mjf #endif
1558 1.1.6.2 mjf }
1559