From: Reginald Kennedy Date: Sun, 23 Sep 2012 10:33:23 +0000 (+0800) Subject: Change bar_action handling to eliminate the need for bar_delay. X-Git-Tag: SPECTRWM_2_1_0~32 X-Git-Url: https://code.delx.au/spectrwm/commitdiff_plain/d3818f73f1a4d3c7c50bee72fa2897d22c07f8c1 Change bar_action handling to eliminate the need for bar_delay. Old code called alarm() regularly and checked for input only at certain times. Now, the file descriptor for reading the text is added to the select() in the main loop, and so updates are caught immediately and efficiently. Patch submitted by Jason Woofenden (Note: Minor modifications were made to formatting and a dummy version of the bar_delay option was added to avoid breaking old conf files.) --- diff --git a/spectrwm.1 b/spectrwm.1 index 59a5acb..f27d837 100644 --- a/spectrwm.1 +++ b/spectrwm.1 @@ -101,10 +101,6 @@ Set status bar border thickness in pixels. Disable border by setting to 0. .It Ic bar_color Ns Bq Ar x Color of the status bar window in screen -.Ar x . -.It Ic bar_delay -Update frequency, in seconds, of external script that populates the status -bar. .It Ic bar_enabled Set default .Ar bar_toggle diff --git a/spectrwm.c b/spectrwm.c index 639969f..0020f39 100644 --- a/spectrwm.c +++ b/spectrwm.c @@ -351,8 +351,6 @@ int bar_pipe[2]; char bar_ext[SWM_BAR_MAX]; char bar_vertext[SWM_BAR_MAX]; int bar_version = 0; -sig_atomic_t bar_alarm = 0; -int bar_delay = 30; int bar_enabled = 1; int bar_border_width = 1; int bar_at_bottom = 0; @@ -834,7 +832,6 @@ void bar_replace_pad(char *, int *, size_t); char * bar_replace_seq(char *, char *, struct swm_region *, size_t *, size_t); void bar_setup(struct swm_region *); -void bar_signal(int); void bar_title_name(char *, size_t, struct swm_region *); void bar_toggle(struct swm_region *, union arg *); void bar_update(void); @@ -2203,10 +2200,8 @@ bar_update(void) size_t len; char *b; - if (!bar_enabled) - return; - if (bar_extra && bar_extra_running) { - /* ignore short reads; it'll correct itself */ + if (bar_enabled && bar_extra && bar_extra_running) { + /* Ignore short reads; it'll correct itself. */ while ((b = fgetln(stdin, &len)) != NULL) if (b && b[len - 1] == '\n') { b[len - 1] = '\0'; @@ -2216,20 +2211,20 @@ bar_update(void) warn("bar_update: bar_extra failed"); bar_extra_stop(); } - } else - strlcpy(bar_ext, "", sizeof bar_ext); + } else { + /* + * Attempt to drain stdin, so it doesn't cause the main loop to + * call us as fast as it can. + */ + fgetln(stdin, &len); - bar_fmt_print(); - alarm(bar_delay); -} + if (!bar_enabled) + return; -void -bar_signal(int sig) -{ - /* suppress unused warning since var is needed */ - (void)sig; + bar_ext[0] = '\0'; + } - bar_alarm = 1; + bar_fmt_print(); } void @@ -2291,10 +2286,15 @@ bar_refresh(void) err(1, "pipe error"); socket_setnonblock(bar_pipe[0]); socket_setnonblock(bar_pipe[1]); /* XXX hmmm, really? */ + + /* Set stdin to read from the pipe. */ if (dup2(bar_pipe[0], 0) == -1) err(1, "dup2"); + + /* Set stdout to write to the pipe. */ if (dup2(bar_pipe[1], 1) == -1) err(1, "dup2"); + if (signal(SIGPIPE, SIG_IGN) == SIG_ERR) err(1, "could not disable SIGPIPE"); switch (bar_pid = fork()) { @@ -2322,7 +2322,9 @@ bar_refresh(void) xcb_change_window_attributes(conn, r->bar->id, XCB_CW_BACK_PIXEL | XCB_CW_BORDER_PIXEL, wa); } + bar_update(); + xcb_flush(conn); } int @@ -2488,8 +2490,6 @@ bar_setup(struct swm_region *r) "%d x %d\n", WINID(r->bar), X(r->bar), Y(r->bar), WIDTH(r->bar), HEIGHT(r->bar)); - if (signal(SIGALRM, bar_signal) == SIG_ERR) - err(1, "could not install bar_signal"); bar_refresh(); } @@ -6489,7 +6489,7 @@ setconfvalue(char *selector, char *value, int flags) bar_border_width = 0; break; case SWM_S_BAR_DELAY: - bar_delay = atoi(value); + /* No longer needed; leave to not break old conf files. */ break; case SWM_S_BAR_ENABLED: bar_enabled = atoi(value); @@ -8838,6 +8838,9 @@ main(int argc, char *argv[]) xcb_generic_event_t *evt; struct timeval tv; fd_set rd; + int rd_max; + int do_bar_update = 0; + int num_readable; /* suppress unused warning since var is needed */ (void)argc; @@ -8968,6 +8971,8 @@ noconfig: xcb_ungrab_server(conn); xcb_flush(conn); + rd_max = xfd > STDIN_FILENO ? xfd : STDIN_FILENO; + while (running) { while ((evt = xcb_poll_for_event(conn))) { if (!running) @@ -8992,21 +8997,27 @@ noconfig: } FD_ZERO(&rd); + FD_SET(STDIN_FILENO, &rd); FD_SET(xfd, &rd); tv.tv_sec = 1; tv.tv_usec = 0; - if (select(xfd + 1, &rd, NULL, NULL, &tv) == -1) - if (errno != EINTR) { - DNPRINTF(SWM_D_MISC, "select failed"); - } + num_readable = select(rd_max + 1, &rd, NULL, NULL, &tv); + if (num_readable == -1 && errno != EINTR) + DNPRINTF(SWM_D_MISC, "select failed"); + else if (num_readable > 0 && FD_ISSET(STDIN_FILENO, &rd)) + do_bar_update = 1; + if (restart_wm) restart(NULL, NULL); + if (search_resp) search_do_resp(); + if (!running) goto done; - if (bar_alarm) { - bar_alarm = 0; + + if (do_bar_update) { + do_bar_update = 0; bar_update(); } } diff --git a/spectrwm.conf b/spectrwm.conf index f56559a..576e374 100644 --- a/spectrwm.conf +++ b/spectrwm.conf @@ -25,7 +25,6 @@ # bar_font_color[1] = rgb:a0/a0/a0 # bar_font = -*-terminus-medium-*-*-*-*-*-*-*-*-*-*-* # bar_action = baraction.sh -# bar_delay = 1 # bar_justify = left # bar_format = +N:+I +S <+D>+4<%a %b %d %R %Z %Y+8<+A+4<+V # bar_at_bottom = 1 diff --git a/spectrwm_es.1 b/spectrwm_es.1 index 0645e60..90010a6 100644 --- a/spectrwm_es.1 +++ b/spectrwm_es.1 @@ -105,9 +105,6 @@ Fuente de la barra de estado. .It Cm bar_action Scripts externos con populares agregados de información para la barra de estado, como la vida de la bateria. -.It Cm bar_delay -Frecuencia de actualización, en segundos, de los scripts de la barra de -estado. .It Cm bar_at_bottom Puedes posicionar la statusbar en la parte inferior de la pantalla. .It Cm stack_enabled diff --git a/spectrwm_it.1 b/spectrwm_it.1 index 09d7356..ef85d43 100644 --- a/spectrwm_it.1 +++ b/spectrwm_it.1 @@ -105,9 +105,6 @@ Font della barra di stato. .It Cm bar_action Script esterno che aggiunge informazioni come la carica della batteria alla barra di stato. -.It Cm bar_delay -Frequenza di aggiornamento, in secondi, dello script esterno che aggiunge -informazioni alla barra di stato. .It Cm bar_at_bottom Posiziona la barra di stato sul fondo dello schermo anzich? in cima. .It Cm stack_enabled diff --git a/spectrwm_pt.1 b/spectrwm_pt.1 index 3249901..b2835ef 100644 --- a/spectrwm_pt.1 +++ b/spectrwm_pt.1 @@ -98,9 +98,6 @@ Fonte da barra de status. .It Cm bar_action Script externo que preenche a barra de status com informa\(,c\(~oes adicionais, como tempo de vida da bateria. -.It Cm bar_delay -Freq\(:u\(^encia da atualiza\(,c\(~ao, em segundos, do script externo que preenche -a barra de status. .It Cm bar_at_bottom Coloca a barra de status na parte inferior de cada regi\(~ao, ao inv\('es da parte superior. .It Cm stack_enabled diff --git a/spectrwm_ru.1 b/spectrwm_ru.1 index c65a21b..4c3c5d9 100644 --- a/spectrwm_ru.1 +++ b/spectrwm_ru.1 @@ -96,8 +96,6 @@ Shift .It Cm bar_action Внешний файл скрипта для статусной строки, выводящий туда информацию, например, уровень заряда батарей. -.It Cm bar_delay -Частота выполнения внешнего скрипта статусной строки, секунды. .It Cm stack_enabled Включить отображение способа укладки окон в статусной строке. .It Cm clock_enabled