summaryrefslogtreecommitdiff
path: root/sys/dev/wscons
diff options
context:
space:
mode:
authorchristos <christos@NetBSD.org>2006-02-10 17:33:01 +0000
committerchristos <christos@NetBSD.org>2006-02-10 17:33:01 +0000
commit0fa6ea2f2c3633e05e2b758dc33676189ea23b52 (patch)
tree0db9a53d5139f3d72a964348f3272f87bb057f7d /sys/dev/wscons
parent62bee0ffa526f24212494b128f96e49173903a60 (diff)
PR/32794: Paul Shupak: Panic in wsmouse code.
Checking the number of events after you've trashed the stack is not very useful. Instead, break out of the loop if we ran out, printing a message. Also don't try to inject 0 events; reset our state instead. Maybe having 0 events should be a diagnostic printf at this point? Anyway it is not nice having the kernel die because the mouse code got confused. Finally, explain why the array of events is sized funny.
Diffstat (limited to 'sys/dev/wscons')
-rw-r--r--sys/dev/wscons/wsmouse.c16
1 files changed, 10 insertions, 6 deletions
diff --git a/sys/dev/wscons/wsmouse.c b/sys/dev/wscons/wsmouse.c
index 8829f325d47..d23613eaedf 100644
--- a/sys/dev/wscons/wsmouse.c
+++ b/sys/dev/wscons/wsmouse.c
@@ -1,4 +1,4 @@
-/* $NetBSD: wsmouse.c,v 1.40 2006/02/07 09:13:02 jmmv Exp $ */
+/* $NetBSD: wsmouse.c,v 1.41 2006/02/10 17:33:01 christos Exp $ */
/*-
* Copyright (c) 2006 The NetBSD Foundation, Inc.
@@ -111,7 +111,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: wsmouse.c,v 1.40 2006/02/07 09:13:02 jmmv Exp $");
+__KERNEL_RCSID(0, "$NetBSD: wsmouse.c,v 1.41 2006/02/10 17:33:01 christos Exp $");
#include "wsmouse.h"
#include "wsdisplay.h"
@@ -346,6 +346,7 @@ wsmouse_input_xyzw(struct device *wsmousedev, u_int btns /* 0 is up */,
struct wsmouse_softc *sc = (struct wsmouse_softc *)wsmousedev;
struct wseventvar *evar;
int mb, ub, d, nevents;
+ /* one for each dimension (4) + a bit for each button */
struct wscons_event events[4 + sizeof(d) * 8];
/*
@@ -463,6 +464,12 @@ wsmouse_input_xyzw(struct device *wsmousedev, u_int btns /* 0 is up */,
btnno = ffs(d) - 1;
KASSERT(btnno >= 0);
+ if (nevents >= events / sizeof(events[0])) {
+ printf("%s: Event queue full (button status mb=0x%x"
+ " ub=0x%x\n", sc->sc_dev.dv_xname, mb, ub);
+ break;
+ }
+
events[nevents].type =
(mb & d) ? WSCONS_EVENT_MOUSE_DOWN : WSCONS_EVENT_MOUSE_UP;
events[nevents].value = btnno;
@@ -483,10 +490,7 @@ wsmouse_input_xyzw(struct device *wsmousedev, u_int btns /* 0 is up */,
}
}
- KASSERT(nevents > 0 &&
- nevents <= sizeof(events) / sizeof(struct wscons_event));
-
- if (wsevent_inject(evar, events, nevents) == 0) {
+ if (nevents == 0 || wsevent_inject(evar, events, nevents) == 0) {
/* All events were correctly injected into the queue.
* Synchronize the mouse's status with what the user
* has received. */