]> skyeroc.xyz Git - dgamelaunch/commitdiff
Use kqueue() if available (FreeBSD) to improve watching.
authorJilles Tjoelker <jilles@stack.nl>
Mon, 23 Aug 2004 14:00:29 +0000 (14:00 +0000)
committerJilles Tjoelker <jilles@stack.nl>
Mon, 23 Aug 2004 14:00:29 +0000 (14:00 +0000)
git-svn-id: svn://katsu.triplehelix.org/dgamelaunch/trunk@336 db0b04b0-f4d1-0310-9a6d-de3e77497b0e

Changelog
configure.ac
ttyplay.c

index 703344173dd6018feb87363fc2e39961838b841d..35bdfc9256dd5d6a5232e02a66c09882efa911e4 100644 (file)
--- a/Changelog
+++ b/Changelog
@@ -4,6 +4,7 @@
        * Fix bug where old cruft was left under the watch list after 'm'
          had been used.
        * Allow ^L and ^R to fully refresh the watch list.
+       * Use kqueue() if available (FreeBSD) to improve watching.
 
 1.4.6 (2004/07/03)
        * Fix some signed/unsigned warnings.
index 47a7f391f8741fdf1f271e45e4b6c6b4c994eba1..6a27b31e73e21d040f2dc57e0e75a2df7cb9c6bf 100644 (file)
@@ -78,7 +78,7 @@ AC_ARG_WITH(config-file,
 AC_DEFINE_UNQUOTED(DEFCONFIG, "$configfile", [Path to the default config file.])
 
 AC_CHECK_HEADERS([sys/pstat.h])
-AC_CHECK_FUNCS([openpty setenv setproctitle pstat])
+AC_CHECK_FUNCS([openpty setenv setproctitle pstat kqueue])
 
 if test "$ac_cv_func_setproctitle" = no; then
   SETPROCTITLE_C=setproctitle.c
index 5ffee95b257757c508fabf306410d694aaee1db7..187c66f7bb9b8ce19feb3ad9b89586faff35f10a 100644 (file)
--- a/ttyplay.c
+++ b/ttyplay.c
  * SUCH DAMAGE.
  */
 
+#include "config.h"
+
 #include <sys/types.h>
 #include <sys/time.h>
 #include <sys/stat.h>
+#ifdef HAVE_KQUEUE
+#include <sys/event.h>
+#endif
 
 #include <stdio.h>
 #include <stdlib.h>
@@ -137,10 +142,27 @@ ttyread (FILE * fp, Header * h, char **buf, int pread)
 int
 ttypread (FILE * fp, Header * h, char **buf, int pread)
 {
+  int n;
+#ifdef HAVE_KQUEUE
+  struct kevent evt[2];
+  static int kq = -1;
+#else
+  struct timeval w = { 0, 100000 };
   int counter = 0;
   fd_set readfs;
-  struct timeval w = { 0, 100000 };
+#endif
   struct termios t;
+  int doread = 0;
+
+#ifdef HAVE_KQUEUE
+  if (kq == -1)
+    kq = kqueue ();
+  if (kq == -1)
+    {
+      printf ("kqueue() failed.\n");
+      exit (1);
+    }
+#endif
 
   /*
    * Read persistently just like tail -f.
@@ -149,16 +171,37 @@ ttypread (FILE * fp, Header * h, char **buf, int pread)
     {
       fflush(stdout);
       clearerr (fp);
+#ifdef HAVE_KQUEUE
+      EV_SET (&evt[0], STDIN_FILENO, EVFILT_READ, EV_ADD | EV_ONESHOT, 0, 0, NULL);
+      EV_SET (&evt[1], fileno (fp), EVFILT_READ, EV_ADD | EV_ONESHOT, 0, 0, NULL);
+      n = kevent (kq, evt, 2, evt, 1, NULL);
+      doread = (n >= 1 && evt[0].ident == STDIN_FILENO &&
+        evt[0].filter == EVFILT_READ) ||
+        (n >= 2 && evt[1].ident == STDIN_FILENO &&
+        evt[1].filter == EVFILT_READ);
+#else
       if (counter++ > (20 * 60 * 10))
         {
+         /*
+          * The reason for this timeout is that the select() method uses
+          * some CPU in waiting. The kqueue() method does not do that, so it
+          * does not need the timeout.
+          */
           endwin ();
           printf ("Exiting due to 20 minutes of inactivity.\n");
           exit (-23);
         }
       FD_ZERO (&readfs);
       FD_SET (STDIN_FILENO, &readfs);
-      select (1, &readfs, NULL, NULL, &w);
-      if (FD_ISSET (0, &readfs))
+      n = select (1, &readfs, NULL, NULL, &w);
+      doread = n >= 1 && FD_ISSET (0, &readfs);
+#endif
+      if (n == -1)
+       {
+         printf("select()/kevent() failed.\n");
+         exit (1);
+       }
+      if (doread)
         {                       /* user hits a character? */
           char c;
           read (STDIN_FILENO, &c, 1); /* drain the character */