linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Dmitry Torokhov <dmitry.torokhov@gmail.com>
To: Damjan Jovanovic <damjan.jov@gmail.com>
Cc: Alessandro Rubini <rubini@cvml.unipv.it>,
	linux-kernel@vger.kernel.org, linux-input@vger.kernel.org,
	akpm@linux-foundation.org
Subject: Re: [PATCH] input: handle bad parity PS/2 packets in mouse drivers better
Date: Wed, 14 Apr 2010 13:59:59 -0700	[thread overview]
Message-ID: <20100414205959.GB11838@core.coreip.homeip.net> (raw)
In-Reply-To: <g2v9e89675b1004130429w6f6f9775u2e34d4727de706e@mail.gmail.com>

Hi Damjan,

On Tue, Apr 13, 2010 at 01:29:20PM +0200, Damjan Jovanovic wrote:
> This fixes a regression introduced in Linux 2.6.2 where mice that
> sporadically produce bad parity go crazy and start jumping around and
> clicking randomly, which never happens in any version of Windows
> running on the same hardware. The bugzilla bug is
> https://bugzilla.kernel.org/show_bug.cgi?id=6105
> 
> The patch works by always accumulating a full PS/2 packet, then
> ignoring the packet if any byte had a bad checksum. A month of testing
> it against an affected mouse has revealed it works perfectly in
> practice.
> 
> This is the third resend, also CC'ed to lkml and Andrew Morton this
> time, because the previous 2 emails to linux-input@vger.kernel.org and
> the input/mouse maintainers from 28 March 2010 were ignored.
> 

I am not sure whether we can rely on the mouse and KBC combo to always
finish transmitting entire packet when parity error is detected,
regardless of the protocol involved. However I had a chanceto observe
several versions of the $OTHER_OS in presence of parity errors and
they (at least when used with stock mouse driver) appear to simply
ignore errors and process motion data as usual. Therefore I propose
instead of your patch the patch below.

Could you please try it on your box and see if it helps?

Thanks.

-- 
Dmitry


Input: psmouse - ignore parity error for basic protocols

From: Dmitry Torokhov <dmitry.torokhov@gmail.com>

Observing behavior of the other OS it appears that parity errors reported
by the keyboard controller are being ignored and the data is processed
as usual. Let's do the same for standard PS/2 protocols (bare, Intellimouse
and Intellimouse Explorer) to provide better compatibility. Thsi should fix
teh following bug:

	https://bugzilla.kernel.org/show_bug.cgi?id=6105

Thanks for Damjan Jovanovic for locating the source of issue and ideas
for the patch.

Signed-off-by: Dmitry Torokhov <dtor@mail.ru>
---

 drivers/input/mouse/psmouse-base.c |   18 +++++++++++++++---
 drivers/input/mouse/psmouse.h      |    1 +
 2 files changed, 16 insertions(+), 3 deletions(-)


diff --git a/drivers/input/mouse/psmouse-base.c b/drivers/input/mouse/psmouse-base.c
index d8c0c8d..cbc8072 100644
--- a/drivers/input/mouse/psmouse-base.c
+++ b/drivers/input/mouse/psmouse-base.c
@@ -110,6 +110,7 @@ static struct workqueue_struct *kpsmoused_wq;
 struct psmouse_protocol {
 	enum psmouse_type type;
 	bool maxproto;
+	bool ignore_parity; /* Protocol should ignore parity errors from KBC */
 	const char *name;
 	const char *alias;
 	int (*detect)(struct psmouse *, bool);
@@ -288,7 +289,9 @@ static irqreturn_t psmouse_interrupt(struct serio *serio,
 	if (psmouse->state == PSMOUSE_IGNORE)
 		goto out;
 
-	if (flags & (SERIO_PARITY|SERIO_TIMEOUT)) {
+	if (unlikely((flags & SERIO_TIMEOUT) ||
+		     ((flags & SERIO_PARITY) && !psmouse->ignore_parity))) {
+
 		if (psmouse->state == PSMOUSE_ACTIVATED)
 			printk(KERN_WARNING "psmouse.c: bad data from KBC -%s%s\n",
 				flags & SERIO_TIMEOUT ? " timeout" : "",
@@ -759,6 +762,7 @@ static const struct psmouse_protocol psmouse_protocols[] = {
 		.name		= "PS/2",
 		.alias		= "bare",
 		.maxproto	= true,
+		.ignore_parity	= true,
 		.detect		= ps2bare_detect,
 	},
 #ifdef CONFIG_MOUSE_PS2_LOGIPS2PP
@@ -786,6 +790,7 @@ static const struct psmouse_protocol psmouse_protocols[] = {
 		.name		= "ImPS/2",
 		.alias		= "imps",
 		.maxproto	= true,
+		.ignore_parity	= true,
 		.detect		= intellimouse_detect,
 	},
 	{
@@ -793,6 +798,7 @@ static const struct psmouse_protocol psmouse_protocols[] = {
 		.name		= "ImExPS/2",
 		.alias		= "exps",
 		.maxproto	= true,
+		.ignore_parity	= true,
 		.detect		= im_explorer_detect,
 	},
 #ifdef CONFIG_MOUSE_PS2_SYNAPTICS
@@ -1222,6 +1228,7 @@ static void psmouse_disconnect(struct serio *serio)
 static int psmouse_switch_protocol(struct psmouse *psmouse,
 				   const struct psmouse_protocol *proto)
 {
+	const struct psmouse_protocol *selected_proto;
 	struct input_dev *input_dev = psmouse->dev;
 
 	input_dev->dev.parent = &psmouse->ps2dev.serio->dev;
@@ -1245,9 +1252,14 @@ static int psmouse_switch_protocol(struct psmouse *psmouse,
 			return -1;
 
 		psmouse->type = proto->type;
-	} else
+		selected_proto = proto;
+	} else {
 		psmouse->type = psmouse_extensions(psmouse,
 						   psmouse_max_proto, true);
+		selected_proto = psmouse_protocol_by_type(psmouse->type);
+	}
+
+	psmouse->ignore_parity = selected_proto->ignore_parity;
 
 	/*
 	 * If mouse's packet size is 3 there is no point in polling the
@@ -1267,7 +1279,7 @@ static int psmouse_switch_protocol(struct psmouse *psmouse,
 		psmouse->resync_time = 0;
 
 	snprintf(psmouse->devname, sizeof(psmouse->devname), "%s %s %s",
-		 psmouse_protocol_by_type(psmouse->type)->name, psmouse->vendor, psmouse->name);
+		 selected_proto->name, psmouse->vendor, psmouse->name);
 
 	input_dev->name = psmouse->devname;
 	input_dev->phys = psmouse->phys;
diff --git a/drivers/input/mouse/psmouse.h b/drivers/input/mouse/psmouse.h
index e053bdd..593e910 100644
--- a/drivers/input/mouse/psmouse.h
+++ b/drivers/input/mouse/psmouse.h
@@ -47,6 +47,7 @@ struct psmouse {
 	unsigned char pktcnt;
 	unsigned char pktsize;
 	unsigned char type;
+	bool ignore_parity;
 	bool acks_disable_command;
 	unsigned int model;
 	unsigned long last;

  reply	other threads:[~2010-04-14 21:00 UTC|newest]

Thread overview: 5+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <r2x9e89675b1004080434yfea09b06x2c3c4680a9437a9@mail.gmail.com>
2010-04-13 11:29 ` [PATCH] input: handle bad parity PS/2 packets in mouse drivers better Damjan Jovanovic
2010-04-14 20:59   ` Dmitry Torokhov [this message]
2010-04-17  9:33     ` Damjan Jovanovic
2010-05-03 11:31       ` Damjan Jovanovic
2010-05-05 16:24         ` Dmitry Torokhov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20100414205959.GB11838@core.coreip.homeip.net \
    --to=dmitry.torokhov@gmail.com \
    --cc=akpm@linux-foundation.org \
    --cc=damjan.jov@gmail.com \
    --cc=linux-input@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=rubini@cvml.unipv.it \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).