From 3e0dc7b3164038125187c79380eeaf63dc0145be Mon Sep 17 00:00:00 2001 From: takemura Date: Tue, 28 Dec 1999 03:15:16 +0000 Subject: [PATCH] VR41xx's PIU (Touch panel I/F unit) suport. Currently it emulates relative pointing device like mouse, but it should behave like an absolute pointing device. It needs more works in wsmouse side. --- sys/arch/hpcmips/conf/GENERIC | 16 +- sys/arch/hpcmips/conf/files.hpcmips | 7 +- sys/arch/hpcmips/vr/icureg.h | 4 +- sys/arch/hpcmips/vr/mra.c | 111 ++++++ sys/arch/hpcmips/vr/vrip.c | 4 +- sys/arch/hpcmips/vr/vrpiu.c | 554 ++++++++++++++++++++++++++++ sys/arch/hpcmips/vr/vrpiureg.h | 156 ++++++++ sys/arch/hpcmips/vr/vrpiuvar.h | 53 +++ 8 files changed, 892 insertions(+), 13 deletions(-) create mode 100644 sys/arch/hpcmips/vr/mra.c create mode 100644 sys/arch/hpcmips/vr/vrpiu.c create mode 100644 sys/arch/hpcmips/vr/vrpiureg.h create mode 100644 sys/arch/hpcmips/vr/vrpiuvar.h diff --git a/sys/arch/hpcmips/conf/GENERIC b/sys/arch/hpcmips/conf/GENERIC index ae51ed583df6..624bf4edc557 100644 --- a/sys/arch/hpcmips/conf/GENERIC +++ b/sys/arch/hpcmips/conf/GENERIC @@ -2,7 +2,7 @@ # Distribution kernel (any model) kernel config file # -# $NetBSD: GENERIC,v 1.18 1999/12/23 06:26:08 takemura Exp $ +# $NetBSD: GENERIC,v 1.19 1999/12/28 03:15:16 takemura Exp $ # include "arch/hpcmips/conf/std.hpcmips" @@ -101,13 +101,6 @@ options WSDISPLAY_DEFAULTSCREENS=4 #options FONT_VT220L8x8 options FONT_VT220L8x10 -# Workstation Console attachments -fb* at mainbus0 -wsdisplay* at fb? -wskbd* at vrkiu? mux 1 -#wsmouse* at pms? mux 0 - - vrip* at mainbus0 vrcmu* at vrip? addr 0x0b000060 size 0x20 vrbcu* at vrip? addr 0x0b000000 size 0x20 @@ -119,6 +112,13 @@ com* at vrip? addr 0x0c000000 size 0x20 intr 9 vrgiu* at vrip? addr 0x0b000100 size 0x20 intr 8 vrpmu* at vrip? addr 0x0b0000a0 size 0x20 intr 1 # power switch vrdsu* at vrip? addr 0x0b0000e0 size 0x08 +vrpiu* at vrip? addr 0x0b000120 size 0x1a0 intr 5 + +# Workstation Console attachments +fb* at mainbus0 +wsdisplay* at fb? +wskbd* at vrkiu? mux 1 +wsmouse* at vrpiu? mux 0 # # MC-R300 diff --git a/sys/arch/hpcmips/conf/files.hpcmips b/sys/arch/hpcmips/conf/files.hpcmips index 8f8556a75bbf..1614639189db 100644 --- a/sys/arch/hpcmips/conf/files.hpcmips +++ b/sys/arch/hpcmips/conf/files.hpcmips @@ -1,4 +1,4 @@ -# $NetBSD: files.hpcmips,v 1.12 1999/12/23 06:26:08 takemura Exp $ +# $NetBSD: files.hpcmips,v 1.13 1999/12/28 03:15:17 takemura Exp $ # maxpartitions must be first item in files.${ARCH}. maxpartitions 8 @@ -146,6 +146,11 @@ device vrdsu attach vrdsu at vrip file arch/hpcmips/vr/vrdsu.c vrdsu needs-flag +device vrpiu: wsmousedev +attach vrpiu at vrip +file arch/hpcmips/vr/vrpiu.c vrpiu +file arch/hpcmips/vr/mra.c vrpiu + # # TOSHIBA TX3912/3922 # diff --git a/sys/arch/hpcmips/vr/icureg.h b/sys/arch/hpcmips/vr/icureg.h index 7252f5922a81..b75ce9855d0b 100644 --- a/sys/arch/hpcmips/vr/icureg.h +++ b/sys/arch/hpcmips/vr/icureg.h @@ -1,4 +1,4 @@ -/* $NetBSD: icureg.h,v 1.1.1.1 1999/09/16 12:23:32 takemura Exp $ */ +/* $NetBSD: icureg.h,v 1.2 1999/12/28 03:15:17 takemura Exp $ */ /*- * Copyright (c) 1999 Shin Takemura. All rights reserved. @@ -60,7 +60,7 @@ #define SYSINT1_BAT (1<<0) /* Battery intr */ -#define PIUINT_REG_W 0x002 /* Level2 PIU intr reg */ +#define ICUPIUINT_REG_W 0x002 /* Level2 PIU intr reg */ #define MPIUINT_REG_W 0x00e /* Level2 Mask PIU intr reg */ #define PIUINT_PADCMD (1<<6) /* PIU command scan intr */ diff --git a/sys/arch/hpcmips/vr/mra.c b/sys/arch/hpcmips/vr/mra.c new file mode 100644 index 000000000000..9b10a47c5cc0 --- /dev/null +++ b/sys/arch/hpcmips/vr/mra.c @@ -0,0 +1,111 @@ +/* $NetBSD: mra.c,v 1.1 1999/12/28 03:15:18 takemura Exp $ */ + +/* + * Copyright (c) 1999 Shin Takemura All rights reserved. + * Copyright (c) 1999 PocketBSD Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#include +#include + +int mra_Y_AX1_BX2_C __P((int *y, int ys, int *x1, int x1s, int *x2, int x2s, + int n, int scale, int *a, int *b, int *c)); + +/* + * multiple regression analysis + * Y = AX1 + BX2 + C + */ +int +mra_Y_AX1_BX2_C(y, ys, x1, x1s, x2, x2s, n, scale, a, b, c) + int *y, ys, *x1, x1s, *x2, x2s, n, scale, *a, *b, *c; +{ + int i; + int64_t X1a, X2a, Ya; + int64_t X1X1s, X2X2s, X1X2s; + int64_t YYs, X1Ys, X2Ys; + int64_t S11, S22, S12; + int64_t SYY, S1Y, S2Y; + int64_t A, B, C, M; +#define AA(p, s, i) (*((long*)(((char*)(p)) + (s) * (i)))) +#define X1(i) AA(x1, x1s, i) +#define X2(i) AA(x2, x2s, i) +#define Y(i) AA(y, ys, i) + + /* + * get avarage and sum + */ + X1a = 0; X2a = 0; Ya = 0; + X1X1s = 0; X2X2s = 0; X1X2s = 0; + X1Ys = 0; X2Ys = 0; YYs = 0; + for (i = 0; i < n; i++) { + X1a += X1(i); + X2a += X2(i); + Ya += Y(i); + + X1X1s += X1(i) * X1(i); + X2X2s += X2(i) * X2(i); + X1X2s += X1(i) * X2(i); + + X1Ys += X1(i) * Y(i); + X2Ys += X2(i) * Y(i); + YYs += Y(i) * Y(i); + } + X1a /= n; X2a /= n; Ya /= n; + + S11 = X1X1s - n * X1a * X1a; + S22 = X2X2s - n * X2a * X2a; + S12 = X1X2s - n * X1a * X2a; + + SYY = YYs - n * Ya * Ya; + S1Y = X1Ys - n * X1a * Ya; + S2Y = X2Ys - n * X2a * Ya; + +#if 0 + printf("X1a=%d X2a=%d Ya=%d\n", (int)X1a, (int)X2a, (int)Ya); + printf("X1X1s=%d X2X2s=%d X1X2s=%d\n", (int)X1X1s, (int)X2X2s, (int)X1X2s); + printf("X1Ys=%d X2Ys=%d YYs=%d\n", (int)X1Ys, (int)X2Ys, (int)YYs); + printf("S11=%d S22=%d S12=%d\n", (int)S11, (int)S22, (int)S12); + printf("SYY=%d S1Y=%d S2Y=%d\n", (int)SYY, (int)S1Y, (int)S2Y); +#endif + + M = (S11 * S22 - S12 * S12); + if (M == 0) { + /* error */ + return -1; + } + + A = (S1Y * S22 - S2Y * S12) * scale / M; + B = (S2Y * S11 - S1Y * S12) * scale / M; + C = Ya - (A * X1a + B * X2a) / scale; + +#if 0 + printf("A=%d B=%d C=%d\n", (int)A, (int)B, (int)C); +#endif + *a = A; + *b = B; + *c = C; + + return (0); +} diff --git a/sys/arch/hpcmips/vr/vrip.c b/sys/arch/hpcmips/vr/vrip.c index fb887af1d907..1200e25d1c5d 100644 --- a/sys/arch/hpcmips/vr/vrip.c +++ b/sys/arch/hpcmips/vr/vrip.c @@ -1,4 +1,4 @@ -/* $NetBSD: vrip.c,v 1.3 1999/12/23 06:26:10 takemura Exp $ */ +/* $NetBSD: vrip.c,v 1.4 1999/12/28 03:15:18 takemura Exp $ */ /*- * Copyright (c) 1999 @@ -82,7 +82,7 @@ static struct intrhand { bus_addr_t ih_hreg; bus_addr_t ih_mhreg; } intrhand[MAX_LEVEL1] = { - [5] = { 0, 0, 0, 0, PIUINT_REG_W, MPIUINT_REG_W }, + [5] = { 0, 0, 0, 0, ICUPIUINT_REG_W, MPIUINT_REG_W }, [6] = { 0, 0, 0, 0, AIUINT_REG_W, MAIUINT_REG_W }, [7] = { 0, 0, 0, 0, KIUINT_REG_W, MKIUINT_REG_W }, [8] = { 0, 0, 0, 0, GIUINT_L_REG_W, MGIUINT_L_REG_W, GIUINT_H_REG_W, MGIUINT_H_REG_W }, diff --git a/sys/arch/hpcmips/vr/vrpiu.c b/sys/arch/hpcmips/vr/vrpiu.c new file mode 100644 index 000000000000..a4b0e426ff82 --- /dev/null +++ b/sys/arch/hpcmips/vr/vrpiu.c @@ -0,0 +1,554 @@ +/* $NetBSD: vrpiu.c,v 1.1 1999/12/28 03:15:18 takemura Exp $ */ + +/* + * Copyright (c) 1999 Shin Takemura All rights reserved. + * Copyright (c) 1999 PocketBSD Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +#include +#include +#include +#include + +#include +#include + +#include + +#include +#include +#include +#include + +/* + * contant and macro definitions + */ +#define VRPIUDEBUG +#ifdef VRPIUDEBUG +int vrpiu_debug = 0; +#define DPRINTF(arg) if (vrpiu_debug) printf arg; +#else +#define DPRINTF(arg) +#endif + +#define SCALE (1024*1024) + +/* + * data types + */ +/* struct vrpiu_softc is defined in vrpiuvar.h */ + +/* + * function prototypes + */ +static int vrpiumatch __P((struct device *, struct cfdata *, void *)); +static void vrpiuattach __P((struct device *, struct device *, void *)); + +static void vrpiu_write __P((struct vrpiu_softc *, int, unsigned short)); +static u_short vrpiu_read __P((struct vrpiu_softc *, int)); + +static int vrpiu_intr __P((void *)); +static void vrpiu_reset_param __P((struct vrpiu_softc *sc)); +static void vrpiu_timeout __P((void *)); +#ifdef DEBUG +static void vrpiu_dump_cntreg __P((unsigned int cmd)); +#endif + +static int vrpiu_enable __P((void *)); +static int vrpiu_ioctl __P((void *, u_long, caddr_t, int, struct proc *)); +static void vrpiu_disable __P((void *)); + +/* mra is defined in mra.c */ +int mra_Y_AX1_BX2_C __P((int *y, int ys, int *x1, int x1s, int *x2, int x2s, + int n, int scale, int *a, int *b, int *c)); + +/* + * static or global variables + */ +struct cfattach vrpiu_ca = { + sizeof(struct vrpiu_softc), vrpiumatch, vrpiuattach +}; + +const struct wsmouse_accessops vrpiu_accessops = { + vrpiu_enable, + vrpiu_ioctl, + vrpiu_disable, +}; + +/* + * function definitions + */ +static inline void +vrpiu_write(sc, port, val) + struct vrpiu_softc *sc; + int port; + unsigned short val; +{ + bus_space_write_2(sc->sc_iot, sc->sc_ioh, port, val); +} + +static inline u_short +vrpiu_read(sc, port) + struct vrpiu_softc *sc; + int port; +{ + return bus_space_read_2(sc->sc_iot, sc->sc_ioh, port); +} + +static int +vrpiumatch(parent, cf, aux) + struct device *parent; + struct cfdata *cf; + void *aux; +{ + return 1; +} + +static void +vrpiuattach(parent, self, aux) + struct device *parent; + struct device *self; + void *aux; +{ + struct vrpiu_softc *sc = (struct vrpiu_softc *)self; + struct vrip_attach_args *va = aux; + struct wsmousedev_attach_args wsmaa; + + bus_space_tag_t iot = va->va_iot; + bus_space_handle_t ioh; + + if (bus_space_map(iot, va->va_addr, 1, 0, &ioh)) { + printf(": can't map bus space\n"); + return; + } + + sc->sc_iot = iot; + sc->sc_ioh = ioh; + sc->sc_vrip = va->va_vc; + + /* + * disable device until vrpiu_enable called + */ + sc->sc_stat = VRPIU_STAT_DISABLE; + + vrpiu_reset_param(sc); +#if 1 + /* + * XXX, calibrate parameters + */ + { + static struct sample { + int xraw, yraw, x, y; + } D[] = { + /* samples got on my MC-R500 */ + { 502, 486, 320, 120 }, + { 55, 109, 0, 0 }, + { 54, 913, 0, 239 }, + { 973, 924, 639, 239 }, + { 975, 123, 639, 0 }, + }; + int s = sizeof(*D); + int n = sizeof(D)/s; + + sc->sc_prmxs = 640; + sc->sc_prmys = 240; + + if (mra_Y_AX1_BX2_C(&D->x, s, &D->xraw, s, &D->yraw, s, n, + SCALE, &sc->sc_prmax, &sc->sc_prmbx, + &sc->sc_prmcx) || + mra_Y_AX1_BX2_C(&D->y, s, &D->xraw, s, &D->yraw, s, n, + SCALE, &sc->sc_prmay, + &sc->sc_prmby, &sc->sc_prmcy)) { + printf(": MRA error"); + vrpiu_reset_param(sc); + } else { + DPRINTF(("Ax=%d Bx=%d Cx=%d\n", + sc->sc_prmax, sc->sc_prmbx, sc->sc_prmcx)); + DPRINTF(("Ay=%d By=%d Cy=%d\n", + sc->sc_prmay, sc->sc_prmby, sc->sc_prmcy)); + } + } +#endif + + /* install interrupt handler and enable interrupt */ + if (!(sc->sc_handler = + vrip_intr_establish(va->va_vc, va->va_intr, IPL_TTY, + vrpiu_intr, sc))) { + printf (": can't map interrupt line.\n"); + return; + } + + /* mask level2 interrupt, stop scan sequencer and mask clock to piu */ + vrpiu_disable(sc); + + printf("\n"); + + wsmaa.accessops = &vrpiu_accessops; + wsmaa.accesscookie = sc; + + /* + * attach the wsmouse + */ + sc->sc_wsmousedev = config_found(self, &wsmaa, wsmousedevprint); +} + +int +vrpiu_enable(v) + void *v; +{ + struct vrpiu_softc *sc = v; + int s; + unsigned int cnt; + + DPRINTF(("%s(%d): vrpiu_enable()\n", __FILE__, __LINE__)); + if (sc->sc_stat != VRPIU_STAT_DISABLE) + return EBUSY; + + /* supply clock to PIU */ + __vrcmu_supply(CMUMSKPIU, 1); + + /* Scan interval 0x7FF is maximum value */ + vrpiu_write(sc, PIUSIVL_REG_W, 0x7FF); + + s = spltty(); + + /* clear interrupt status */ + vrpiu_write(sc, PIUINT_REG_W, PIUINT_ALLINTR); + + /* Disable -> Standby */ + cnt = PIUCNT_PIUPWR | + PIUCNT_PIUMODE_COORDINATE | + PIUCNT_PADATSTART | PIUCNT_PADATSTOP; + vrpiu_write(sc, PIUCNT_REG_W, cnt); + + /* save pen status, touch or release */ + cnt = vrpiu_read(sc, PIUCNT_REG_W); + + /* Level2 interrupt register setting */ + vrip_intr_setmask2(sc->sc_vrip, sc->sc_handler, PIUINT_ALLINTR, 1); + + /* + * Enable scan sequencer operation + * Standby -> WaitPenTouch + */ + cnt |= PIUCNT_PIUSEQEN; + vrpiu_write(sc, PIUCNT_REG_W, cnt); + + /* transit status DISABLE -> TOUCH or RELEASE */ + sc->sc_stat = (cnt & PIUCNT_PENSTC) ? + VRPIU_STAT_TOUCH : VRPIU_STAT_RELEASE; + + sc->sc_timeout = 1; + + splx(s); + + return 0; +} + +void +vrpiu_disable(v) + void *v; +{ + struct vrpiu_softc *sc = v; + int s; + + DPRINTF(("%s(%d): vrpiu_disable()\n", __FILE__, __LINE__)); + + /* Set level2 interrupt register to mask interrupts */ + vrip_intr_setmask2(sc->sc_vrip, sc->sc_handler, PIUINT_ALLINTR, 0); + + sc->sc_stat = VRPIU_STAT_DISABLE; + + /* Disable scan sequencer operation and power off */ + vrpiu_write(sc, PIUCNT_REG_W, 0); + + /* mask clock to PIU */ + __vrcmu_supply(CMUMSKPIU, 1); + + s = spltty(); + if (!sc->sc_timeout) { + untimeout(vrpiu_timeout, sc); + } + splx(s); +} + +int +vrpiu_ioctl(v, cmd, data, flag, p) + void *v; + u_long cmd; + caddr_t data; + int flag; + struct proc *p; +{ + struct vrpiu_softc *sc = v; + + DPRINTF(("%s(%d): vrpiu_ioctl(%08lx)\n", __FILE__, __LINE__, cmd)); + + switch (cmd) { + case WSMOUSEIO_GTYPE: + *(u_int *)data = WSMOUSE_TYPE_PS2; + break; + + case WSMOUSEIO_SRES: + printf("%s(%d): WSMOUSRIO_SRES is not supported", + __FILE__, __LINE__); + break; + + default: + return (-1); + } + return (0); +} + +/* + * PIU interrupt handler. + */ +int +vrpiu_intr(arg) + void *arg; +{ + struct vrpiu_softc *sc = arg; + unsigned int cnt, i; + unsigned int intrstat, page; + int tpx0, tpx1, tpy0, tpy1; + int x, y, xraw, yraw; + + intrstat = vrpiu_read(sc, PIUINT_REG_W); + + if (sc->sc_stat == VRPIU_STAT_DISABLE) { + /* + * the device isn't enabled. just clear interrupt. + */ + vrpiu_write(sc, PIUINT_REG_W, intrstat); + return (0); + } + + page = (intrstat & PIUINT_OVP) ? 1 : 0; + if (intrstat & (PIUINT_PADPAGE0INTR | PIUINT_PADPAGE1INTR)) { + tpx0 = vrpiu_read(sc, PIUPB(page, 0)); + tpx1 = vrpiu_read(sc, PIUPB(page, 1)); + tpy0 = vrpiu_read(sc, PIUPB(page, 2)); + tpy1 = vrpiu_read(sc, PIUPB(page, 3)); + } + + if (intrstat & PIUINT_PADDLOSTINTR) { + page = page ? 0 : 1; + for (i = 0; i < 4; i++) + vrpiu_read(sc, PIUPB(page, i)); + } + + cnt = vrpiu_read(sc, PIUCNT_REG_W); +#ifdef DEBUG + if (vrpiu_debug) + vrpiu_dump_cntreg(cnt); +#endif + + /* clear interrupt status */ + vrpiu_write(sc, PIUINT_REG_W, intrstat); + +#if 0 + DPRINTF(("vrpiu_intr: OVP=%d", page)); + if (intrstat & PIUINT_PADCMDINTR) + DPRINTF((" CMD")); + if (intrstat & PIUINT_PADADPINTR) + DPRINTF((" A/D")); + if (intrstat & PIUINT_PADPAGE1INTR) + DPRINTF((" PAGE1")); + if (intrstat & PIUINT_PADPAGE0INTR) + DPRINTF((" PAGE0")); + if (intrstat & PIUINT_PADDLOSTINTR) + DPRINTF((" DLOST")); + if (intrstat & PIUINT_PENCHGINTR) + DPRINTF((" PENCHG")); + DPRINTF(("\n")); +#endif + if (cnt & PIUCNT_PENSTC) { + if (sc->sc_stat == VRPIU_STAT_RELEASE) { + /* + * pen touch + */ + DPRINTF(("PEN TOUCH\n")); + sc->sc_stat = VRPIU_STAT_TOUCH; + if (sc->sc_timeout) { + sc->sc_timeout = 0; + sc->sc_releasecount = 0; + timeout(vrpiu_timeout, sc, hz/3); + } + } + } else { + if (sc->sc_stat == VRPIU_STAT_TOUCH || + sc->sc_stat == VRPIU_STAT_DRAG) { + /* + * pen release + */ + DPRINTF(("RELEASE\n")); + sc->sc_stat = VRPIU_STAT_RELEASE; + if (!sc->sc_timeout) { + if (++sc->sc_releasecount == 2) { + untimeout(vrpiu_timeout, sc); + sc->sc_timeout = 1; + DPRINTF(("TAP!\n")); + /* button 0 DOWN */ + wsmouse_input(sc->sc_wsmousedev, + (1 << 0), + 0, 0, 0); + /* button 0 UP */ + wsmouse_input(sc->sc_wsmousedev, + 0, 0, 0, 0); + } + } + } + } + + if (intrstat & (PIUINT_PADPAGE0INTR | PIUINT_PADPAGE1INTR)) { + if (!((tpx0 & PIUPB_VALID) && (tpx1 & PIUPB_VALID) && + (tpy0 & PIUPB_VALID) && (tpy1 & PIUPB_VALID))) { + printf("vrpiu: internal error, data is not valid!\n"); + } else { + tpx0 &= PIUPB_PADDATA_MASK; + tpx1 &= PIUPB_PADDATA_MASK; + tpy0 &= PIUPB_PADDATA_MASK; + tpy1 &= PIUPB_PADDATA_MASK; +#define ISVALID(n, c, m) ((c) - (m) < (n) && (n) < (c) + (m)) + if (ISVALID(tpx0 + tpx1, 1024, 200) && + ISVALID(tpx0 + tpx1, 1024, 200)) { +#if 0 + DPRINTF(("%04x %04x %04x %04x\n", + tpx0, tpx1, tpy0, tpy1)); + DPRINTF(("%3d %3d (%4d %4d)->", tpx0, tpy0, + tpx0 + tpx1, tpy0 + tpy1); +#endif + xraw = tpy1 * 1024 / (tpy0 + tpy1); + yraw = tpx1 * 1024 / (tpx0 + tpx1); + DPRINTF(("%3d %3d", xraw, yraw)); + + x = (sc->sc_prmax*xraw + sc->sc_prmbx*yraw) / + SCALE + sc->sc_prmcx; + y = (sc->sc_prmay*xraw + sc->sc_prmby*yraw) / + SCALE + sc->sc_prmcy; + if (x < 0) x = 0; + if (y < 0) y = 0; + if (sc->sc_prmxs <= x) + x = sc->sc_prmxs - 1; + if (sc->sc_prmys <= y) + y = sc->sc_prmys - 1; + DPRINTF(("->%4d %4d", x, y)); + if (sc->sc_stat == VRPIU_STAT_TOUCH) { + sc->sc_stat = VRPIU_STAT_DRAG; + sc->sc_x = x; + sc->sc_y = y; + } else + if (sc->sc_stat == VRPIU_STAT_DRAG) { + DPRINTF((" delta %d %d", + x - sc->sc_x, y - sc->sc_y)); + wsmouse_input(sc->sc_wsmousedev, + 0, /* all buttons up */ + x - sc->sc_x, /* dx */ + y - sc->sc_y, /* dy */ + 0); /* dz */ + sc->sc_x = x; + sc->sc_y = y; + } + DPRINTF(("\n")); + } + } + } + + if (intrstat & PIUINT_PADDLOSTINTR) { + cnt |= PIUCNT_PIUSEQEN; + vrpiu_write(sc, PIUCNT_REG_W, cnt); + } + + return 0; +} + +void +vrpiu_reset_param(sc) + struct vrpiu_softc *sc; +{ + sc->sc_prmax = SCALE; + sc->sc_prmbx = 0; + sc->sc_prmcx = 0; + sc->sc_prmxs = PIUPB_PADDATA_MAX; + sc->sc_prmay = 0; + sc->sc_prmby = SCALE; + sc->sc_prmcy = 0; + sc->sc_prmys = PIUPB_PADDATA_MAX; +} + +void +vrpiu_timeout(arg) + void *arg; +{ + struct vrpiu_softc *sc = arg; + sc->sc_timeout = 1; +} + +#ifdef DEBUG +void +vrpiu_dump_cntreg(cnt) + unsigned int cnt; +{ + printf("%s", (cnt & PIUCNT_PENSTC) ? "Touch" : "Release"); + printf(" state="); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_CmdScan) + printf("CmdScan"); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_IntervalNextScan) + printf("IntervalNextScan"); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_PenDataScan) + printf("PenDataScan"); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_WaitPenTouch) + printf("WaitPenTouch"); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_RFU) + printf("???"); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_ADPortScan) + printf("ADPortScan"); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_Standby) + printf("Standby"); + if ((cnt & PIUCNT_PADSTATE_MASK) == PIUCNT_PADSTATE_Disable) + printf("Disable"); + if (cnt & PIUCNT_PADATSTOP) + printf(" AutoStop"); + if (cnt & PIUCNT_PADATSTART) + printf(" AutoStart"); + if (cnt & PIUCNT_PADSCANSTOP) + printf(" Stop"); + if (cnt & PIUCNT_PADSCANSTART) + printf(" Start"); + if (cnt & PIUCNT_PADSCANTYPE) + printf(" ScanPressure"); + if ((cnt & PIUCNT_PIUMODE_MASK) == PIUCNT_PIUMODE_ADCONVERTER) + printf(" A/D"); + if ((cnt & PIUCNT_PIUMODE_MASK) == PIUCNT_PIUMODE_COORDINATE) + printf(" Coordinate"); + if (cnt & PIUCNT_PIUSEQEN) + printf(" SeqEn"); + if ((cnt & PIUCNT_PIUPWR) == 0) + printf(" PowerOff"); + if ((cnt & PIUCNT_PADRST) == 0) + printf(" Reset"); + printf("\n"); +} +#endif diff --git a/sys/arch/hpcmips/vr/vrpiureg.h b/sys/arch/hpcmips/vr/vrpiureg.h new file mode 100644 index 000000000000..678b697658fc --- /dev/null +++ b/sys/arch/hpcmips/vr/vrpiureg.h @@ -0,0 +1,156 @@ +/* $NetBSD: vrpiureg.h,v 1.1 1999/12/28 03:15:18 takemura Exp $ */ + +/* + * Copyright (c) 1999 Shin Takemura All rights reserved. + * Copyright (c) 1999 PocketBSD Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +/* + * PIU (Touch panel interface unit) register definitions + */ + +#define PIUCNT_REG_W 0x002 /* PIU Control register */ +#define PIUCNT_PENSTC (1<<13) +#define PIUCNT_PADSTATE_MASK (0x7<<10) +#define PIUCNT_PADSTATE_SHIFT 10 +#define PIUCNT_PADSTATE_CmdScan (0x7<<10) +#define PIUCNT_PADSTATE_IntervalNextScan (0x6<<10) +#define PIUCNT_PADSTATE_PenDataScan (0x5<<10) +#define PIUCNT_PADSTATE_WaitPenTouch (0x4<<10) +#define PIUCNT_PADSTATE_RFU (0x3<<10) +#define PIUCNT_PADSTATE_ADPortScan (0x2<<10) +#define PIUCNT_PADSTATE_Standby (0x1<<10) +#define PIUCNT_PADSTATE_Disable (0x0<<10) +#define PIUCNT_PADATSTOP (1<<9) +#define PIUCNT_PADATSTART (1<<8) +#define PIUCNT_PADSCANSTOP (1<<7) +#define PIUCNT_PADSCANSTART (1<<6) +#define PIUCNT_PADSCANTYPE (1<<5) +#define PIUCNT_PIUMODE_MASK (0x3<<3) +#define PIUCNT_PIUMODE_ADCONVERTER (0x1<<3) +#define PIUCNT_PIUMODE_COORDINATE (0x0<<3) +#define PIUCNT_PIUSEQEN (1<<2) +#define PIUCNT_PIUPWR (1<<1) +#define PIUCNT_PADRST (1<<0) + +#define PIUINT_REG_W 0x004 /* PIU Interruptcause register */ +#define PIUINT_OVP (1<<15) +#define PIUINT_PADCMDINTR (1<<6) +#define PIUINT_PADADPINTR (1<<5) +#define PIUINT_PADPAGE1INTR (1<<4) +#define PIUINT_PADPAGE0INTR (1<<3) +#define PIUINT_PADDLOSTINTR (1<<2) +#define PIUINT_PENCHGINTR (1<<0) +#define PIUINT_ALLINTR (PIUINT_PADCMDINTR | \ + PIUINT_PADADPINTR | \ + PIUINT_PADPAGE1INTR | \ + PIUINT_PADPAGE0INTR | \ + PIUINT_PADDLOSTINTR | \ + PIUINT_PENCHGINTR) + +#define PIUSIVL_REG_W 0x006 /* PIU Data sampling interval register */ +#define PIUSIVL_SCANINTVAL_MASK 0x7FF +#define PIUSIVL_SCANINTVAL_UNIT 30 /* 30 us */ + +#define PIUSTBL_REG_W 0x008 /* PIU A/D converter start delay register*/ +#define PIUSTBL_STABLE_MASK 0x1F +#define PIUSTBL_STABLE_UNIT 30 /* 30 us */ + +#define PIUCMD_REG_W 0x00A /* PIU A/D command register */ +#define PIUCMD_STABLEON (1<<12) +#define PIUCMD_TPYEN_MASK (3<<10) +#define PIUCMD_TPY1_INPUT (0<<11) +#define PIUCMD_TPY1_OUTPUT (1<<11) +#define PIUCMD_TPY0_INPUT (0<<10) +#define PIUCMD_TPY0_OUTPUT (1<<10) +#define PIUCMD_TPXEN_MASK (3<<8) +#define PIUCMD_TPX1_INPUT (0<<9) +#define PIUCMD_TPX1_OUTPUT (1<<9) +#define PIUCMD_TPX0_INPUT (0<<8) +#define PIUCMD_TPX0_OUTPUT (1<<8) +#define PIUCMD_TPYD_MASK (3<<6) +#define PIUCMD_TPY1_LOW (0<<7) +#define PIUCMD_TPY1_HIGH (1<<7) +#define PIUCMD_TPY0_LOW (0<<6) +#define PIUCMD_TPY0_HIGH (1<<6) +#define PIUCMD_TPXD_MASK (3<<4) +#define PIUCMD_TPX1_LOW (0<<5) +#define PIUCMD_TPX1_HIGH (1<<5) +#define PIUCMD_TPX0_LOW (0<<4) +#define PIUCMD_TPX0_HIGH (1<<4) +#define PIUCMD_ADCMD_MASK 0xF +#define PIUCMD_STANBYREQ 0xF +#define PIUCMD_AUDIOIN 0x7 +#define PIUCMD_ADIN2 0x6 +#define PIUCMD_ADIN1 0x5 +#define PIUCMD_ADIN0 0x4 +#define PIUCMD_TPY1 0x3 +#define PIUCMD_TPY0 0x2 +#define PIUCMD_TPX1 0x1 +#define PIUCMD_TPX0 0x0 + +#define PIUASCN_REG_W 0x010 /* PIU A/D port scan register */ +#define PIUACN_TPPSCAN (1<<1) +#define PIUACN_ADPSSTART (1<<0) + +#define PIUAMSK_REG_W 0x012 /* PIU A/D scan mask register */ +#define PIUAMSK_ADINM3 (1<<7) +#define PIUAMSK_AUDIOM PIUAMSK_ADINM3 +#define PIUAMSK_ADINM2 (1<<6) +#define PIUAMSK_ADINM1 (1<<5) +#define PIUAMSK_ADINM0 (1<<4) +#define PIUAMSK_ADINMALL 0x70 +#define PIUAMSK_TPYM1 (1<<3) +#define PIUAMSK_TPYM0 (1<<2) +#define PIUAMSK_TPXM1 (1<<1) +#define PIUAMSK_TPXM0 (1<<0) +#define PIUAMSK_TPMALL 0xF0 + +#define PIUCIVL_REG_W 0x01E /* PIU Check interval register */ +#define PIUCIVL_CHKINTVAL_MASK 0x7FF + +#define PIUPB00_REG_W 0x180 /* PIU Page 0 Buffer 0 register */ +#define PIUPB01_REG_W 0x182 /* PIU Page 0 Buffer 1 register */ +#define PIUPB02_REG_W 0x184 /* PIU Page 0 Buffer 2 register */ +#define PIUPB03_REG_W 0x186 /* PIU Page 0 Buffer 3 register */ +#define PIUPB04_REG_W 0x19C /* PIU Page 0 Buffer 4 register */ +#define PIUPB10_REG_W 0x188 /* PIU Page 1 Buffer 0 register */ +#define PIUPB11_REG_W 0x18A /* PIU Page 1 Buffer 1 register */ +#define PIUPB12_REG_W 0x18C /* PIU Page 1 Buffer 2 register */ +#define PIUPB13_REG_W 0x18E /* PIU Page 1 Buffer 3 register */ +#define PIUPB14_REG_W 0x19E /* PIU Page 1 Buffer 4 register */ +#define PIUPB(page, n) (((n)<4) ? \ + (0x180 + (page) * 8 + (n) * 2) : \ + (0x19C + (page) * 2)) +#define PIUPB_VALID (1<<15) +#define PIUPB_PADDATA_MASK 0x3FF +#define PIUPB_PADDATA_MAX 0x3FF + +#define PIUAB0_REG_W 0x190 /* PIU A/D scan Buffer 0 register */ +#define PIUAB1_REG_W 0x192 /* PIU A/D scan Buffer 1 register */ +#define PIUAB2_REG_W 0x194 /* PIU A/D scan Buffer 2 register */ +#define PIUAB3_REG_W 0x196 /* PIU A/D scan Buffer 3 register */ +#define PIUAB_VALID (1<<15) +#define PIUAB_PADDATA_MASK 0x3FF diff --git a/sys/arch/hpcmips/vr/vrpiuvar.h b/sys/arch/hpcmips/vr/vrpiuvar.h new file mode 100644 index 000000000000..16b0f45cfb79 --- /dev/null +++ b/sys/arch/hpcmips/vr/vrpiuvar.h @@ -0,0 +1,53 @@ +/* $NetBSD: vrpiuvar.h,v 1.1 1999/12/28 03:15:19 takemura Exp $ */ + +/* + * Copyright (c) 1999 Shin Takemura All rights reserved. + * Copyright (c) 1999 PocketBSD Project. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ + +enum vrpiu_stat { + VRPIU_STAT_DISABLE, + VRPIU_STAT_RELEASE, + VRPIU_STAT_TOUCH, + VRPIU_STAT_DRAG, +}; + +struct vrpiu_softc { + struct device sc_dev; + bus_space_tag_t sc_iot; + bus_space_handle_t sc_ioh; + void *sc_handler; + vrip_chipset_tag_t *sc_vrip; + + enum vrpiu_stat sc_stat; + struct device *sc_wsmousedev; + int sc_x, sc_y; + int sc_timeout; + int sc_releasecount; + + /* correction parameters */ + int sc_prmax, sc_prmbx, sc_prmcx, sc_prmxs; + int sc_prmay, sc_prmby, sc_prmcy, sc_prmys; +};