* ALPS touchpad PS/2 mouse driver
*
* Copyright (c) 2003 Neil Brown <neilb@cse.unsw.edu.au>
- * Copyright (c) 2003 Peter Osterlund <petero2@telia.com>
+ * Copyright (c) 2003-2005 Peter Osterlund <petero2@telia.com>
* Copyright (c) 2004 Dmitry Torokhov <dtor@mail.ru>
* Copyright (c) 2005 Vojtech Pavlik <vojtech@suse.cz>
*
{
struct alps_data *priv = psmouse->private;
unsigned char *packet = psmouse->packet;
- struct input_dev *dev = &psmouse->dev;
- struct input_dev *dev2 = &priv->dev2;
+ struct input_dev *dev = psmouse->dev;
+ struct input_dev *dev2 = priv->dev2;
int x, y, z, ges, fin, left, right, middle;
int back = 0, forward = 0;
input_report_key(dev, BTN_TOOL_FINGER, z > 0);
if (priv->i->flags & ALPS_WHEEL)
- input_report_rel(dev, REL_WHEEL, ((packet[0] >> 4) & 0x07) | ((packet[2] >> 2) & 0x08));
+ input_report_rel(dev, REL_WHEEL, ((packet[2] << 1) & 0x08) - ((packet[0] >> 4) & 0x07));
if (priv->i->flags & (ALPS_FW_BK_1 | ALPS_FW_BK_2)) {
input_report_key(dev, BTN_FORWARD, forward);
static int alps_reconnect(struct psmouse *psmouse)
{
struct alps_data *priv = psmouse->private;
- unsigned char param[4];
int version;
psmouse_reset(psmouse);
if (!(priv->i = alps_get_model(psmouse, &version)))
return -1;
- if (priv->i->flags & ALPS_PASS && alps_passthrough_mode(psmouse, 1))
+ if ((priv->i->flags & ALPS_PASS) && alps_passthrough_mode(psmouse, 1))
return -1;
- if (alps_get_status(psmouse, param))
+ if (alps_tap_mode(psmouse, 1)) {
+ printk(KERN_WARNING "alps.c: Failed to reenable hardware tapping\n");
return -1;
-
- if (!(param[0] & 0x04))
- alps_tap_mode(psmouse, 1);
+ }
if (alps_absolute_mode(psmouse)) {
- printk(KERN_ERR "alps.c: Failed to enable absolute mode\n");
+ printk(KERN_ERR "alps.c: Failed to reenable absolute mode\n");
return -1;
}
- if (priv->i->flags == ALPS_PASS && alps_passthrough_mode(psmouse, 0))
+ if ((priv->i->flags & ALPS_PASS) && alps_passthrough_mode(psmouse, 0))
return -1;
return 0;
static void alps_disconnect(struct psmouse *psmouse)
{
struct alps_data *priv = psmouse->private;
+
psmouse_reset(psmouse);
- input_unregister_device(&priv->dev2);
+ input_unregister_device(priv->dev2);
kfree(priv);
}
int alps_init(struct psmouse *psmouse)
{
struct alps_data *priv;
- unsigned char param[4];
+ struct input_dev *dev1 = psmouse->dev, *dev2;
int version;
- psmouse->private = priv = kmalloc(sizeof(struct alps_data), GFP_KERNEL);
- if (!priv)
+ psmouse->private = priv = kzalloc(sizeof(struct alps_data), GFP_KERNEL);
+ dev2 = input_allocate_device();
+ if (!priv || !dev2)
goto init_fail;
- memset(priv, 0, sizeof(struct alps_data));
+
+ priv->dev2 = dev2;
if (!(priv->i = alps_get_model(psmouse, &version)))
goto init_fail;
if ((priv->i->flags & ALPS_PASS) && alps_passthrough_mode(psmouse, 1))
goto init_fail;
- if (alps_get_status(psmouse, param)) {
- printk(KERN_ERR "alps.c: touchpad status report request failed\n");
- goto init_fail;
- }
-
- if (param[0] & 0x04) {
- printk(KERN_INFO "alps.c: Enabling hardware tapping\n");
- if (alps_tap_mode(psmouse, 1))
- printk(KERN_WARNING "alps.c: Failed to enable hardware tapping\n");
- }
+ if (alps_tap_mode(psmouse, 1))
+ printk(KERN_WARNING "alps.c: Failed to enable hardware tapping\n");
if (alps_absolute_mode(psmouse)) {
printk(KERN_ERR "alps.c: Failed to enable absolute mode\n");
if ((priv->i->flags & ALPS_PASS) && alps_passthrough_mode(psmouse, 0))
goto init_fail;
- psmouse->dev.evbit[LONG(EV_KEY)] |= BIT(EV_KEY);
- psmouse->dev.keybit[LONG(BTN_TOUCH)] |= BIT(BTN_TOUCH);
- psmouse->dev.keybit[LONG(BTN_TOOL_FINGER)] |= BIT(BTN_TOOL_FINGER);
- psmouse->dev.keybit[LONG(BTN_LEFT)] |= BIT(BTN_LEFT) | BIT(BTN_MIDDLE) | BIT(BTN_RIGHT);
+ dev1->evbit[LONG(EV_KEY)] |= BIT(EV_KEY);
+ dev1->keybit[LONG(BTN_TOUCH)] |= BIT(BTN_TOUCH);
+ dev1->keybit[LONG(BTN_TOOL_FINGER)] |= BIT(BTN_TOOL_FINGER);
+ dev1->keybit[LONG(BTN_LEFT)] |= BIT(BTN_LEFT) | BIT(BTN_MIDDLE) | BIT(BTN_RIGHT);
- psmouse->dev.evbit[LONG(EV_ABS)] |= BIT(EV_ABS);
- input_set_abs_params(&psmouse->dev, ABS_X, 0, 1023, 0, 0);
- input_set_abs_params(&psmouse->dev, ABS_Y, 0, 767, 0, 0);
- input_set_abs_params(&psmouse->dev, ABS_PRESSURE, 0, 127, 0, 0);
+ dev1->evbit[LONG(EV_ABS)] |= BIT(EV_ABS);
+ input_set_abs_params(dev1, ABS_X, 0, 1023, 0, 0);
+ input_set_abs_params(dev1, ABS_Y, 0, 767, 0, 0);
+ input_set_abs_params(dev1, ABS_PRESSURE, 0, 127, 0, 0);
if (priv->i->flags & ALPS_WHEEL) {
- psmouse->dev.evbit[LONG(EV_REL)] |= BIT(EV_REL);
- psmouse->dev.relbit[LONG(REL_WHEEL)] |= BIT(REL_WHEEL);
+ dev1->evbit[LONG(EV_REL)] |= BIT(EV_REL);
+ dev1->relbit[LONG(REL_WHEEL)] |= BIT(REL_WHEEL);
}
if (priv->i->flags & (ALPS_FW_BK_1 | ALPS_FW_BK_2)) {
- psmouse->dev.keybit[LONG(BTN_FORWARD)] |= BIT(BTN_FORWARD);
- psmouse->dev.keybit[LONG(BTN_BACK)] |= BIT(BTN_BACK);
+ dev1->keybit[LONG(BTN_FORWARD)] |= BIT(BTN_FORWARD);
+ dev1->keybit[LONG(BTN_BACK)] |= BIT(BTN_BACK);
}
sprintf(priv->phys, "%s/input1", psmouse->ps2dev.serio->phys);
- priv->dev2.phys = priv->phys;
- priv->dev2.name = (priv->i->flags & ALPS_DUALPOINT) ? "DualPoint Stick" : "PS/2 Mouse";
- priv->dev2.id.bustype = BUS_I8042;
- priv->dev2.id.vendor = 0x0002;
- priv->dev2.id.product = PSMOUSE_ALPS;
- priv->dev2.id.version = 0x0000;
-
- priv->dev2.evbit[0] = BIT(EV_KEY) | BIT(EV_REL);
- priv->dev2.relbit[LONG(REL_X)] |= BIT(REL_X) | BIT(REL_Y);
- priv->dev2.keybit[LONG(BTN_LEFT)] |= BIT(BTN_LEFT) | BIT(BTN_MIDDLE) | BIT(BTN_RIGHT);
+ dev2->phys = priv->phys;
+ dev2->name = (priv->i->flags & ALPS_DUALPOINT) ? "DualPoint Stick" : "PS/2 Mouse";
+ dev2->id.bustype = BUS_I8042;
+ dev2->id.vendor = 0x0002;
+ dev2->id.product = PSMOUSE_ALPS;
+ dev2->id.version = 0x0000;
- input_register_device(&priv->dev2);
+ dev2->evbit[0] = BIT(EV_KEY) | BIT(EV_REL);
+ dev2->relbit[LONG(REL_X)] |= BIT(REL_X) | BIT(REL_Y);
+ dev2->keybit[LONG(BTN_LEFT)] |= BIT(BTN_LEFT) | BIT(BTN_MIDDLE) | BIT(BTN_RIGHT);
- printk(KERN_INFO "input: %s on %s\n", priv->dev2.name, psmouse->ps2dev.serio->phys);
+ input_register_device(priv->dev2);
psmouse->protocol_handler = alps_process_byte;
psmouse->disconnect = alps_disconnect;
return 0;
init_fail:
+ input_free_device(dev2);
kfree(priv);
return -1;
}