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