diff --git a/Makefile.in b/Makefile.in index 020ae06..f29a06e 100644 --- a/Makefile.in +++ b/Makefile.in @@ -32,7 +32,7 @@ src/wmfs.c # flags CFLAGS+= -DXDG_CONFIG_DIR=\"${XDG_CONFIG_DIR}\" CFLAGS+= -DWMFS_VERSION=\"${VERSION}\" -CFLAGS+= -W -Wall -Wextra -ansi +CFLAGS+= -W -Wall -Wextra OBJS= ${SRCS:.c=.o} @@ -50,6 +50,10 @@ ${MAN}.gz: ${MAN} clean: rm -f ${OBJS} wmfs ${MAN}.gz +distclean: clean + rm -f Makefile + + install: all @echo installing executable file to ${DESTDIR}${PREFIX}/bin mkdir -p ${DESTDIR}${PREFIX}/bin @@ -77,5 +81,5 @@ uninstall: -.PHONY: all clean install uninstall +.PHONY: all clean distclean install uninstall diff --git a/configure b/configure index 27b83e0..7a89d41 100755 --- a/configure +++ b/configure @@ -79,8 +79,6 @@ fi [ -n "$USE_XRANDR" ] && CFLAGS="$CFLAGS -DHAVE_XRANDR" [ -n "$USE_IMLIB2" ] && CFLAGS="$CFLAGS -DHAVE_IMLIB" -LDFLAGS="$LDFLAGS -lpthread" - cat > Makefile << EOF PREFIX=$PREFIX XDG_CONFIG_DIR=$XDG_CONFIG_DIR diff --git a/src/config.c b/src/config.c index df102c8..e258e65 100644 --- a/src/config.c +++ b/src/config.c @@ -549,7 +549,7 @@ conf_tag_section(void) { ++conf.ntag[k]; tags[k][conf.ntag[k]].name = fetch_opt_first(tag[i], fetch_opt_first(def_tag, "", "name").str, "name").str; - tags[k][conf.ntag[k]].mwfact = fetch_opt_first(tag[i], fetch_opt_first(def_tag, "0.6", "mwfact").str, "mwfact").fnum; + tags[k][conf.ntag[k]].mwfact = fetch_opt_first(tag[i], fetch_opt_first(def_tag, "0.65", "mwfact").str, "mwfact").fnum; tags[k][conf.ntag[k]].nmaster = fetch_opt_first(tag[i], fetch_opt_first(def_tag, "1", "nmaster").str, "nmaster").num; tags[k][conf.ntag[k]].resizehint = fetch_opt_first(tag[i], fetch_opt_first(def_tag, "false", "resizehint").str, "resizehint").bool; tags[k][conf.ntag[k]].abovefc = fetch_opt_first(tag[i], "false", "abovefc").bool; diff --git a/src/event.c b/src/event.c index e1e0989..c391521 100644 --- a/src/event.c +++ b/src/event.c @@ -695,7 +695,5 @@ getevent(XEvent ev) break; } - wait((int[]){0}); - return; } diff --git a/src/parse.c b/src/parse.c index dcca36c..be1641f 100644 --- a/src/parse.c +++ b/src/parse.c @@ -30,7 +30,6 @@ #include #include #include -#include #include #include @@ -183,19 +182,22 @@ parse_keywords(const char *filename) return NULL; } + buf = zmalloc(st.st_size+1); + + if (read(fd, buf, st.st_size) == -1) { + warn("%s", filename); + free(buf); + close(fd); + return NULL; + } + + buf[st.st_size] = '\0'; + file = zcalloc(sizeof(*file)); bufname = zcalloc(sizeof(*bufname) * BUFSIZ); file->name = strdup(path); file->parent = NULL; - buf = (char *)mmap(0, st.st_size, PROT_READ, MAP_PRIVATE, fd, SEEK_SET); - - if (buf == (char*)MAP_FAILED) { - warn("%s", filename); - return NULL; - } - - for(i = 0, j = 0, line = 1; i < (size_t)st.st_size; i++) { if (!head && tail) @@ -303,7 +305,7 @@ parse_keywords(const char *filename) bufname[j++] = buf[i]; } - munmap(buf, st.st_size); + free(buf); free(bufname); warnx("%s read", file->name); diff --git a/src/tag.c b/src/tag.c index 111a97c..917bb12 100644 --- a/src/tag.c +++ b/src/tag.c @@ -563,18 +563,20 @@ tag_new(int s, char *name) ++conf.ntag[s]; + /* TODO: memleak here */ if(!name || strlen(name) == 0) { if(conf.tagnamecount) { - displayedName = zmalloc(2); - sprintf(displayedName, "[%d]", conf.ntag[s]); + /* displayedName = zmalloc(2); */ + xasprintf(&displayedName, "[%d]", conf.ntag[s]); } else displayedName = conf.default_tag.name; } else - displayedName = name; + displayedName = xstrdup(name); + Tag t = { displayedName, NULL, 0, 0, conf.default_tag.mwfact, conf.default_tag.nmaster, diff --git a/src/util.c b/src/util.c index f6527cf..961b92a 100644 --- a/src/util.c +++ b/src/util.c @@ -30,6 +30,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +#define _GNU_SOURCE #include "wmfs.h" /** malloc with error support and size_t overflow protection @@ -248,33 +249,18 @@ alias_to_str(char *conf_choice) } /* }}} */ -/** Get the mouse pointer position. -*/ -XRectangle -get_mouse_pos(void) -{ - Window dum; - int d, u; - XRectangle ret; - - XQueryPointer(dpy, ROOT, &dum, &dum, (int*)&ret.x, (int*)&ret.y, &d, &d, (uint *)&u); - - return ret; -} - /** Execute a sh command * \param cmd Command * \return child pid */ -int +pid_t spawn(const char *format, ...) { char *sh = NULL; char cmd[512]; va_list ap; - pid_t pid, ret; - int p[2]; size_t len; + pid_t pid; va_start(ap, format); len = vsnprintf(cmd, sizeof(cmd), format, ap); @@ -289,48 +275,18 @@ spawn(const char *format, ...) if(!(sh = getenv("SHELL"))) sh = "/bin/sh"; - if (pipe(p) == -1) - { - warn("pipe"); - return -1; - } - if((pid = fork()) == 0) { - close(p[0]); - if((pid = fork()) == 0) - { - if(dpy) - close(ConnectionNumber(dpy)); - setsid(); - execl(sh, sh, "-c", cmd, (char*)NULL); - exit(EXIT_FAILURE); - } - - if (sizeof(pid_t) != write(p[1], &pid, sizeof(pid_t))) - warn("write"); - - close(p[1]); - exit(EXIT_SUCCESS); - } - else if (pid != -1) - { - close(p[1]); - if (sizeof(pid_t) != read(p[0], &ret, sizeof(pid_t))) - { - warn("read"); - ret = -1; - } - close(p[0]); - waitpid(pid, NULL, 0); - } - else - { - warn("fork"); - ret = -1; + if(dpy) + close(ConnectionNumber(dpy)); + setsid(); + execl(sh, sh, "-c", cmd, (char*)NULL); + err(1, "execl(%s)", cmd); } + if (pid == -1) + warn("fork()"); - return ret; + return pid; } /** Swap two pointer. diff --git a/src/wmfs.c b/src/wmfs.c index 10d0cfe..6963d5f 100644 --- a/src/wmfs.c +++ b/src/wmfs.c @@ -32,6 +32,8 @@ #include "wmfs.h" +static void signal_handle(int); + int errorhandler(Display *d, XErrorEvent *event) { @@ -133,55 +135,25 @@ quit(void) XCloseDisplay(dpy); /* kill status script */ - if (conf.status_pid != (pid_t)-1) - kill(conf.status_pid, SIGQUIT); + if (conf.status_pid != -1) + kill(conf.status_pid, SIGTERM); return; } -void * -thread_process(void *arg) -{ - XEvent ev; - - /* X event loop */ - if(arg) - { - while(!exiting && !XNextEvent(dpy, &ev)) - getevent(ev); - } - /* Status checking loop with timing */ - else - { - pthread_detach(pthread_self()); - do - { - conf.status_pid = spawn(conf.status_path); - sleep(conf.status_timing); - } while (!exiting && conf.status_timing != 0); - } - pthread_exit(NULL); -} - /** WMFS main loop. */ void mainloop(void) { XEvent ev; - pthread_t evloop, evstatus; - void *ret; - if(!estatus) - while(!exiting && !XNextEvent(dpy, &ev)) - getevent(ev); - else - { - pthread_create(&evloop, NULL, thread_process, "1"); - pthread_create(&evstatus, NULL, thread_process, NULL); + /* launch status loop */ + if (estatus) + signal_handle(SIGALRM); - (void)pthread_join(evloop, &ret); - } + while(!exiting && !XNextEvent(dpy, &ev)) + getevent(ev); return; } @@ -398,13 +370,39 @@ update_status(void) /** Signal handle function */ -void +static void signal_handle(int sig) { - (void)sig; - exiting = True; - quit(); - exit(EXIT_SUCCESS); + pid_t pid; + + switch (sig) + { + case SIGQUIT: + case SIGTERM: + exiting = True; + quit(); + exit(EXIT_SUCCESS); + break; + case SIGCHLD: + /* re-set signal handler and wait childs */ + if (signal(SIGCHLD, &signal_handle) == SIG_ERR) + warn("signal(%d)", SIGCHLD); + while ((pid = waitpid(-1, NULL, WNOHANG)) > 0) + if (pid == conf.status_pid) + conf.status_pid = -1; + break; + case SIGALRM: + /* re-set signal handler */ + if (signal(SIGALRM, &signal_handle) == SIG_ERR) + warn("signal(%d)", SIGALRM); + /* exec status script (only if still not running) */ + if (conf.status_pid == (pid_t)-1) + conf.status_pid = spawn(conf.status_path); + /* re-set timer */ + if (conf.status_timing > 0) + alarm(conf.status_timing); + break; + } return; } @@ -419,6 +417,9 @@ main(int argc, char **argv) { int i; char *ol = "csgVS"; + extern char *optarg; + extern int optind; + int sigs[] = { SIGTERM, SIGQUIT, SIGCHLD }; argv_global = xstrdup(argv[0]); all_argv = argv; @@ -502,8 +503,9 @@ main(int argc, char **argv) errx(EXIT_FAILURE, "cannot open X server."); /* Set signal handler */ - (void)signal(SIGTERM, &signal_handle); - (void)signal(SIGINT, &signal_handle); + for (i = 0; i < (int)LEN(sigs); i++) + if (signal(sigs[i], &signal_handle) == SIG_ERR) + warn("signal(%d)", sigs[i]); /* Check if an other WM is already running; set the error handler */ XSetErrorHandler(errorhandler); diff --git a/src/wmfs.h b/src/wmfs.h index 102a07b..039ae50 100644 --- a/src/wmfs.h +++ b/src/wmfs.h @@ -33,17 +33,6 @@ #ifndef WMFS_H #define WMFS_H -/* glibc stuff */ -#ifndef _BSD_SOURCE -#define _BSD_SOURCE /* vsnprintf */ -#endif -#ifndef _POSIX_SOURCE -#define _POSIX_SOURCE /* kill */ -#endif -#ifndef _GNU_SOURCE -#define _GNU_SOURCE /* asprintf */ -#endif - /* Lib headers */ #include #include @@ -308,9 +297,8 @@ uint char_to_button(char *name, name_to_uint_t blist[]); Layout layout_name_to_struct(Layout lt[], char *name, int n, const func_name_list_t llist[]); char* alias_to_str(char *conf_choice); /* }}} */ -XRectangle get_mouse_pos(void); char *char_to_str(const char c); -int spawn(const char *str, ...); +pid_t spawn(const char *str, ...); void swap_ptr(void **x, void **y); void uicb_spawn(uicb_t); char *clean_value(char *str);