Hiding keyboard state
Peter Hutterer
peter.hutterer at who-t.net
Tue Dec 1 20:55:17 PST 2015
On Mon, Nov 23, 2015 at 11:04:10AM -0800, Keith Packard wrote:
>
> One of the many security holes in X is that any application can monitor
> the state of the keyboard device by querying the list of pressed keys on
> a regular basis. Here's a simple patch which makes that request report
> only key state which the client itself has already seen through X
> events.
>
> With this patch in place, grabbing the keyboard should be sufficient to
> hide key presses from other clients.
>
> I think we need to try to fix some of these issues, even if the fixes
> break existing applications. The next thing I'd like to try is to to
> deliver input events to only one client (owner first, then
> others). After that, apply the same rules to the input extension.
>
> In general, there are three areas that I'm wondering if we can fix:
>
> 1) input monitoring. This seems fairly "safe" as far as existing apps
> go.
>
> 2) output monitoring. This seems much harder as so many useful hacks
> and extensions take advantage of being able to get contents from
> other windows.
>
> 3) breaking screen saver security. We've got an extension, let's make
> it work.
>
> -keith
>
> From 627815391d2d6845f7e0a66d447c6b379be9d3cb Mon Sep 17 00:00:00 2001
> From: Keith Packard <keithp at keithp.com>
> Date: Mon, 23 Nov 2015 10:01:10 -0800
> Subject: [PATCH xserver] Track keystate per client for QueryKeymap
>
> This adds a per-client key state vector and uses that for
> ProcQueryKeymap instead of the device keymap.
>
> Signed-off-by: Keith Packard <keithp at keithp.com>
I _think_ this is correct, but you really want a lot of test cases for this
to make sure you're not missing out on any shortcuts the event delivery code
may take somewhere. I don't think there are any, but...
Reviewed-by: Peter Hutterer <peter.hutterer at who-t.net>
also, as I wrote in the other email this breaks syndaemon's
disable-while-typing feature, especially together with RECORD disabled.
Cheers,
Peter
> ---
> dix/devices.c | 2 +-
> dix/events.c | 13 +++++++++++++
> include/dixstruct.h | 1 +
> 3 files changed, 15 insertions(+), 1 deletion(-)
>
> diff --git a/dix/devices.c b/dix/devices.c
> index 9b0c7d2..49b6994 100644
> --- a/dix/devices.c
> +++ b/dix/devices.c
> @@ -2405,7 +2405,7 @@ ProcQueryKeymap(ClientPtr client)
> xQueryKeymapReply rep;
> int rc, i;
> DeviceIntPtr keybd = PickKeyboard(client);
> - CARD8 *down = keybd->key->down;
> + CARD8 *down = client->down;
>
> REQUEST_SIZE_MATCH(xReq);
> rep = (xQueryKeymapReply) {
> diff --git a/dix/events.c b/dix/events.c
> index efaf91d..4114471 100644
> --- a/dix/events.c
> +++ b/dix/events.c
> @@ -2006,6 +2006,19 @@ TryClientEvents(ClientPtr client, DeviceIntPtr dev, xEvent *pEvents,
> }
> }
>
> + /* Track keyboard state per client */
> + switch (type) {
> + case KeyPress:
> + SetBit(client->down, pEvents->u.u.detail);
> + break;
> + case KeyRelease:
> + ClearBit(client->down, pEvents->u.u.detail);
> + break;
> + case KeymapNotify:
> + memcpy(client->down+1, ((xKeymapEvent *) pEvents)->map, 31);
> + break;
> + }
> +
> if (BitIsOn(criticalEvents, type)) {
> if (client->smart_priority < SMART_MAX_PRIORITY)
> client->smart_priority++;
> diff --git a/include/dixstruct.h b/include/dixstruct.h
> index 8e70ae1..1e9f69e 100644
> --- a/include/dixstruct.h
> +++ b/include/dixstruct.h
> @@ -103,6 +103,7 @@ typedef struct _Client {
> unsigned short newKeyboardNotifyMask;
> unsigned short vMajor, vMinor;
> KeyCode minKC, maxKC;
> + CARD8 down[DOWN_LENGTH]; /* track key state for QueryKeymap */
>
> int smart_start_tick;
> int smart_stop_tick;
> --
> 2.6.1
More information about the xorg-devel
mailing list