svn commit: r269199 - user/jceel/soc2014_evdev/head/sys/dev/usb/input
Jakub Wojciech Klama
jceel at FreeBSD.org
Mon Jul 28 22:10:16 UTC 2014
Author: jceel
Date: Mon Jul 28 22:10:16 2014
New Revision: 269199
URL: http://svnweb.freebsd.org/changeset/base/269199
Log:
Initial evdev support for uep(4).
Modified:
user/jceel/soc2014_evdev/head/sys/dev/usb/input/uep.c
Modified: user/jceel/soc2014_evdev/head/sys/dev/usb/input/uep.c
==============================================================================
--- user/jceel/soc2014_evdev/head/sys/dev/usb/input/uep.c Mon Jul 28 21:57:09 2014 (r269198)
+++ user/jceel/soc2014_evdev/head/sys/dev/usb/input/uep.c Mon Jul 28 22:10:16 2014 (r269199)
@@ -30,6 +30,8 @@
* http://home.eeti.com.tw/web20/drivers/Software%20Programming%20Guide_v2.0.pdf
*/
+#include "opt_evdev.h"
+
#include <sys/param.h>
#include <sys/bus.h>
#include <sys/callout.h>
@@ -51,6 +53,11 @@
#include <sys/fcntl.h>
#include <sys/tty.h>
+#ifdef EVDEV
+#include <dev/evdev/input.h>
+#include <dev/evdev/evdev.h>
+#endif
+
#define USB_DEBUG_VAR uep_debug
#include <dev/usb/usb_debug.h>
@@ -93,6 +100,11 @@ struct uep_softc {
u_int pollrate;
u_int state;
#define UEP_ENABLED 0x01
+#define UEP_EV_OPENED 0x02
+
+#ifdef EVDEV
+ struct evdev_dev *evdev;
+#endif
/* Reassembling buffer. */
u_char buf[UEP_PACKET_LEN_MAX];
@@ -110,6 +122,9 @@ static usb_fifo_cmd_t uep_stop_read;
static usb_fifo_open_t uep_open;
static usb_fifo_close_t uep_close;
+static evdev_open_t uep_ev_open;
+static evdev_close_t uep_ev_close;
+
static void uep_put_queue(struct uep_softc *, u_char *);
static struct usb_fifo_methods uep_fifo_methods = {
@@ -120,6 +135,11 @@ static struct usb_fifo_methods uep_fifo_
.basename[0] = "uep",
};
+static struct evdev_methods uep_evdev_methods = {
+ .ev_open = &uep_ev_open,
+ .ev_close = &uep_ev_close,
+};
+
static int
get_pkt_len(u_char *buf)
{
@@ -152,6 +172,7 @@ static void
uep_process_pkt(struct uep_softc *sc, u_char *buf)
{
int32_t x, y;
+ int touch;
if ((buf[0] & 0xFE) != 0x80) {
DPRINTF("bad input packet format 0x%.2x\n", buf[0]);
@@ -179,11 +200,19 @@ uep_process_pkt(struct uep_softc *sc, u_
*
*/
+ touch = buf[0] & (1 << 0);
x = (buf[1] << 7) | buf[2];
y = (buf[3] << 7) | buf[4];
DPRINTFN(2, "x %u y %u\n", x, y);
+#ifdef EVDEV
+ evdev_push_event(sc->evdev, EV_ABS, ABS_X, x);
+ evdev_push_event(sc->evdev, EV_ABS, ABS_Y, y);
+ evdev_push_event(sc->evdev, EV_KEY, BTN_TOUCH, !!touch);
+ evdev_sync(sc->evdev);
+#endif
+
uep_put_queue(sc, buf);
}
@@ -260,11 +289,17 @@ uep_intr_callback(struct usb_xfer *xfer,
case USB_ST_SETUP:
tr_setup:
/* check if we can put more data into the FIFO */
- if (usb_fifo_put_bytes_max(sc->fifo.fp[USB_FIFO_RX]) != 0) {
- usbd_xfer_set_frame_len(xfer, 0,
- usbd_xfer_max_len(xfer));
- usbd_transfer_submit(xfer);
- }
+ if (usb_fifo_put_bytes_max(sc->fifo.fp[USB_FIFO_RX]) == 0) {
+#ifdef EVDEV
+ if ((sc->state & UEP_EV_OPENED) == 0)
+ break;
+#else
+ break;
+#endif
+ }
+
+ usbd_xfer_set_frame_len(xfer, 0, usbd_xfer_max_len(xfer));
+ usbd_transfer_submit(xfer);
break;
default:
@@ -315,6 +350,9 @@ uep_attach(device_t dev)
struct usb_attach_arg *uaa = device_get_ivars(dev);
struct uep_softc *sc = device_get_softc(dev);
int error;
+#ifdef EVDEV
+ struct input_absinfo absinfo = { 0 };
+#endif
device_set_usb_desc(dev);
@@ -337,6 +375,29 @@ uep_attach(device_t dev)
goto detach;
}
+#ifdef EVDEV
+ sc->evdev = evdev_alloc();
+ evdev_set_name(sc->evdev, device_get_desc(dev));
+ evdev_set_serial(sc->evdev, "0");
+ evdev_set_softc(sc->evdev, sc);
+ evdev_set_methods(sc->evdev, &uep_evdev_methods);
+ evdev_support_event(sc->evdev, EV_SYN);
+ evdev_support_event(sc->evdev, EV_ABS);
+ evdev_support_event(sc->evdev, EV_KEY);
+ evdev_support_abs(sc->evdev, ABS_X);
+ evdev_support_abs(sc->evdev, ABS_Y);
+
+ absinfo.minimum = 0;
+ absinfo.maximum = UEP_MAX_X;
+ evdev_set_absinfo(sc->evdev, ABS_X, &absinfo);
+
+ absinfo.minimum = 0;
+ absinfo.maximum = UEP_MAX_Y;
+ evdev_set_absinfo(sc->evdev, ABS_Y, &absinfo);
+
+ evdev_register(dev, sc->evdev);
+#endif
+
sc->buf_len = 0;
return (0);
@@ -423,6 +484,36 @@ uep_close(struct usb_fifo *fifo, int ffl
}
}
+static void
+uep_ev_close(struct evdev_dev *evdev, void *ev_softc)
+{
+ struct uep_softc *sc = (struct uep_softc *)ev_softc;
+
+ mtx_lock(&sc->mtx);
+ usbd_transfer_stop(sc->xfer[UEP_INTR_DT]);
+ mtx_unlock(&sc->mtx);
+
+ sc->state &= ~(UEP_EV_OPENED);
+}
+
+static int
+uep_ev_open(struct evdev_dev *evdev, void *ev_softc)
+{
+ struct uep_softc *sc = (struct uep_softc *)ev_softc;
+
+ mtx_lock(&sc->mtx);
+
+ usbd_transfer_stop(sc->xfer[UEP_INTR_DT]);
+ usbd_xfer_set_interval(sc->xfer[UEP_INTR_DT], 100);
+ usbd_transfer_start(sc->xfer[UEP_INTR_DT]);
+
+ mtx_unlock(&sc->mtx);
+
+ sc->state |= UEP_EV_OPENED;
+
+ return (0);
+}
+
static devclass_t uep_devclass;
static device_method_t uep_methods[] = {
More information about the svn-src-user
mailing list