[psm] Workaround active PS/2 multiplexor hang

which happens on some laptops after returning to legacy multiplexing mode
at initialization stage.

PR:		242542
Reported by:	Felix Palmen <felix@palmen-it.de>
MFC after:	1 week
This commit is contained in:
Vladimir Kondratyev 2020-06-02 01:04:49 +00:00
parent 8137fb2e38
commit ec45be6c36
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=361718
2 changed files with 32 additions and 1 deletions

View File

@ -26,7 +26,7 @@
.\"
.\" $FreeBSD$
.\"
.Dd September 26, 2016
.Dd June 2, 2020
.Dt PSM 4
.Os
.Sh NAME
@ -361,6 +361,15 @@ the sysctl with the same name and by restarting
.Xr moused 8
using
.Pa /etc/rc.d/moused .
.Pp
Active multiplexing support can be disabled by setting
.Va hw.psm.mux_disabled
to
.Em 1
at boot-time.
This will prevent
.Nm
from enabling active multiplexing mode needed for some Synaptics touchpads.
.Sh IOCTLS
There are a few
.Xr ioctl 2

View File

@ -517,6 +517,7 @@ static int verbose = PSM_DEBUG;
static int synaptics_support = 1;
static int trackpoint_support = 1;
static int elantech_support = 1;
static int mux_disabled = 0;
/* for backward compatibility */
#define OLD_MOUSE_GETHWINFO _IOR('M', 1, old_mousehw_t)
@ -2989,6 +2990,9 @@ SYSCTL_INT(_hw_psm, OID_AUTO, trackpoint_support, CTLFLAG_RDTUN,
SYSCTL_INT(_hw_psm, OID_AUTO, elantech_support, CTLFLAG_RDTUN,
&elantech_support, 0, "Enable support for Elantech touchpads");
SYSCTL_INT(_hw_psm, OID_AUTO, mux_disabled, CTLFLAG_RDTUN,
&mux_disabled, 0, "Disable active multiplexing");
static void
psmintr(void *arg)
{
@ -6293,6 +6297,9 @@ enable_synaptics_mux(struct psm_softc *sc, enum probearg arg)
int active_ports_count = 0;
int active_ports_mask = 0;
if (mux_disabled != 0)
return (FALSE);
version = enable_aux_mux(kbdc);
if (version == -1)
return (FALSE);
@ -6330,6 +6337,21 @@ enable_synaptics_mux(struct psm_softc *sc, enum probearg arg)
/* IRQ handler does not support active multiplexing mode */
disable_aux_mux(kbdc);
/* Is MUX still alive after switching back to legacy mode? */
if (!enable_aux_dev(kbdc) || !disable_aux_dev(kbdc)) {
/*
* On some laptops e.g. Lenovo X121e dead AUX MUX can be
* brought back to life with resetting of keyboard.
*/
reset_kbd(kbdc);
if (!enable_aux_dev(kbdc) || !disable_aux_dev(kbdc)) {
printf("psm%d: AUX MUX hang detected!\n", sc->unit);
printf("Consider adding hw.psm.mux_disabled=1 to "
"loader tunables\n");
}
}
empty_both_buffers(kbdc, 10); /* remove stray data if any */
return (probe);
}