mirror of
https://github.com/9fans/plan9port.git
synced 2025-01-12 11:10:07 +00:00
fix double free bug, simplify error handling, reduce X11 calls, improve style
This commit is contained in:
parent
52be2761ae
commit
3e764832bc
1 changed files with 74 additions and 100 deletions
|
@ -24,6 +24,7 @@ struct Win {
|
|||
|
||||
XDisplay *dpy;
|
||||
XWindow root;
|
||||
|
||||
Atom net_active_window;
|
||||
Reprog *exclude = nil;
|
||||
Win *win;
|
||||
|
@ -36,14 +37,13 @@ int showwmnames;
|
|||
Font *font;
|
||||
Image *lightblue;
|
||||
|
||||
XErrorHandler oldxerrorhandler;
|
||||
|
||||
enum {
|
||||
enum
|
||||
{
|
||||
PAD = 3,
|
||||
MARGIN = 5
|
||||
};
|
||||
|
||||
static jmp_buf savebuf;
|
||||
|
||||
int
|
||||
winwatchxerrorhandler(XDisplay *disp, XErrorEvent *xe)
|
||||
|
@ -53,11 +53,7 @@ winwatchxerrorhandler(XDisplay *disp, XErrorEvent *xe)
|
|||
XGetErrorText(disp, xe->error_code, buf, 100);
|
||||
fprint(2, "winwatch: X error %s, request code %d\n",
|
||||
buf, xe->request_code);
|
||||
XFlush(disp);
|
||||
XSync(disp, False);
|
||||
XSetErrorHandler(oldxerrorhandler);
|
||||
longjmp(savebuf, 1);
|
||||
return(0); /* Not reached */
|
||||
return 0;
|
||||
}
|
||||
|
||||
void*
|
||||
|
@ -75,7 +71,7 @@ estrdup(char *s)
|
|||
s = strdup(s);
|
||||
if(s == nil)
|
||||
sysfatal("out of memory allocating");
|
||||
return(s);
|
||||
return s;
|
||||
}
|
||||
|
||||
char*
|
||||
|
@ -89,18 +85,15 @@ getproperty(XWindow w, Atom a)
|
|||
|
||||
n = 100;
|
||||
p = nil;
|
||||
oldxerrorhandler = XSetErrorHandler(winwatchxerrorhandler);
|
||||
s = XGetWindowProperty(dpy, w, a, 0, 100L, 0,
|
||||
AnyPropertyType, &type, &fmt, &n, &dummy, &p);
|
||||
XFlush(dpy);
|
||||
XSync(dpy, False);
|
||||
XSetErrorHandler(oldxerrorhandler);
|
||||
|
||||
if(s != 0){
|
||||
XFree(p);
|
||||
return(nil);
|
||||
return nil;
|
||||
}
|
||||
|
||||
return((char*)p);
|
||||
return (char*)p;
|
||||
}
|
||||
|
||||
XWindow
|
||||
|
@ -108,7 +101,7 @@ findname(XWindow w)
|
|||
{
|
||||
int i;
|
||||
uint nxwin;
|
||||
XWindow dw1, dw2, *xwin;
|
||||
XWindow dw1, dw2, *xwin, rwin;
|
||||
char *p;
|
||||
int s;
|
||||
Atom net_wm_name;
|
||||
|
@ -116,37 +109,32 @@ findname(XWindow w)
|
|||
p = getproperty(w, XA_WM_NAME);
|
||||
if(p){
|
||||
free(p);
|
||||
return(w);
|
||||
return w;
|
||||
}
|
||||
|
||||
net_wm_name = XInternAtom(dpy, "_NET_WM_NAME", FALSE);
|
||||
p = getproperty(w, net_wm_name);
|
||||
if(p){
|
||||
free(p);
|
||||
return(w);
|
||||
return w;
|
||||
}
|
||||
|
||||
oldxerrorhandler = XSetErrorHandler(winwatchxerrorhandler);
|
||||
rwin = 0;
|
||||
|
||||
s = XQueryTree(dpy, w, &dw1, &dw2, &xwin, &nxwin);
|
||||
XFlush(dpy);
|
||||
XSync(dpy, False);
|
||||
XSetErrorHandler(oldxerrorhandler);
|
||||
if(s == 0) {
|
||||
if (xwin != NULL)
|
||||
XFree(xwin);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(s != 0){
|
||||
for (i = 0; i < nxwin; i++){
|
||||
w = findname(xwin[i]);
|
||||
if(w != 0){
|
||||
XFree(xwin);
|
||||
return w;
|
||||
rwin = w;
|
||||
break ;
|
||||
}
|
||||
}
|
||||
XFree(xwin);
|
||||
}
|
||||
|
||||
return 0;
|
||||
return rwin;
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -156,7 +144,6 @@ wcmp(const void *w1, const void *w2)
|
|||
}
|
||||
|
||||
/* unicode-aware case-insensitive strcmp, taken from golang’s gc/subr.c */
|
||||
|
||||
int
|
||||
_cistrcmp(char *p, char *q)
|
||||
{
|
||||
|
@ -200,17 +187,14 @@ refreshwin(void)
|
|||
Status s;
|
||||
Atom net_wm_name;
|
||||
|
||||
|
||||
oldxerrorhandler = XSetErrorHandler(winwatchxerrorhandler);
|
||||
s = XQueryTree(dpy, root, &dw1, &dw2, &xwin, &nxwin);
|
||||
XFlush(dpy);
|
||||
XSync(dpy, False);
|
||||
XSetErrorHandler(oldxerrorhandler);
|
||||
|
||||
if(s == 0){
|
||||
if(xwin != NULL)
|
||||
XFree(xwin);
|
||||
return;
|
||||
}
|
||||
|
||||
qsort(xwin, nxwin, sizeof(xwin[0]), wcmp);
|
||||
|
||||
nw = 0;
|
||||
|
@ -220,11 +204,8 @@ refreshwin(void)
|
|||
if(xwin[i] == 0)
|
||||
continue;
|
||||
|
||||
oldxerrorhandler = XSetErrorHandler(winwatchxerrorhandler);
|
||||
s = XGetWindowAttributes(dpy, xwin[i], &attr);
|
||||
XFlush(dpy);
|
||||
XSync(dpy, False);
|
||||
XSetErrorHandler(oldxerrorhandler);
|
||||
|
||||
if(s == 0)
|
||||
continue;
|
||||
if(attr.width <= 0 ||
|
||||
|
@ -232,11 +213,7 @@ refreshwin(void)
|
|||
attr.map_state != IsViewable)
|
||||
continue;
|
||||
|
||||
oldxerrorhandler = XSetErrorHandler(winwatchxerrorhandler);
|
||||
s = XGetClassHint(dpy, xwin[i], &class);
|
||||
XFlush(dpy);
|
||||
XSync(dpy, False);
|
||||
XSetErrorHandler(oldxerrorhandler);
|
||||
|
||||
if(s == 0)
|
||||
continue;
|
||||
|
@ -280,6 +257,7 @@ refreshwin(void)
|
|||
mwin += 8;
|
||||
win = erealloc(win, mwin * sizeof(win[0]));
|
||||
}
|
||||
|
||||
win[nw].n = xwin[i];
|
||||
win[nw].label = estrdup(label);
|
||||
win[nw].dirty = 1;
|
||||
|
@ -290,11 +268,7 @@ refreshwin(void)
|
|||
nw++;
|
||||
}
|
||||
|
||||
oldxerrorhandler = XSetErrorHandler(winwatchxerrorhandler);
|
||||
XFree(xwin);
|
||||
XFlush(dpy);
|
||||
XSync(dpy, False);
|
||||
XSetErrorHandler(oldxerrorhandler);
|
||||
|
||||
while(nwin > nw)
|
||||
free(win[--nwin].label);
|
||||
|
@ -481,9 +455,6 @@ main(int argc, char **argv)
|
|||
if(argc)
|
||||
usage();
|
||||
|
||||
/* moved up from original winwatch.c for p9p because there can be only one but we want to restart when needed */
|
||||
einit(Emouse | Ekeyboard);
|
||||
Etimer = etimer(0, 1000);
|
||||
|
||||
dpy = XOpenDisplay("");
|
||||
if(dpy == nil)
|
||||
|
@ -500,11 +471,14 @@ main(int argc, char **argv)
|
|||
if(font == nil)
|
||||
sysfatal("font '%s' not found", fontname);
|
||||
|
||||
/* reentry point upon X server errors */
|
||||
setjmp(savebuf);
|
||||
einit(Emouse | Ekeyboard);
|
||||
Etimer = etimer(0, 1000);
|
||||
|
||||
XSetErrorHandler(winwatchxerrorhandler);
|
||||
|
||||
refreshwin();
|
||||
redraw(screen, 1);
|
||||
|
||||
for(;;){
|
||||
switch(eread(Emouse|Ekeyboard|Etimer, &e)){
|
||||
case Ekeyboard:
|
||||
|
|
Loading…
Reference in a new issue