gui: Use nonblock API for command and audiod pipe.
authorAndre Noll <maan@systemlinux.org>
Thu, 6 May 2010 04:48:45 +0000 (06:48 +0200)
committerAndre Noll <maan@systemlinux.org>
Thu, 6 May 2010 04:48:45 +0000 (06:48 +0200)
This gets rid of another two calls to the unreliable FD_ISSET().

gui.c

diff --git a/gui.c b/gui.c
index f2098d4..31987c4 100644 (file)
--- a/gui.c
+++ b/gui.c
@@ -708,12 +708,15 @@ print:
        return 1;
 }
 
-static int read_audiod_pipe(int fd)
+static int read_audiod_pipe(fd_set *rfds)
 {
        static char *buf;
        static int bufsize, loaded;
-       int ret;
+       int ret, ret2;
+       size_t sz;
 
+       if (audiod_pipe < 0)
+               return 0;
        if (loaded >= bufsize) {
                if (bufsize > 1000 * 1000) {
                        loaded = 0;
@@ -723,16 +726,18 @@ static int read_audiod_pipe(int fd)
                buf = para_realloc(buf, bufsize);
        }
        assert(loaded < bufsize);
-       ret = read(fd, buf + loaded, bufsize - loaded);
-       if (ret <= 0)
-               return ret;
-       loaded += ret;
-       ret = for_each_stat_item(buf, loaded, update_item);
-       if (ret < 0)
-               return ret;
-       if (ret > 0 && ret < loaded)
-               memmove(buf, buf + loaded - ret, ret);
-       loaded = ret;
+       ret = read_nonblock(audiod_pipe, buf + loaded, bufsize - loaded,
+               rfds, &sz);
+       loaded += sz;
+       ret2 = for_each_stat_item(buf, loaded, update_item);
+       if (ret < 0 || ret2 < 0) {
+               loaded = 0;
+               return ret2 < 0? ret2 : ret;
+       }
+       sz = ret2; /* what is left */
+       if (sz > 0 && sz < loaded)
+               memmove(buf, buf + loaded - sz, sz);
+       loaded = sz;
        return 1;
 }
 
@@ -931,7 +936,7 @@ static int do_select(int mode)
 {
        fd_set rfds;
        int ret;
-       int max_fileno, cp_numread = 1;
+       int max_fileno;
        char command_buf[4096] = "";
        int cbo = 0; /* command buf offset */
        struct timeval tv;
@@ -959,40 +964,37 @@ repeat:
        if (ret > 0)
                handle_signal(ret);
        /* read command pipe if ready */
-       if (command_pipe >= 0 && mode == COMMAND_MODE &&
-                       FD_ISSET(command_pipe, &rfds)) {
-               cp_numread = read(command_pipe, command_buf + cbo,
-                       sizeof(command_buf) - 1 - cbo);
-               if (cp_numread >= 0)
-                       cbo += cp_numread;
-               else {
-                       if (cp_numread < 0)
-                               PARA_ERROR_LOG("read error (%d)", cp_numread);
+       if (command_pipe >= 0 && mode == COMMAND_MODE) {
+               size_t sz;
+               ret = read_nonblock(command_pipe, command_buf + cbo,
+                       sizeof(command_buf) - 1 - cbo, &rfds, &sz);
+               cbo += sz;
+               sz = cbo;
+               cbo = for_each_line(command_buf, cbo, &add_output_line, NULL);
+               if (sz != cbo)
+                       wrefresh(bot.win);
+               if (ret < 0) {
+                       PARA_NOTICE_LOG("closing command pipe: %s",
+                               para_strerror(-ret));
                        close(command_pipe);
                        command_pipe = -1;
+                       return 0;
                }
        }
-       if (audiod_pipe >= 0 && FD_ISSET(audiod_pipe, &rfds))
-               if (read_audiod_pipe(audiod_pipe) <= 0) {
-                       close(audiod_pipe);
-                       audiod_pipe = -1;
-                       clear_all_items();
-                       free(stat_content[SI_BASENAME]);
-                       stat_content[SI_BASENAME] =
-                               para_strdup("audiod not running!?");
-                       print_all_items();
-               }
+       ret = read_audiod_pipe(&rfds);
+       if (ret < 0) {
+               PARA_NOTICE_LOG("closing audiod pipe: %s\n", para_strerror(-ret));
+               close(audiod_pipe);
+               audiod_pipe = -1;
+               clear_all_items();
+               free(stat_content[SI_BASENAME]);
+               stat_content[SI_BASENAME] =
+                       para_strdup("stat command terminated!?");
+               print_all_items();
+       }
 check_return:
        switch (mode) {
        case COMMAND_MODE:
-               if (cp_numread <= 0 && !cbo) /* command complete */
-                       return 0;
-               if (cbo)
-                       cbo = for_each_line(command_buf, cbo,
-                               &add_output_line, NULL);
-               if (cp_numread <= 0)
-                       cbo = 0;
-               wrefresh(bot.win);
                ret = wgetch(top.win);
                if (ret != ERR && ret != KEY_RESIZE) {
                        if (command_pipe) {