summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sys/dev/adb/adb.h18
-rw-r--r--sys/dev/adb/akbd.c229
-rw-r--r--sys/dev/adb/ams.c37
-rw-r--r--sys/dev/adb/keyboard.h30
4 files changed, 131 insertions, 183 deletions
diff --git a/sys/dev/adb/adb.h b/sys/dev/adb/adb.h
index e18e61cc0ea..e675281628f 100644
--- a/sys/dev/adb/adb.h
+++ b/sys/dev/adb/adb.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: adb.h,v 1.1 2006/01/18 23:21:17 miod Exp $ */
+/* $OpenBSD: adb.h,v 1.2 2006/02/12 18:06:23 miod Exp $ */
/* $NetBSD: adbsys.h,v 1.4 2000/12/19 02:59:24 tsubai Exp $ */
/*-
@@ -39,8 +39,6 @@
#ifdef _KERNEL
-#include <sys/time.h> /* timeval stuff */
-
/*
* Arguments used to attach a device to the Apple Desktop Bus
*/
@@ -57,22 +55,8 @@ struct adb_attach_args {
/* an ADB event */
typedef struct adb_event_s {
- int addr; /* device address */
- int hand_id; /* handler id */
- int def_addr; /* default address */
int byte_count; /* number of bytes */
unsigned char bytes[8]; /* bytes from register 0 */
- struct timeval timestamp; /* time event was acquired */
- union {
- struct adb_keydata_s {
- int key; /* ADB key code */
- } k;
- struct adb_mousedata_s {
- int dx; /* mouse delta x */
- int dy; /* mouse delta y */
- int buttons; /* buttons (down << (buttonnum)) */
- } m;
- } u; /* courtesy interpretation */
} adb_event_t;
/* Interesting default addresses */
diff --git a/sys/dev/adb/akbd.c b/sys/dev/adb/akbd.c
index 1b37910e2a0..2edf2e97f4f 100644
--- a/sys/dev/adb/akbd.c
+++ b/sys/dev/adb/akbd.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: akbd.c,v 1.2 2006/02/06 21:25:40 miod Exp $ */
+/* $OpenBSD: akbd.c,v 1.3 2006/02/12 18:06:24 miod Exp $ */
/* $NetBSD: akbd.c,v 1.17 2005/01/15 16:00:59 chs Exp $ */
/*
@@ -35,11 +35,6 @@
#include <sys/timeout.h>
#include <sys/kernel.h>
#include <sys/device.h>
-#include <sys/fcntl.h>
-#include <sys/poll.h>
-#include <sys/selinfo.h>
-#include <sys/proc.h>
-#include <sys/signalvar.h>
#include <sys/systm.h>
#include <dev/wscons/wsconsio.h>
@@ -62,13 +57,6 @@
*/
int akbdmatch(struct device *, void *, void *);
void akbdattach(struct device *, struct device *, void *);
-void kbd_adbcomplete(caddr_t, caddr_t, int);
-void kbd_processevent(adb_event_t *, struct akbd_softc *);
-#ifdef notyet
-u_char getleds(int);
-int setleds(struct akbd_softc *, u_char);
-void blinkleds(struct akbd_softc *);
-#endif
/* Driver definition. */
struct cfattach akbd_ca = {
@@ -78,11 +66,9 @@ struct cfdriver akbd_cd = {
NULL, "akbd", DV_DULL
};
-int akbd_enable(void *, int);
-void akbd_set_leds(void *, int);
-int akbd_ioctl(void *, u_long, caddr_t, int, struct proc *);
-int akbd_intr(adb_event_t *, struct akbd_softc *);
-void akbd_rawrepeat(void *v);
+int akbd_enable(void *, int);
+void akbd_set_leds(void *, int);
+int akbd_ioctl(void *, u_long, caddr_t, int, struct proc *);
struct wskbd_accessops akbd_accessops = {
@@ -100,15 +86,26 @@ struct wskbd_mapdata akbd_keymapdata = {
#endif
};
+void akbd_adbcomplete(caddr_t, caddr_t, int);
+void akbd_capslockwrapper(struct akbd_softc *, int);
+void akbd_input(struct akbd_softc *, int);
+void akbd_processevent(struct akbd_softc *, adb_event_t *);
+void akbd_rawrepeat(void *v);
+#ifdef notyet
+u_char getleds(int);
+int setleds(struct akbd_softc *, u_char);
+void blinkleds(struct akbd_softc *);
+#endif
+
int
akbdmatch(struct device *parent, void *vcf, void *aux)
{
struct adb_attach_args *aa_args = (struct adb_attach_args *)aux;
if (aa_args->origaddr == ADBADDR_KBD)
- return 1;
+ return (1);
else
- return 0;
+ return (0);
}
void
@@ -130,7 +127,7 @@ akbdattach(struct device *parent, struct device *self, void *aux)
sc->sc_leds = (u_int8_t)0x00; /* initially off */
- adbinfo.siServiceRtPtr = (Ptr)kbd_adbcomplete;
+ adbinfo.siServiceRtPtr = (Ptr)akbd_adbcomplete;
adbinfo.siDataAreaAddr = (caddr_t)sc;
printf(": ");
@@ -259,10 +256,10 @@ akbdattach(struct device *parent, struct device *self, void *aux)
* an ADB event record.
*/
void
-kbd_adbcomplete(caddr_t buffer, caddr_t data_area, int adb_command)
+akbd_adbcomplete(caddr_t buffer, caddr_t data_area, int adb_command)
{
adb_event_t event;
- struct akbd_softc *ksc;
+ struct akbd_softc *sc;
int adbaddr;
#ifdef ADB_DEBUG
int i;
@@ -272,52 +269,23 @@ kbd_adbcomplete(caddr_t buffer, caddr_t data_area, int adb_command)
#endif
adbaddr = ADB_CMDADDR(adb_command);
- ksc = (struct akbd_softc *)data_area;
+ sc = (struct akbd_softc *)data_area;
- event.addr = adbaddr;
- event.hand_id = ksc->handler_id;
- event.def_addr = ksc->origaddr;
event.byte_count = buffer[0];
memcpy(event.bytes, buffer + 1, event.byte_count);
#ifdef ADB_DEBUG
if (adb_debug) {
- printf("akbd: from %d at %d (org %d) %d:", event.addr,
- event.hand_id, event.def_addr, buffer[0]);
+ printf("akbd: from %d at %d (org %d) %d:", adbaddr,
+ sc->handler_id, sc->origaddr, buffer[0]);
for (i = 1; i <= buffer[0]; i++)
printf(" %x", buffer[i]);
printf("\n");
}
#endif
- microtime(&event.timestamp);
-
- kbd_processevent(&event, ksc);
-}
-
-/*
- * Given a keyboard ADB event, record the keycodes and call the key
- * repeat handler, optionally passing the event through the mouse
- * button emulation handler first.
- */
-void
-kbd_processevent(adb_event_t *event, struct akbd_softc *ksc)
-{
- adb_event_t new_event;
-
- new_event = *event;
- new_event.u.k.key = event->bytes[0];
- new_event.bytes[1] = 0xff;
- if (ksc->sc_wskbddev != NULL) /* wskbd is attached? */
- akbd_intr(&new_event, ksc);
- if (event->bytes[1] != 0xff) {
- new_event.u.k.key = event->bytes[1];
- new_event.bytes[0] = event->bytes[1];
- new_event.bytes[1] = 0xff;
- if (ksc->sc_wskbddev != NULL) /* wskbd is attached? */
- akbd_intr(&new_event, ksc);
- }
-
+ if (sc->sc_wskbddev != NULL)
+ akbd_processevent(sc, &event);
}
#ifdef notyet
@@ -348,16 +316,13 @@ getleds(int addr)
* actual keyboard register format
*/
int
-setleds(struct akbd_softc *ksc, u_char leds)
+setleds(struct akbd_softc *sc, u_char leds)
{
int addr;
short cmd;
u_char buffer[9];
- if ((leds & 0x07) == (ksc->sc_leds & 0x07))
- return (0);
-
- addr = ksc->adbaddr;
+ addr = sc->adbaddr;
buffer[0] = 0;
cmd = ADBTALK(addr, 2);
@@ -376,8 +341,6 @@ setleds(struct akbd_softc *ksc, u_char leds)
if (adb_op_sync((Ptr)buffer, (Ptr)0, (Ptr)0, cmd) || buffer[0] == 0)
return (EIO);
- ksc->sc_leds = ~((u_int8_t)buffer[2]) & 0x07;
-
if ((buffer[2] & 0xf8) != leds)
return (EIO);
else
@@ -388,27 +351,21 @@ setleds(struct akbd_softc *ksc, u_char leds)
* Toggle all of the LED's on and off, just for show.
*/
void
-blinkleds(struct akbd_softc *ksc)
+blinkleds(struct akbd_softc *sc)
{
- int addr, i;
- u_char blinkleds, origleds;
-
- addr = ksc->adbaddr;
- origleds = getleds(addr);
- blinkleds = LED_NUMLOCK | LED_CAPSLOCK | LED_SCROLL_LOCK;
-
- (void)setleds(ksc, blinkleds);
-
- for (i = 0; i < 10000; i++)
- delay(50);
-
- /* make sure that we restore the LED settings */
- i = 10;
- do {
- (void)setleds(ksc, (u_char)0x00);
- } while (setleds(ksc, (u_char)0x00) && (i-- > 0));
-
- return;
+ u_char origleds;
+
+ origleds = getleds(sc->adbaddr);
+ setleds(sc, LED_NUMLOCK | LED_CAPSLOCK | LED_SCROLL_LOCK);
+ delay(400000);
+ setleds(sc, origleds);
+
+ if (origleds & LED_NUMLOCK)
+ sc->sc_leds |= WSKBD_LED_NUM;
+ if (origleds & LED_CAPSLOCK)
+ sc->sc_leds |= WSKBD_LED_CAPS;
+ if (origleds & LED_SCROLL_LOCK)
+ sc->sc_leds |= WSKBD_LED_SCROLL;
}
#endif
@@ -421,14 +378,31 @@ akbd_enable(void *v, int on)
void
akbd_set_leds(void *v, int on)
{
+#ifdef notyet
+ struct akbd_softc *sc = v;
+ int leds;
+
+ if (sc->sc_extended) {
+ if (sc->sc_leds == on)
+ return;
+
+ leds = 0;
+ if (on & WSKBD_LED_NUM)
+ leds |= LED_NUMLOCK;
+ if (on & WSKBD_LED_CAPS)
+ leds |= LED_CAPSLOCK;
+ if (on & WSKBD_LED_SCROLL)
+ leds |= LED_SCROLL_LOCK;
+
+ setleds(sc, leds);
+ }
+#endif
}
int
akbd_ioctl(void *v, u_long cmd, caddr_t data, int flag, struct proc *p)
{
-#ifdef WSDISPLAY_COMPAT_RAWKBD
struct akbd_softc *sc = v;
-#endif
switch (cmd) {
@@ -436,9 +410,10 @@ akbd_ioctl(void *v, u_long cmd, caddr_t data, int flag, struct proc *p)
*(int *)data = WSKBD_TYPE_ADB;
return 0;
case WSKBDIO_SETLEDS:
+ akbd_set_leds(v, *(int *)data);
return 0;
case WSKBDIO_GETLEDS:
- *(int *)data = 0;
+ *(int *)data = sc->sc_leds;
return 0;
#ifdef WSDISPLAY_COMPAT_RAWKBD
case WSKBDIO_SETMODE:
@@ -475,35 +450,64 @@ akbd_rawrepeat(void *v)
}
#endif
-int adb_polledkey;
-int
-akbd_intr(adb_event_t *event, struct akbd_softc *sc)
+/*
+ * Given a keyboard ADB event, decode the keycodes and pass them to wskbd.
+ */
+void
+akbd_processevent(struct akbd_softc *sc, adb_event_t *event)
{
- int key, press, val;
- int type;
- static int shift;
+ switch (event->byte_count) {
+ case 1:
+ akbd_capslockwrapper(sc, event->bytes[0]);
+ break;
+ case 2:
+ /*
+ * The reset (or power) key sends 0x7f7f on press and
+ * 0xffff on release, and we ignore it.
+ */
+ if (event->bytes[0] == event->bytes[1] &&
+ ADBK_KEYVAL(event->bytes[0]) == ADBK_RESET)
+ break;
+ akbd_capslockwrapper(sc, event->bytes[0]);
+ akbd_capslockwrapper(sc, event->bytes[1]);
+ break;
+ default:
+#ifdef DIAGNOSTIC
+ printf("%s: unexpected message length %d\n",
+ sc->sc_dev.dv_xname, event->byte_count);
+#endif
+ break;
+ }
- key = event->u.k.key;
+}
+void
+akbd_capslockwrapper(struct akbd_softc *sc, int key)
+{
/*
- * Caps lock is weird. The key sequence generated is:
- * press: down(57) [57] (LED turns on)
- * release: up(127) [255]
- * press: up(127) [255]
- * release: up(57) [185] (LED turns off)
+ * Caps lock is special: since on earlier keyboards, the physical
+ * key stays down when pressed, we will get a notification of the
+ * key press, but not of the key release. Then, when it is pressed
+ * again, we will not get a notification of the key press, but will
+ * see the key release.
+ * For proper wskbd operation, we should report each capslock
+ * notification as both events (press and release).
*/
- if (ADBK_KEYVAL(key) == ADBK_CAPSLOCK)
- shift = 0;
-
- if (key == 255) {
- if (shift == 0) {
- key = ADBK_KEYUP(ADBK_CAPSLOCK);
- shift = 1;
- } else {
- key = ADBK_KEYDOWN(ADBK_CAPSLOCK);
- shift = 0;
- }
+ if (ADBK_KEYVAL(key) == ADBK_CAPSLOCK) {
+ akbd_input(sc, ADBK_KEYDOWN(ADBK_CAPSLOCK));
+ akbd_input(sc, ADBK_KEYUP(ADBK_CAPSLOCK));
+ } else {
+ if (key != 0xff)
+ akbd_input(sc, key);
}
+}
+
+int adb_polledkey;
+void
+akbd_input(struct akbd_softc *sc, int key)
+{
+ int press, val;
+ int type;
press = ADBK_PRESS(key);
val = ADBK_KEYVAL(key);
@@ -522,7 +526,7 @@ akbd_intr(adb_event_t *event, struct akbd_softc *sc)
c = keyboard[val][3];
if (c == 0) {
- return 0; /* XXX */
+ return; /* XXX */
}
if (c & 0x80)
cbuf[j++] = 0xe0;
@@ -543,11 +547,8 @@ akbd_intr(adb_event_t *event, struct akbd_softc *sc)
sc->sc_nrep = npress;
if (npress != 0)
timeout_add(&sc->sc_rawrepeat_ch, hz * REP_DELAY1/1000);
- return 0;
#endif
} else {
wskbd_input(sc->sc_wskbddev, type, val);
}
-
- return 0;
}
diff --git a/sys/dev/adb/ams.c b/sys/dev/adb/ams.c
index 114f5cebe98..a85db149ac5 100644
--- a/sys/dev/adb/ams.c
+++ b/sys/dev/adb/ams.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ams.c,v 1.2 2006/02/03 21:51:50 matthieu Exp $ */
+/* $OpenBSD: ams.c,v 1.3 2006/02/12 18:06:24 miod Exp $ */
/* $NetBSD: ams.c,v 1.11 2000/12/19 03:13:40 tsubai Exp $ */
/*
@@ -33,11 +33,6 @@
#include <sys/param.h>
#include <sys/device.h>
-#include <sys/fcntl.h>
-#include <sys/poll.h>
-#include <sys/selinfo.h>
-#include <sys/proc.h>
-#include <sys/signalvar.h>
#include <sys/systm.h>
#include <machine/autoconf.h>
@@ -423,24 +418,19 @@ ms_adbcomplete(caddr_t buffer, caddr_t data_area, int adb_command)
buffer[3] = 0x80;
}
- event.addr = adbaddr;
- event.hand_id = sc->handler_id;
- event.def_addr = sc->origaddr;
event.byte_count = buffer[0];
memcpy(event.bytes, buffer + 1, event.byte_count);
#ifdef ADB_DEBUG
if (adb_debug) {
- printf("ams: from %d at %d (org %d) %d:", event.addr,
- event.hand_id, event.def_addr, buffer[0]);
+ printf("ams: from %d at %d (org %d) %d:", adbaddr,
+ sc->handler_id, sc->origaddr, buffer[0]);
for (i = 1; i <= buffer[0]; i++)
printf(" %x", buffer[i]);
printf("\n");
}
#endif
- microtime(&event.timestamp);
-
ms_processevent(&event, sc);
}
@@ -451,10 +441,9 @@ ms_adbcomplete(caddr_t buffer, caddr_t data_area, int adb_command)
void
ms_processevent(adb_event_t *event, struct ams_softc *sc)
{
- adb_event_t new_event;
- int i, button_bit, max_byte, mask, buttons;
+ int i, button_bit, max_byte, mask;
+ int dx, dy, buttons;
- new_event = *event;
buttons = 0;
/*
@@ -463,7 +452,7 @@ ms_processevent(adb_event_t *event, struct ams_softc *sc)
*/
max_byte = event->byte_count;
button_bit = 1;
- switch (event->hand_id) {
+ switch (sc->handler_id) {
case ADBMS_USPEED:
case ADBMS_UCONTOUR:
/* MicroSpeed mouse and Contour mouse */
@@ -501,15 +490,15 @@ ms_processevent(adb_event_t *event, struct ams_softc *sc)
}
break;
}
- new_event.u.m.buttons = sc->sc_mb | buttons;
- new_event.u.m.dx = ((signed int) (event->bytes[1] & 0x3f)) -
- ((event->bytes[1] & 0x40) ? 64 : 0);
- new_event.u.m.dy = ((signed int) (event->bytes[0] & 0x3f)) -
- ((event->bytes[0] & 0x40) ? 64 : 0);
+
+ buttons |= sc->sc_mb;
+ dx = ((signed int) (event->bytes[1] & 0x3f)) -
+ ((event->bytes[1] & 0x40) ? 64 : 0);
+ dy = ((signed int) (event->bytes[0] & 0x3f)) -
+ ((event->bytes[0] & 0x40) ? 64 : 0);
if (sc->sc_wsmousedev)
- wsmouse_input(sc->sc_wsmousedev, new_event.u.m.buttons,
- new_event.u.m.dx, -new_event.u.m.dy, 0,
+ wsmouse_input(sc->sc_wsmousedev, buttons, dx, -dy, 0,
WSMOUSE_INPUT_DELTA);
}
diff --git a/sys/dev/adb/keyboard.h b/sys/dev/adb/keyboard.h
index ae158f92b63..b348cd5572b 100644
--- a/sys/dev/adb/keyboard.h
+++ b/sys/dev/adb/keyboard.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: keyboard.h,v 1.1 2006/01/18 23:21:17 miod Exp $ */
+/* $OpenBSD: keyboard.h,v 1.2 2006/02/12 18:06:24 miod Exp $ */
/* $NetBSD: keyboard.h,v 1.1 1998/05/15 10:15:54 tsubai Exp $ */
/*-
@@ -34,34 +34,8 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#define ADBK_LEFT 0x3B
-#define ADBK_RIGHT 0x3C
-#define ADBK_UP 0x3E
-#define ADBK_DOWN 0x3D
-#define ADBK_PGUP 0x74
-#define ADBK_PGDN 0x79
-#define ADBK_HOME 0x73
-#define ADBK_END 0x77
-#define ADBK_CONTROL 0x36
-#define ADBK_FLOWER 0x37
-#define ADBK_SHIFT 0x38
#define ADBK_CAPSLOCK 0x39
-#define ADBK_OPTION 0x3A
-#define ADBK_F 0x03
-#define ADBK_O 0x1F
-#define ADBK_P 0x23
-#define ADBK_Q 0x0C
-#define ADBK_V 0x09
-#define ADBK_1 0x12
-#define ADBK_2 0x13
-#define ADBK_3 0x14
-#define ADBK_4 0x15
-#define ADBK_5 0x17
-#define ADBK_6 0x16
-#define ADBK_7 0x1A
-#define ADBK_8 0x1C
-#define ADBK_9 0x19
-#define ADBK_0 0x1D
+#define ADBK_RESET 0x7f
#define ADBK_KEYVAL(key) ((key) & 0x7f)
#define ADBK_PRESS(key) (((key) & 0x80) == 0)