Am 01.11.2010 16:05, schrieb Thomas Dahms:
Hi list,

I am using dwm inside an Oracle Virtualbox (version 3.2.10 on Windows
host, Arch Linux x86_64 guest with xorg-server 1.9.901).

When switching focus between two side-by-side terminals, only the upper
parts of the window borders are redrawn (down to the point where the
lowest of the two cursors is). Other applications also show border
drawing issues, but it's not as predictable as with terminals. When
redrawing everything (by switching layouts), the borders are redrawn
correctly.

The funny thing is that when I try to take a screenshot of what's
happening, the borders look right in the screenshot. Regardless of where
I take the screenshot, host or guest.

This does not occur with other window managers, but it may still not be
dwm's fault. I'd be glad if someone can help.

Nobody replied, which is fine because this is really not a bug in dwm. The X drivers of Virtualbox and VMWare seem to mishandle XSetWindowBorder() [1].

Attached patch (against dwm tip) works around the problem in a very ugly way, but maybe other people running Virtualbox are interested.

[1] https://bugs.launchpad.net/ubuntu/+source/xserver-xorg-video-vmware/+bug/312080

--
Thomas Dahms
# HG changeset patch
# User Thomas Dahms <[email protected]>
# Date 1288773625 -3600
# Node ID b86e37eb3d5f0f348239b8abf72d8caf9f4b617b
# Parent  406003e3a01f8584f7bb54d0e5b1ff6585f7de6d
Virtualbox workaround.

diff -r 406003e3a01f -r b86e37eb3d5f dwm.c
--- a/dwm.c     Mon Sep 27 07:53:44 2010 +0000
+++ b/dwm.c     Wed Nov 03 09:40:25 2010 +0100
@@ -202,6 +202,7 @@
 static Monitor *ptrtomon(int x, int y);
 static void propertynotify(XEvent *e);
 static void quit(const Arg *arg);
+static void redrawborder(Client *c);
 static void resize(Client *c, int x, int y, int w, int h, Bool interact);
 static void resizeclient(Client *c, int x, int y, int w, int h);
 static void resizemouse(const Arg *arg);
@@ -825,6 +826,7 @@
                attachstack(c);
                grabbuttons(c, True);
                XSetWindowBorder(dpy, c->win, dc.sel[ColBorder]);
+               redrawborder(c);
                XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime);
        }
        else
@@ -1334,6 +1336,16 @@
 }
 
 void
+redrawborder(Client *c) {
+       /* works around a bug in X drivers of Virtualbox and VMWare */
+       XWindowChanges wc;
+       wc.border_width = 0;
+       XConfigureWindow(dpy, c->win, CWBorderWidth, &wc);
+       wc.border_width = c->bw;
+       XConfigureWindow(dpy, c->win, CWBorderWidth, &wc);
+}
+
+void
 resizeclient(Client *c, int x, int y, int w, int h) {
        XWindowChanges wc;
 
@@ -1704,6 +1716,7 @@
                return;
        grabbuttons(c, False);
        XSetWindowBorder(dpy, c->win, dc.norm[ColBorder]);
+       redrawborder(c);
        if(setfocus)
                XSetInputFocus(dpy, root, RevertToPointerRoot, CurrentTime);
 }

Reply via email to