From e0b34aa50f0cbc3a9b1ef9e9b9023619c7d0676c Mon Sep 17 00:00:00 2001 From: David du Colombier <0intro@gmail.com> Date: Sat, 18 May 2002 00:00:00 +0000 Subject: [PATCH] Plan 9 from Bell Labs 2002-05-18 --- bitsy/io.h | 25 +++---- bitsy/l.s | 189 +++++++++++++++++++++++++++++--------------------- bitsy/mem.h | 24 +++++++ bitsy/power.c | 16 +++-- bitsy/trap.c | 2 + 5 files changed, 156 insertions(+), 100 deletions(-) diff --git a/bitsy/io.h b/bitsy/io.h index 2c99d711d10178cca9912b81c264c0b7b8602c64..aa91760d8246dcf3650c3319395e8da0d7eb0193 100644 --- a/bitsy/io.h +++ b/bitsy/io.h @@ -254,26 +254,18 @@ extern MemConfRegs *memconfregs; */ /* Power management ops */ -enum { - PCFR_suspend = 1, - - PCFR_opde = 1, - PCFR_fp = 2, - PCFR_fs = 4, - PCFR_fo = 8, -}; typedef struct PowerRegs PowerRegs; struct PowerRegs { - ulong pmcr; /* Power manager control register */ - ulong pssr; /* Power manager sleep status register */ - ulong pspr; /* Power manager scratch pad register */ - ulong pwer; /* Power manager wakeup enable register */ - ulong pcfr; /* Power manager general configuration register */ - ulong ppcr; /* Power manager PPL configuration register */ - ulong pgsr; /* Power manager GPIO sleep state register */ - ulong posr; /* Power manager oscillator status register */ + ulong pmcr; /* 0x0 Power manager control register */ + ulong pssr; /* 0x4 Power manager sleep status register */ + ulong pspr; /* 0x8 Power manager scratch pad register */ + ulong pwer; /* 0xc Power manager wakeup enable register */ + ulong pcfr; /* 0x10 Power manager general configuration register */ + ulong ppcr; /* 0x14 Power manager PPL configuration register */ + ulong pgsr; /* 0x18 Power manager GPIO sleep state register */ + ulong posr; /* 0x1c Power manager oscillator status register */ }; extern PowerRegs *powerregs; @@ -287,7 +279,6 @@ enum RCSR_swr = 0x00000002, /* sw reset */ RCSR_wdr = 0x00000004, /* watch dog */ RCSR_smr = 0x00000008, /* sleep mode reset */ - RCSR_all = 0x0000000f, }; typedef struct ResetRegs ResetRegs; diff --git a/bitsy/l.s b/bitsy/l.s index 8ab29d04cf8c907c46c3cd01cb470cb740629f5c..53e82b6f7c90598f4c15d894c45ad2d26445f65c 100644 --- a/bitsy/l.s +++ b/bitsy/l.s @@ -509,9 +509,18 @@ TEXT setpowerlabel(SB), $-4 MOVW R3, 160(R0) MRC CpMMU, 0, R3, C(CpPID), C(0x0) MOVW R3, 164(R0) + /* usr */ + BIC $(PsrMask), R2, R3 + ORR $(0xdf), R3 + MOVW R3, CPSR + MOVW SPSR, R11 + MOVW R11, 168(R0) + MOVW R12, 172(R0) + MOVW R13, 176(R0) + MOVW R14, 180(R0) /* irq */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMirq), R3 + ORR $(0xd2), R3 MOVW R3, CPSR MOVW SPSR, R11 MOVW R11, 64(R0) @@ -520,7 +529,7 @@ TEXT setpowerlabel(SB), $-4 MOVW R14, 76(R0) /* und */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMund), R3 + ORR $(0xdb), R3 MOVW R3, CPSR MOVW SPSR, R11 MOVW R11, 80(R0) @@ -529,7 +538,7 @@ TEXT setpowerlabel(SB), $-4 MOVW R14, 92(R0) /* abt */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMabt), R3 + ORR $(0xd7), R3 MOVW R3, CPSR MOVW SPSR, R11 MOVW R11, 96(R0) @@ -538,7 +547,7 @@ TEXT setpowerlabel(SB), $-4 MOVW R14, 108(R0) /* fiq */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMfiq), R3 + ORR $(0xd1), R3 MOVW R3, CPSR MOVW SPSR, R7 MOVW R7, 112(R0) @@ -607,9 +616,17 @@ TEXT power_resume(SB), $-4 MOVW R0,R0 MOVW R0,R0 MOVW R0,R0 + /* usr */ + BIC $(PsrMask), R2, R3 + ORR $(0xdf), R3 + MOVW 168(R0), R11 + MOVW 172(R0), R12 + MOVW 176(R0), R13 + MOVW 180(R0), R14 + MOVW R11, SPSR /* irq */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMirq), R3 + ORR $(0xd2), R3 MOVW R3, CPSR MOVW 64(R0), R11 MOVW 68(R0), R12 @@ -618,7 +635,7 @@ TEXT power_resume(SB), $-4 MOVW R11, SPSR /* und */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMund), R3 + ORR $(0xdb), R3 MOVW R3, CPSR MOVW 80(R0), R11 MOVW 84(R0), R12 @@ -627,7 +644,7 @@ TEXT power_resume(SB), $-4 MOVW R11, SPSR /* abt */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMabt), R3 + ORR $(0xd7), R3 MOVW R3, CPSR MOVW 96(R0), R11 MOVW 100(R0), R12 @@ -636,7 +653,7 @@ TEXT power_resume(SB), $-4 MOVW R11, SPSR /* fiq */ BIC $(PsrMask), R2, R3 - ORR $(PsrDirq|PsrMfiq), R3 + ORR $(0xd1), R3 MOVW R3, CPSR MOVW 112(R0), R7 MOVW 116(R0), R8 @@ -677,83 +694,99 @@ TEXT power_down(SB), $-4 MOVW gpioregs+0(SB),R6 MOVW memconfregs+0(SB),R5 MOVW powerregs+0(SB),R3 - MOVW 0x1c(R5),R4 - ORR $0x30400000,R4 - AND $(~0xfff0),R4 - MOVW $0x80000003,R2 + + + /* wakeup on power | rtc */ + MOVW $(PWR_rtc|PWR_gpio0),R2 MOVW R2,0xc(R3) - MOVW $15,R2 - MOVW R2,0x4(R7) - MOVW $7,R2 + + /* clear reset status */ + MOVW $(RCSR_all), R2 + MOVW R2, 0x4(R7) + /* float */ + MOVW $(PCFR_opde|PCFR_fp|PCFR_fs), R2 MOVW R2,0x10(R3) + /* sleep state */ MOVW $0,R2 MOVW R2,0x18(R3) - MOVW $power_resume+0(SB),R2 -/* MOVW $0,R2 */ + /* set resume address (pspr)*/ + MOVW $resumeaddr+0(SB),R1 + MOVW 0x0(R1), R2 MOVW R2,0x8(R3) - MOVW $0,R2 - MOVW R2,0x4(R6) - MOVW 0x1c(R5),R2 - ORR $0x400000,R2 - MOVW R2,0x1c(R5) - MOVW $(90*206),R0 -l13: SUB $1,R0 - BGT l13 - MOVW powerregs+0(SB),R3 - MOVW $0,R2 - MOVW R2,20(R3) - MOVW $(90*206),R0 -l14: SUB $1,R0 - BGT l14 - MOVW powerregs+0(SB),R5 - ORR $0x80000000,R4,R6 - AND $(~0x80100000),R6,R11 - - MOVW memconfregs+0(SB),R3 - MOVW 0x0(R3),R12 - AND $(~0x30003),R12 - - MOVW 0x10(R3),R2 - AND $(~0x00030003),R2 - MOVW R2,0x10(R3) - MOVW 0x14(R3),R2 - AND $(~0x00030003),R2 - MOVW R2,0x14(R3) - MOVW 0x2c(R3),R2 - AND $(~0x00030003),R2 - MOVW R2,0x2c(R3) - MOVW R0,R0 - MOVW R0,R0 - MOVW R0,R0 - MOVW R0,R0 - MOVW R0,R0 - MOVW R0,R0 - MOVW R0,R0 - MOVW R0,R0 - MOVW R0,R0 - /* align this on a cache-line boundary */ - MOVW $1,R2 - MOVW R4,0x1c(R3) - MOVW R6,0x1c(R3) - MOVW R12,0x0(R3) - MOVW R11,0x1c(R3) - MOVW R2,0x0(R5) -xlloop: - B xlloop /* loop waiting for sleep */ - -/* The first instruction of this function needs to be on a cache-line - * boundary; to make this happen, it will be copied (in trap.c). - * - * Hibernate puts the machine into hibernation. - */ -TEXT _hibernate(SB), $-4 + BL cacheflush(SB) + + /* disable clock switching */ + MCR CpPWR, 0, R1, C(CpTest), C(0x2), 2 + + /* adjust mem timing */ + MOVW memconfregs+0(SB),R5 + MOVW 0x1c(R5), R2 + ORR $(MDREFR_k1db2), R2 + MOVW R2, 0x1c(R5) + + /* set PLL to lower speed w/ delay (ppcr = 0)*/ + MOVW powerregs+0(SB),R3 + MOVW $(120*206),R0 +l11: SUB $1,R0 + BGT l11 + MOVW $0, R2 + MOVW R2, 0x14(R3) + MOVW $(120*206),R0 +l12: SUB $1,R0 + BGT l12 + + /* setup registers for suspend procedure: + * 1. clear RT in mscx (R1, R7, R8) + * 2. clear DRI in mdrefr (R4) + * 3. set slfrsh in mdrefr (R6) + * 4. clear DE in mdcnfg (R9) + * 5. clear dram refresh (R10) + * 6. force sleep (R2) + */ + /* 1 */ + MOVW 0x10(R5), R2 + BIC $(MSC_rt), R2 + MOVW R2, R1 + MOVW 0x14(R5), R2 + BIC $(MSC_rt), R2 + MOVW R2, R7 + MOVW 0x2c(R5), R2 + BIC $(MSC_rt), R2 + MOVW R2, R8 + /* 2 */ + MOVW 0x1c(R5), R2 + BIC $(0xff00), R2 + BIC $(0x00f0), R2 + MOVW R2, R4 + /* 3 */ + ORR $(MDREFR_slfrsh), R2, R6 + /* 4 */ + MOVW 0x0(R5), R9 + BIC $(MDCFNG_de), R9, R9 + /* 5 */ + MOVW R4, R2 + BIC $(MDREFR_slfrsh), R2, R2 + BIC $(MDREFR_e1pin), R2, R2 + MOVW R2, R10 + /* 6 */ MOVW $1,R2 - MOVW R4,0x1c(R3) - MOVW R6,0x1c(R3) - MOVW R12,0x0(R3) - MOVW R11,0x1c(R3) - MOVW R2,0x0(R5) + + /* Follow the procedure */ + /* 1 */ + MOVW R1, 0x10(R5) + MOVW R7, 0x14(R5) + MOVW R8, 0x2c(R5) + /* 2 */ + MOVW R4, 0x1c(R5) + /* 3 */ + MOVW R6, 0x1c(R5) + /* 4 */ + MOVW R9, 0x0(R5) + /* 5 */ + MOVW R10, 0x1c(R5) + /* 6 */ + MOVW R2, 0x0(R3) slloop: B slloop /* loop waiting for sleep */ diff --git a/bitsy/mem.h b/bitsy/mem.h index c54d0aa33492427b5f448d638eaa3162304e4973..df4bc0f60094347888f175761f57058763c4be15 100644 --- a/bitsy/mem.h +++ b/bitsy/mem.h @@ -210,3 +210,27 @@ * H3650 specific definitions */ #define EGPIOREGS 0x49000000 /* Additional GPIO register */ + +/* Power management */ + +#define PWR_rtc 0x80000000 /* resume on RTC */ +#define PWR_gpio0 0x00000001 /* resume on power button */ + +#define RCSR_all 0x0000000f +#define PCFR_opde 0x00000001 /* oscillator power-down enable */ +#define PCFR_suspend 0x00000001 +#define PCFR_fp 0x00000002 /* float pcmcia */ +#define PCFR_fs 0x00000004 /* float static memory */ +#define PCFR_fo 0x00000008 + +#define MDREFR_k1db2 (1 << 22) +#define MDREFR_slfrsh 0x80000000 /* self refresh */ +#define MDREFR_e1pin (1 << 20) +#define MSC_rt 0x00030003 + +#define MDCNFG_de0 0x00000001 /* dram enable */ +#define MDCNFG_de1 0x00000002 +#define MDCNFG_de2 0x00000004 +#define MDCNFG_de3 0x00000008 +#define MDCFNG_de 0x0000000f +#define PMCR_sf 1 diff --git a/bitsy/power.c b/bitsy/power.c index 635bdf46b22542f688d79f68c76c50f3c21a8b33..4e75b03dc2f671235ffd6141a1ef1ea42e1f7e88 100644 --- a/bitsy/power.c +++ b/bitsy/power.c @@ -14,6 +14,7 @@ * it's only used by routines in l.s */ ulong power_state[200/4]; +ulong resumeaddr[1]; Rendez powerr; ulong powerflag = 0; /* set to start power-off sequence */ @@ -29,6 +30,7 @@ Intrregs savedintrregs; uchar *savedtext; + static void checkflash(void) { @@ -164,16 +166,20 @@ void deepsleep(void) { static int power_pl; ulong xsp, xlink, mecr; + extern void power_resume(void); power_pl = splhi(); xlink = getcallerpc(&xlink); + + *resumeaddr = (ulong) power_resume; +// *resumeaddr = nil; /* Power down */ irpower(0); audiopower(0); screenpower(0); µcpower(0); iprint("entering suspend mode, sp = 0x%lux, pc = 0x%lux, psw = 0x%ux\n", &xsp, xlink, power_pl); - dumpitall(); +// dumpitall(); delay(1000); uartpower(0); rs232power(0); @@ -189,7 +195,7 @@ deepsleep(void) { /* Turn off memory auto power */ // memconfregs->mdrefr &= ~0x30000000; - memconfregs->mecr = mecr; +// memconfregs->mecr = mecr; gpiorestore(gpioregs, &savedgpioregs); delay(50); @@ -206,10 +212,10 @@ deepsleep(void) { delay(100); xlink = getcallerpc(&xlink); iprint("\nresuming execution, sp = 0x%lux, pc = 0x%lux, psw = 0x%ux\n", &xsp, xlink, splhi()); - dumpitall(); +// dumpitall(); delay(1000); // irpower(1); - audiopower(1); +// audiopower(1); µcpower(1); screenpower(1); splx(power_pl); @@ -236,10 +242,10 @@ powerkproc(void*) deepsleep(); xlink1 = getcallerpc(&xlink1); -// iprint("deepsleep returned, pc = 0x%lux, sp = 0x%lux\n", xlink1, &xlink); delay(2000); +// iprint("deepsleep returned, pc = 0x%lux, sp = 0x%lux\n", xlink1, &xlink); powerflag = 0; } } diff --git a/bitsy/trap.c b/bitsy/trap.c index 3602ca91032f8b9cc37c5505372f5be64aaf6038..d2f1e4c58e4662c5e7ee2020ced25cd36476c3ad 100644 --- a/bitsy/trap.c +++ b/bitsy/trap.c @@ -71,8 +71,10 @@ trapinit(void) */ doze = xspanalloc(12*sizeof(long), 16, 0); memmove(doze, _doze, 12*sizeof(long)); +#ifdef notdef hibernate = xspanalloc(8*sizeof(long), 16, 0); memmove(hibernate, _hibernate, 8*sizeof(long)); +#endif wbflush(); /* use exception vectors at 0xFFFF0000 */