From f163a15b133b6726bb52907dbe68df5605056a8f Mon Sep 17 00:00:00 2001 From: "Owen W. Taylor" Date: Wed, 10 Sep 2014 13:06:28 -0400 Subject: [PATCH] MetaStackTracker: optimize out unnecessary X restacking We have a quite accurate view of the X stack, so there's no good reason to ask the X server to do restacking that has no effect. (Restackings that have no effect on either X windows or Wayland windows were generally optimized out in the synchronization code, but in other cases like moving an X window that is only beneath Wayland windows to the top of the stack we would make such requests.) Removing such requests: - Is a small efficiency win in itself - Allows us to immediately go ahead and apply Wayland changes to the verified stack - Prevents queued Wayland changes piling up waiting for an X event that will never be received, since the X server will not send confirmation of no-op restacks. Since such operations may still have an effect on the relative stacking of X and Wayland windows, we need to continue applying them to the local stack. https://bugzilla.gnome.org/show_bug.cgi?id=736559 --- src/core/stack-tracker.c | 54 +++++++++++++++++++++++----------------- 1 file changed, 31 insertions(+), 23 deletions(-) diff --git a/src/core/stack-tracker.c b/src/core/stack-tracker.c index c916e0f9d..9de84e15d 100644 --- a/src/core/stack-tracker.c +++ b/src/core/stack-tracker.c @@ -534,11 +534,11 @@ stack_tracker_apply_prediction (MetaStackTracker *tracker, { gboolean free_at_end = FALSE; - /* If this is a wayland operation then it's implicitly verified so - * we can apply it immediately so long as it doesn't depend on any - * unverified X operations... + /* If this operation doesn't involve restacking X windows then it's + * implicitly verified. We can apply it immediately unless there + * are outstanding X restacks that haven't yet been confirmed. */ - if (!META_STACK_ID_IS_X11 (op->any.window) && + if (op->any.serial == 0 && tracker->unverified_predictions->length == 0) { if (meta_stack_op_apply (tracker, op, tracker->verified_stack, APPLY_DEFAULT)) @@ -976,19 +976,23 @@ meta_stack_tracker_lower_below (MetaStackTracker *tracker, if (META_STACK_ID_IS_X11 (window)) { XWindowChanges changes; - serial = XNextRequest (tracker->screen->display->xdisplay); + changes.sibling = sibling ? find_x11_sibling_upwards (tracker, sibling) : None; - meta_error_trap_push (tracker->screen->display); + if (changes.sibling != find_x11_sibling_upwards (tracker, window)) + { + serial = XNextRequest (tracker->screen->display->xdisplay); - changes.sibling = sibling ? find_x11_sibling_upwards (tracker,sibling) : None; - changes.stack_mode = changes.sibling ? Below : Above; + meta_error_trap_push (tracker->screen->display); - XConfigureWindow (tracker->screen->display->xdisplay, - window, - (changes.sibling ? CWSibling : 0) | CWStackMode, - &changes); + changes.stack_mode = changes.sibling ? Below : Above; - meta_error_trap_pop (tracker->screen->display); + XConfigureWindow (tracker->screen->display->xdisplay, + window, + (changes.sibling ? CWSibling : 0) | CWStackMode, + &changes); + + meta_error_trap_pop (tracker->screen->display); + } } meta_stack_tracker_record_lower_below (tracker, @@ -1013,19 +1017,23 @@ meta_stack_tracker_raise_above (MetaStackTracker *tracker, if (META_STACK_ID_IS_X11 (window)) { XWindowChanges changes; - serial = XNextRequest (tracker->screen->display->xdisplay); - - meta_error_trap_push (tracker->screen->display); - changes.sibling = sibling ? find_x11_sibling_downwards (tracker, sibling) : None; - changes.stack_mode = changes.sibling ? Above : Below; - XConfigureWindow (tracker->screen->display->xdisplay, - (Window)window, - (changes.sibling ? CWSibling : 0) | CWStackMode, - &changes); + if (changes.sibling != find_x11_sibling_downwards (tracker, window)) + { + serial = XNextRequest (tracker->screen->display->xdisplay); - meta_error_trap_pop (tracker->screen->display); + meta_error_trap_push (tracker->screen->display); + + changes.stack_mode = changes.sibling ? Above : Below; + + XConfigureWindow (tracker->screen->display->xdisplay, + (Window)window, + (changes.sibling ? CWSibling : 0) | CWStackMode, + &changes); + + meta_error_trap_pop (tracker->screen->display); + } } meta_stack_tracker_record_raise_above (tracker, window,