Basically just copied from randr properties, with minor changes only.
Each device supports arbitrary properties that can be modified by clients.
Modifications to the properties are passed to the driver (if applicable) and
can then affect the configuration of the device.
Note that device properties are limited to a specific device. A property set
on a slave device does not migrate to the master.
This fixes a severe issue - when the client died the event mask didn't get
unregistered and a future event would dereference dangling pointers. By
storing the event masks in the resource system we can free them when the
client dies.
Using id = 0 only worked pre-MPX since XInput didn't allow XOpenDevice for the
core devices (0 and 1). Now we can now legally register for events so we may
overwrite our device-independent classes with the ones selected for the VCP.
So, increase the EMASKSIZE to MAX_DEVICES + 1 and use MAX_DEVICES as the ID
when we don't have a device.
Mixing usage where some parts of the code treated this field as a bitmask
and other parts as an array of card8 was wrong, and as the wire protocol
wanted bitmasks, it was less invasive to switch the newer counting code use
booleans.
Master devices track slave buttons by waiting for all slave buttons to be
released before delivering the release event to the client.
This also removes the state merging code in DeepCopyDeviceClasses -- that
code was changing master device state without delivering any events,
violating protocol invariants. The result will be that existing slave
button state which does not match the master will not be visible through the
master device. Fixing this would require that we synthesize events in this
function, which seems like a bad idea. Note that keyboards have the same
issue.
Signed-off-by: Daniel Stone <daniel@fooishbar.org>
Signed-off-by: Peter Hutterer <peter@cs.unisa.edu.au>
device->button->down used to be a 32-byte bitmask with one bit for each
button. This has changed into a 256-byte array, with one byte assigned for
each button. Some of the callers were still using this array as a bitmask
however, this is fixed with this patch.
Thanks to Keith Packard for pointing this out. See also:
http://lists.freedesktop.org/archives/xorg/2008-June/036202.html
Button events were mapped once in GetPointerEvents and then again in
UpdateDeviceState. While it might make sense to just fix up UpdateDeviceState,
it turns out to be better to leave the raw button number in the event because
DGA reports raw device events without button translation, and so when it calls
UpdateDeviceState, the button down counts get scrambled and buttons get stuck
down.
See also:
http://lists.freedesktop.org/archives/xorg/2008-June/036201.html
Signed-off-by: Peter Hutterer <peter@cs.unisa.edu.au>
The core protocol requires absolute values and it's a bit hard to get them if
we only have relative ones in the history. Switch the motion history to
absolute, and if we really need the relative values, we can probably generated
them from the abs. ones in the future.
Add each event to the master's MH as well as to the SDs. In the MD, store
min/max and the actual value. When retrieving the MH, rescale all coordinates
to the current coordinate range and only post those valuators that are
currently active on the device.
With the MD/SD device hierarchy we need control over the generation of the
motion history as well as the conversion later before posting it to the
client. So let's not let the drivers change it.
No x.org driver currently uses it anyway, linuxwacom doesn't either so dumping
it seems safe enough.
Event is always absolute, update the device's valuators (always absolute too),
and then change the deviceValuator event to reflect the device's reporting
mode.
We can't rely on GPE to update device->valuators->axisVal. If a SIGIO occurs
during event processing this may have incoherent results.
This reverts commit f6645ddbf7.
During GetPointerEvents (and others), we need to access the last coordinates
posted for this device from the driver (not as posted to the client!). Lastx/y
is ok if we only have two axes, but with more complex devices we also need to
transition between all other axes.
ABI break, recompile your input drivers.
The state field of the event must specify the state of the devices before the
event occured. With the code as it was, the state would also include the
event (e.g. state from a button press event would show the button as pressed)
Gathering the state before updating the device should fix this.
X.Org Bug 15934 <http://bugs.freedesktop.org/show_bug.cgi?id=15934>
When the opcode squash happened in the protocol, the processing vector got out
of sync for a few requests. As a result, client and server would interpret
requests differently, leading to a couple of BadLength problems.
After UpdateDeviceState, the device has the current position in absolute
coordinates, the event has the correct valuator data to be delivered to the
client.
This is better than the approach implemented with
8973a3f798 which disabled XI altogether for 1.x.
Instead, return a device list that resembles a traditional XI setup on pre XI
2.0 servers. If the client tries to open a device other than a floating SD,
return a BadDevice error.
Turns out some programs don't like this change. gnome-settings-daemon crashes
hard if you tell it that XI doesn't exist. So, tell them we have XI, but leave
the other change (the one that pretends no devices are available).
This reverts commit 8973a3f798.
Sorry. With the huge changes in the device handling I honestly don't know how
to support XI and XI2 alongside. So let's just pretend XI doesn't exist if a
client doesn't request it supporting XI2.
Remember the version the client sent to us, so we can adjust our replies
accordingly. This requires the client to use the {major|minor}Version fields
in the GetExtensionVersion request. However, they were padding before, so we
must assume they are garbage if nbytes is non-zero. If nbytes is zero, the
client is probably a new client and we can handle it correctly.
Some leftover code from the previously used alloc/free device classes left us
with a incorrect button count. So a button release didn't come through if
a different pointer was moved after the button press.
Rather than freeing/allocing classes each time the device capabilities need to
swap, store them in the devPrivates system.
When a class is unused, it is pushed into the devPrivates, and later recovered
when needed again. This saves us a lot of memory allocations/frees, admittedly
on the cost of some memory.
We don't free the class anymore, so just store the previous pointers, do the
memcpy from the SD and then restore the pointers.
Plugs a memleak too, before xkbInfo was never freed.
Setting it to NULL isn't correct either. The correct behaviour is to realloc
it to the size necessary (or newly alloc it/free it). Otherwise we have a
memleak.
XkbInitIndicatorMap (in XkbInitDevice) calls XkbFindSrvLedInfo. This accesses
the devices kbdfeed struct, which is all nice and dandy if it is NULL. When
copying the device classes however, kbdfeed may not be NULL and thus
XkbFindSrvLedInfo goes on its merry way to do whatever it does.
By copying kbdfeed first, we avoid XkbFSLI to reference the "old" kbdfeed
struct of the previous SD.
Blindly copying will override the focus setting of the master. If there's XI
applications running, they may set the SD focus, while leaving the
MD's focus as it was. In this case, after a class swap we still want to get
the MD's events to the same window as before.
Floating SDs are paired with themselves, so the paired device may not be a
proper keyboard or mouse. Put some extra checks in to avoid dereferencing a
nullpointer later.
Some pointer devices have key classes (e.g. MS Optical Desktop 2000). The
previous test was performed as Error if ptr -> keybd or keybd -> ptr. This
doesnt work with such devices. New test is Succeed if ptr->ptr or
keybd->keybd.
This is a significant shift in how input events are perceived. The common
approach was to treat a core event as a different entity than the XI event.
This could result in the XI event being delivered to a different client than
the core event. This doesn't work nicely if they come from the same device.
Instead, we treat an input event as a single event, that is delivered through
two separate APIs. So when delivering an event, we first try the XI event,
then the core event. If the window want's neither, we go to the parent and
repeat. Once either core or XI has been delivered, the processing stops.
Important: Different to the previous method, if a client registers for core
button events, the parent window will not get XI events. This should only
cause problems when you're mixing core and XI events, so don't do that!
Generic events don't fit into this yet, they cause me headaches.
This should restore the correct passive grab processing. When checking for
passive grabs, the core event is emulated and we check first for XI grabs on
the window, then for core grabs. Regardless of which event activates the grab,
the XI event is stored in the device's EQ.
When replaying the event, we take the XI event and replay it on the next
window, again including the emulation of the core event.
If two devices are attached to the same master device, pressing button 1 on
each of them leads to two button presses from the same device. Some apps
really don't like that.
So we just put a counter in place and only send the first press and the last
release.
The window ID includes the client ID anyway, so we might as well just look up
the client directly instead of trying to get the window first and the client
from the window.
This also fixes a possible issue with XACE. If the client had permission to
write on the client but not on the window, the previous approach would have
failed.
All the rest of XI uses rc and returns rc in case of error, so make
mpx-related stuff comply. This stops the rest of XI sending the error
manually.
This is just a cosmetic change to be in line with the rest.
This doesn't change much, as the struct previously given has the same size as
the ones now anyway. Still, we should be pendantic.
Thanks to Simon Thum for reporting.