aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/xterm.c154
1 files changed, 73 insertions, 81 deletions
diff --git a/src/xterm.c b/src/xterm.c
index 7b90f8b4816..ea0ddcd3be9 100644
--- a/src/xterm.c
+++ b/src/xterm.c
@@ -12850,6 +12850,72 @@ xi_handle_device_changed (struct x_display_info *dpyinfo,
12850#endif 12850#endif
12851} 12851}
12852 12852
12853/* Remove the client-side record of every device in TO_DISABLE.
12854 Called while processing XI_HierarchyChanged events. We batch up
12855 multiple disabled devices because it is more efficient to disable
12856 them at once. */
12857
12858static void
12859xi_disable_devices (struct x_display_info *dpyinfo,
12860 int *to_disable, int n_disabled)
12861{
12862 struct xi_device_t *devices;
12863 int ndevices, i, j;
12864#ifdef HAVE_XINPUT2_2
12865 struct xi_touch_point_t *tem, *last;
12866#endif
12867
12868 /* Don't pointlessly copy dpyinfo->devices if there are no devices
12869 to disable. */
12870 if (!n_disabled)
12871 return;
12872
12873 ndevices = 0;
12874 devices = xzalloc (sizeof *devices * dpyinfo->num_devices);
12875
12876 /* Loop through every device currently in DPYINFO, and copy it to
12877 DEVICES if it is not in TO_DISABLE. Note that this function
12878 should be called with input blocked, since xfree can otherwise
12879 call GC, which will call mark_xterm with invalid state. */
12880 for (i = 0; i < dpyinfo->num_devices; ++i)
12881 {
12882 for (j = 0; j < n_disabled; ++j)
12883 {
12884 if (to_disable[j] == dpyinfo->devices[i].device_id)
12885 {
12886 /* Free any scroll valuators that might be on this
12887 device. */
12888#ifdef HAVE_XINPUT2_1
12889 xfree (dpyinfo->devices[i].valuators);
12890#endif
12891
12892 /* Free any currently active touch points on this
12893 device. */
12894#ifdef HAVE_XINPUT2_2
12895 tem = dpyinfo->devices[i].touchpoints;
12896 while (tem)
12897 {
12898 last = tem;
12899 tem = tem->next;
12900 xfree (last);
12901 }
12902#endif
12903
12904 goto out;
12905 }
12906
12907 devices[ndevices++] = dpyinfo->devices[i];
12908 out:
12909 }
12910 }
12911
12912 /* Free the old devices array and replace it with ndevices. */
12913 xfree (dpyinfo->devices);
12914
12915 dpyinfo->devices = devices;
12916 dpyinfo->num_devices = ndevices;
12917}
12918
12853#endif 12919#endif
12854 12920
12855/* The focus may have changed. Figure out if it is a real focus change, 12921/* The focus may have changed. Figure out if it is a real focus change,
@@ -22361,11 +22427,8 @@ handle_one_xevent (struct x_display_info *dpyinfo,
22361 { 22427 {
22362 XIHierarchyEvent *hev = (XIHierarchyEvent *) xi_event; 22428 XIHierarchyEvent *hev = (XIHierarchyEvent *) xi_event;
22363 XIDeviceInfo *info; 22429 XIDeviceInfo *info;
22364 int i, j, ndevices, n_disabled, *disabled; 22430 int i, ndevices, n_disabled, *disabled;
22365 struct xi_device_t *device, *devices; 22431 struct xi_device_t *device;
22366#ifdef HAVE_XINPUT2_2
22367 struct xi_touch_point_t *tem, *last;
22368#endif
22369 22432
22370 disabled = SAFE_ALLOCA (sizeof *disabled * hev->num_info); 22433 disabled = SAFE_ALLOCA (sizeof *disabled * hev->num_info);
22371 n_disabled = 0; 22434 n_disabled = 0;
@@ -22376,45 +22439,8 @@ handle_one_xevent (struct x_display_info *dpyinfo,
22376 { 22439 {
22377 /* Handle all disabled devices now, to prevent 22440 /* Handle all disabled devices now, to prevent
22378 things happening out-of-order later. */ 22441 things happening out-of-order later. */
22379 if (n_disabled) 22442 xi_disable_devices (dpyinfo, disabled, n_disabled);
22380 { 22443 n_disabled = 0;
22381 ndevices = 0;
22382 devices = xzalloc (sizeof *devices * dpyinfo->num_devices);
22383
22384 for (i = 0; i < dpyinfo->num_devices; ++i)
22385 {
22386 for (j = 0; j < n_disabled; ++j)
22387 {
22388 if (disabled[j] == dpyinfo->devices[i].device_id)
22389 {
22390#ifdef HAVE_XINPUT2_1
22391 xfree (dpyinfo->devices[i].valuators);
22392#endif
22393#ifdef HAVE_XINPUT2_2
22394 tem = dpyinfo->devices[i].touchpoints;
22395 while (tem)
22396 {
22397 last = tem;
22398 tem = tem->next;
22399 xfree (last);
22400 }
22401#endif
22402 goto continue_detachment;
22403 }
22404 }
22405
22406 devices[ndevices++] = dpyinfo->devices[i];
22407
22408 continue_detachment:
22409 continue;
22410 }
22411
22412 xfree (dpyinfo->devices);
22413 dpyinfo->devices = devices;
22414 dpyinfo->num_devices = ndevices;
22415
22416 n_disabled = 0;
22417 }
22418 22444
22419 x_catch_errors (dpyinfo->display); 22445 x_catch_errors (dpyinfo->display);
22420 info = XIQueryDevice (dpyinfo->display, hev->info[i].deviceid, 22446 info = XIQueryDevice (dpyinfo->display, hev->info[i].deviceid,
@@ -22461,43 +22487,9 @@ handle_one_xevent (struct x_display_info *dpyinfo,
22461 } 22487 }
22462 } 22488 }
22463 22489
22464 if (n_disabled) 22490 /* Delete all devices that were disabled by this
22465 { 22491 event. */
22466 ndevices = 0; 22492 xi_disable_devices (dpyinfo, disabled, n_disabled);
22467 devices = xzalloc (sizeof *devices * dpyinfo->num_devices);
22468
22469 for (i = 0; i < dpyinfo->num_devices; ++i)
22470 {
22471 for (j = 0; j < n_disabled; ++j)
22472 {
22473 if (disabled[j] == dpyinfo->devices[i].device_id)
22474 {
22475#ifdef HAVE_XINPUT2_1
22476 xfree (dpyinfo->devices[i].valuators);
22477#endif
22478#ifdef HAVE_XINPUT2_2
22479 tem = dpyinfo->devices[i].touchpoints;
22480 while (tem)
22481 {
22482 last = tem;
22483 tem = tem->next;
22484 xfree (last);
22485 }
22486#endif
22487 goto break_detachment;
22488 }
22489 }
22490
22491 devices[ndevices++] = dpyinfo->devices[i];
22492
22493 break_detachment:
22494 continue;
22495 }
22496
22497 xfree (dpyinfo->devices);
22498 dpyinfo->devices = devices;
22499 dpyinfo->num_devices = ndevices;
22500 }
22501 22493
22502 /* Now that the device hierarchy has been changed, 22494 /* Now that the device hierarchy has been changed,
22503 recompute focus. */ 22495 recompute focus. */