[PATCH 3/3] xcompmgr: fix window adding with re-used window ids

Forest Bond forest at alittletooquiet.net
Sat Jun 12 16:29:03 PDT 2010


Hi,

Please disregard this patch.  I will resend with adjustments tomorrow.  Sorry
for the noise.

Thanks,
Forest

On Sat, Jun 12, 2010 at 06:39:59PM -0400, Forest Bond wrote:
> The X server can re-use window ids once a window has been destroyed.
> However, xcompmgr does not forget about window ids until after the
> window has finished fading out.  If a window is destroyed and a new
> window with the same id is added before the first window fades out,
> the new window never appears because xcompmgr has two win structures
> with the same window id and chooses the wrong one to map.  This patch
> fixes this problem by tracking which windows have been destroyed and
> looking only at windows that have not been destroyed when matching
> window ids from the server.
> 
> Signed-off-by: Forest Bond <forest at alittletooquiet.net>
> ---
>  xcompmgr.c |  150 +++++++++++++++++++++++++++++++++++++++--------------------
>  1 files changed, 99 insertions(+), 51 deletions(-)
> 
> diff --git a/xcompmgr.c b/xcompmgr.c
> index 47f5667..d25323d 100644
> --- a/xcompmgr.c
> +++ b/xcompmgr.c
> @@ -67,6 +67,7 @@ typedef struct _win {
>      Bool		usable;		    /* mapped and all damaged at one point */
>      XRectangle		damage_bounds;	    /* bounds of damage */
>  #endif
> +    int			destroyed;
>      int			mode;
>      int			damaged;
>      Damage		damage;
> @@ -156,6 +157,7 @@ static conv		*gaussianMap;
>  
>  #define TRANS_OPACITY	0.75
>  
> +#define DEBUG_WINDWS 0
>  #define DEBUG_REPAINT 0
>  #define DEBUG_EVENTS 0
>  #define MONITOR_REPAINT 0
> @@ -751,7 +753,7 @@ find_win (Display *dpy, Window id)
>      win	*w;
>  
>      for (w = list; w; w = w->next)
> -	if (w->id == id)
> +	if ((!w->destroyed) && (w->id == id))
>  	    return w;
>      return NULL;
>  }
> @@ -948,12 +950,20 @@ paint_all (Display *dpy, XserverRegion region)
>  	    continue;
>  #endif
>  	/* never painted, ignore it */
> -	if ((!screen_damaged) && (!w->damaged))
> +	if ((!screen_damaged) && (!w->damaged)) {
> +#if DEBUG_REPAINT
> +	    printf(" [not damaged: 0x%x]", w->id);
> +#endif
>  	    continue;
> +	}
>  	/* if invisible, ignore it */
>  	if (w->a.x + w->a.width < 1 || w->a.y + w->a.height < 1
> -	    || w->a.x >= root_width || w->a.y >= root_height)
> +	    || w->a.x >= root_width || w->a.y >= root_height) {
> +#if DEBUG_REPAINT
> +	    printf(" [invisible: 0x%x]", w->id);
> +#endif
>  	    continue;
> +	}
>  	if (!w->picture)
>  	{
>  	    XRenderPictureAttributes	pa;
> @@ -974,7 +984,7 @@ paint_all (Display *dpy, XserverRegion region)
>  					       &pa);
>  	}
>  #if DEBUG_REPAINT
> -	printf (" 0x%x", w->id);
> +	printf (" [painting 0x%x]", w->id);
>  #endif
>  	if (clipChanged)
>  	{
> @@ -1177,6 +1187,10 @@ map_win (Display *dpy, Window id, unsigned long sequence, Bool fade)
>  {
>      win		*w = find_win (dpy, id);
>  
> +#if DEBUG_WINDOWS
> +    printf("map_win: 0x%x\n", w->id);
> +#endif
> +
>      if (!w)
>  	return;
>  
> @@ -1202,6 +1216,9 @@ map_win (Display *dpy, Window id, unsigned long sequence, Bool fade)
>  static void
>  finish_unmap_win (Display *dpy, win *w)
>  {
> +#if DEBUG_WINDOWS
> +    printf("finish_unmap_win: 0x%x\n", w->id);
> +#endif
>      w->damaged = 0;
>  #if CAN_DO_USABLE
>      w->usable = False;
> @@ -1263,6 +1280,11 @@ static void
>  unmap_win (Display *dpy, Window id, Bool fade)
>  {
>      win *w = find_win (dpy, id);
> +
> +#if DEBUG_WINDOWS
> +    printf("unmap_win: 0x%x\n", w->id);
> +#endif
> +
>      if (!w)
>  	return;
>      w->a.map_state = IsUnmapped;
> @@ -1427,12 +1449,16 @@ add_win (Display *dpy, Window id, Window prev)
>      win				*new = malloc (sizeof (win));
>      win				**p;
>      
> +#if DEBUG_WINDOWS
> +    printf("add_win: 0x%x\n", id);
> +#endif
> +
>      if (!new)
>  	return;
>      if (prev)
>      {
>  	for (p = &list; *p; p = &(*p)->next)
> -	    if ((*p)->id == prev)
> +	    if ((!(*p)->destroyed) && ((*p)->id == prev))
>  		break;
>      }
>      else
> @@ -1442,8 +1468,12 @@ add_win (Display *dpy, Window id, Window prev)
>      if (!XGetWindowAttributes (dpy, id, &new->a))
>      {
>  	free (new);
> +#if DEBUG_WINDOWS
> +	printf("not adding 0x%x: failed to get attributes\n", new->id);
> +#endif
>  	return;
>      }
> +    new->destroyed = 0;
>      new->damaged = 0;
>  #if CAN_DO_USABLE
>      new->usable = False;
> @@ -1489,6 +1519,10 @@ restack_win (Display *dpy, win *w, Window new_above)
>  {
>      Window  old_above;
>      
> +#if DEBUG_WINDOWS
> +    printf("restack_win: 0x%x\n", w->id);
> +#endif
> +
>      if (w->next)
>  	old_above = w->next->id;
>      else
> @@ -1506,7 +1540,7 @@ restack_win (Display *dpy, win *w, Window new_above)
>  	/* rehook */
>  	for (prev = &list; *prev; prev = &(*prev)->next)
>  	{
> -	    if ((*prev)->id == new_above)
> +	    if ((!(*prev)->destroyed) && ((*prev)->id == new_above))
>  		break;
>  	}
>  	w->next = *prev;
> @@ -1597,54 +1631,61 @@ circulate_win (Display *dpy, XCirculateEvent *ce)
>  }
>  
>  static void
> -finish_destroy_win (Display *dpy, Window id, Bool gone)
> +finish_destroy_win (Display *dpy, win *w, Bool gone)
>  {
> -    win	**prev, *w;
> +    win *prev;
>  
> -    for (prev = &list; (w = *prev); prev = &w->next)
> -	if (w->id == id)
> -	{
> -	    if (gone)
> -		finish_unmap_win (dpy, w);
> -	    *prev = w->next;
> -	    if (w->picture)
> -	    {
> -		set_ignore (dpy, NextRequest (dpy));
> -		XRenderFreePicture (dpy, w->picture);
> -		w->picture = None;
> -	    }
> -	    if (w->alphaPict)
> -	    {
> -		XRenderFreePicture (dpy, w->alphaPict);
> -		w->alphaPict = None;
> -	    }
> -	    if (w->shadowPict)
> -	    {
> -		XRenderFreePicture (dpy, w->shadowPict);
> -		w->shadowPict = None;
> -	    }
> -	    if (w->shadow)
> -	    {
> -		XRenderFreePicture (dpy, w->shadow);
> -		w->shadow = None;
> -	    }
> -	    if (w->damage != None)
> -	    {
> -		set_ignore (dpy, NextRequest (dpy));
> -		XDamageDestroy (dpy, w->damage);
> -		w->damage = None;
> -	    }
> -	    cleanup_fade (dpy, w);
> -	    free (w);
> +#if DEBUG_WINDOWS
> +    printf("finish_destroy_win: 0x%x\n", w->id);
> +#endif
> +
> +    for (prev = list; prev; prev = prev->next)
> +	if (prev->next == w)
>  	    break;
> -	}
> +
> +    if (! prev)
> +	/* Couldn't find the window? */
> +	return;
> +
> +    if (gone)
> +	finish_unmap_win (dpy, w);
> +    prev->next = w->next;
> +    if (w->picture)
> +    {
> +	set_ignore (dpy, NextRequest (dpy));
> +	XRenderFreePicture (dpy, w->picture);
> +	w->picture = None;
> +    }
> +    if (w->alphaPict)
> +    {
> +	XRenderFreePicture (dpy, w->alphaPict);
> +	w->alphaPict = None;
> +    }
> +    if (w->shadowPict)
> +    {
> +	XRenderFreePicture (dpy, w->shadowPict);
> +	w->shadowPict = None;
> +    }
> +    if (w->shadow)
> +    {
> +	XRenderFreePicture (dpy, w->shadow);
> +	w->shadow = None;
> +    }
> +    if (w->damage != None)
> +    {
> +	set_ignore (dpy, NextRequest (dpy));
> +	XDamageDestroy (dpy, w->damage);
> +	w->damage = None;
> +    }
> +    cleanup_fade (dpy, w);
> +    free (w);
>  }
>  
>  #if HAS_NAME_WINDOW_PIXMAP
>  static void
>  destroy_callback (Display *dpy, win *w, Bool gone)
>  {
> -    finish_destroy_win (dpy, w->id, gone);
> +    finish_destroy_win (dpy, w, gone);
>  }
>  #endif
>  
> @@ -1652,22 +1693,27 @@ static void
>  destroy_win (Display *dpy, Window id, Bool gone, Bool fade)
>  {
>      win *w = find_win (dpy, id);
> +#if DEBUG_WINDOWS
> +    printf("destroy_win: 0x%x\n", w->id);
> +#endif
> +    w->destroyed = 1;
>  #if HAS_NAME_WINDOW_PIXMAP
>      if (w && w->pixmap && fade && fadeWindows)
>  	set_fade (dpy, w, w->opacity*1.0/OPAQUE, 0.0, fade_out_step, destroy_callback, gone, False, True);
>      else
>  #endif
>      {
> -	finish_destroy_win (dpy, id, gone);
> +	finish_destroy_win (dpy, w, gone);
>      }
>  }
>  
> -/*
> +#if DEBUG_WINDOWS
>  static void
>  dump_win (win *w)
>  {
> -    printf ("\t%08lx: %d x %d + %d + %d (%d)\n", w->id,
> -	    w->a.width, w->a.height, w->a.x, w->a.y, w->a.border_width);
> +    printf ("\t%08lx: %d x %d + %d + %d (%d)%s\n", w->id,
> +	    w->a.width, w->a.height, w->a.x, w->a.y, w->a.border_width,
> +	    w->destroyed ? " (destroyed)" : "");
>  }
>  
>  
> @@ -1680,7 +1726,7 @@ dump_wins (void)
>      for (w = list; w; w = w->next)
>  	dump_win (w);
>  }
> -*/
> +#endif
>  
>  static void
>  damage_win (Display *dpy, XDamageNotifyEvent *de)
> @@ -2128,7 +2174,9 @@ main (int argc, char **argv)
>  	paint_all (dpy, None);
>      for (;;)
>      {
> -	/*	dump_wins (); */
> +#if DEBUG_WINDOWS
> +	dump_wins ();
> +#endif
>  	do {
>  	    if (autoRedirect)
>  		XFlush (dpy);
> -- 
> 1.7.0.4
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 189 bytes
Desc: Digital signature
URL: <http://lists.x.org/archives/xorg-devel/attachments/20100612/33547772/attachment.pgp>


More information about the xorg-devel mailing list