aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Joey Hess <joey@kitenet.net>2012-06-18 12:25:20 -0400
committerGravatar Joey Hess <joey@kitenet.net>2012-06-18 12:25:20 -0400
commit3c8a9043b6fc8fafbeac16e8f9199a0d12870549 (patch)
treed3efa261e61f19b3aea254409cb2c144886f5d05
parent0ecc7dc8927b3840d6a7ba4d39c344f3e962580e (diff)
skeleton C library for calling kqueue
-rw-r--r--.gitignore2
-rw-r--r--Assistant/Watcher.hs12
-rw-r--r--Makefile18
-rw-r--r--Utility/Kqueue.hs31
-rw-r--r--Utility/libkqueue.c22
-rw-r--r--Utility/libkqueue.h1
6 files changed, 75 insertions, 11 deletions
diff --git a/.gitignore b/.gitignore
index d628f23b7..afb5f314e 100644
--- a/.gitignore
+++ b/.gitignore
@@ -11,7 +11,7 @@ html
*.tix
.hpc
Utility/Touch.hs
-Utility/libdiskfree.o
+Utility/*.o
dist
# Sandboxed builds
cabal-dev
diff --git a/Assistant/Watcher.hs b/Assistant/Watcher.hs
index 1d35b5c1e..7c913d98c 100644
--- a/Assistant/Watcher.hs
+++ b/Assistant/Watcher.hs
@@ -33,12 +33,15 @@ import qualified Data.ByteString.Lazy as L
import Utility.Inotify
import System.INotify
#endif
+#ifdef WITH_KQUEUE
+import Utility.Kqueue
+#endif
type Handler = FilePath -> Maybe FileStatus -> DaemonStatusHandle -> Annex (Maybe Change)
checkCanWatch :: Annex ()
checkCanWatch = do
-#ifdef WITH_INOTIFY
+#if (WITH_INOTIFY || WITH_KQUEUE)
unlessM (liftIO (inPath "lsof") <||> Annex.getState Annex.force) $
needLsof
#else
@@ -82,8 +85,13 @@ watchThread st dstatus changechan = withINotify $ \i -> do
, errHook = hook onErr
}
#else
+#ifdef WITH_KQUEUE
+watchThread st dstatus changechan = do
+ print =<< waitChange [stdError, stdOutput]
+#else
watchThread = undefined
-#endif
+#endif /* WITH_KQUEUE */
+#endif /* WITH_INOTIFY */
ignored :: FilePath -> Bool
ignored ".git" = True
diff --git a/Makefile b/Makefile
index 8884b5c64..73fbc4140 100644
--- a/Makefile
+++ b/Makefile
@@ -1,13 +1,22 @@
-OS:=$(shell uname | sed 's/[-_].*//')
+bins=git-annex
+mans=git-annex.1 git-annex-shell.1
+sources=Build/SysConfig.hs Utility/Touch.hs
+all=$(bins) $(mans) docs
+OS:=$(shell uname | sed 's/[-_].*//')
ifeq ($(OS),Linux)
BASEFLAGS_OPTS+=-DWITH_INOTIFY
+clibs=Utility/libdiskfree.o
+else
+BASEFLAGS_OPTS+=-DWITH_KQUEUE
+clibs=Utility/libdiskfree.o Utility/libkqueue.o
endif
PREFIX=/usr
IGNORE=-ignore-package monads-fd -ignore-package monads-tf
BASEFLAGS=-Wall $(IGNORE) -outputdir tmp -IUtility -DWITH_S3 $(BASEFLAGS_OPTS)
GHCFLAGS=-O2 $(BASEFLAGS)
+CFLAGS=-Wall
ifdef PROFILE
GHCFLAGS=-prof -auto-all -rtsopts -caf-all -fforce-recomp $(BASEFLAGS)
@@ -15,13 +24,6 @@ endif
GHCMAKE=ghc $(GHCFLAGS) --make
-bins=git-annex
-mans=git-annex.1 git-annex-shell.1
-sources=Build/SysConfig.hs Utility/Touch.hs
-clibs=Utility/libdiskfree.o
-
-all=$(bins) $(mans) docs
-
# Am I typing :make in vim? Do a fast build.
ifdef VIM
all=fast
diff --git a/Utility/Kqueue.hs b/Utility/Kqueue.hs
new file mode 100644
index 000000000..bfc6ee9fc
--- /dev/null
+++ b/Utility/Kqueue.hs
@@ -0,0 +1,31 @@
+{- BSD kqueue file modification notification interface
+ -
+ - Copyright 2012 Joey Hess <joey@kitenet.net>
+ -
+ - Licensed under the GNU GPL version 3 or higher.
+ -}
+
+{-# LANGUAGE ForeignFunctionInterface #-}
+
+module Utility.Kqueue ( waitChange ) where
+
+import Common
+
+import System.Posix.Types
+import Foreign.C.Types
+import Foreign.C.Error
+import Foreign.Ptr
+import Foreign.Marshal
+
+foreign import ccall unsafe "libkqueue.h waitchange" c_waitchange
+ :: Ptr Fd -> IO Fd
+
+waitChange :: [Fd] -> IO (Maybe Fd)
+waitChange fds = withArray fds $ \c_fds -> do
+ ret <- c_waitchange c_fds
+ ifM (safeErrno <$> getErrno)
+ ( return $ Just ret
+ , return Nothing
+ )
+ where
+ safeErrno (Errno v) = v == 0
diff --git a/Utility/libkqueue.c b/Utility/libkqueue.c
new file mode 100644
index 000000000..0ef42b801
--- /dev/null
+++ b/Utility/libkqueue.c
@@ -0,0 +1,22 @@
+/* kqueue interface, C mini-library
+ *
+ * Copyright 2012 Joey Hess <joey@kitenet.net>
+ *
+ * Licensed under the GNU GPL version 3 or higher.
+ */
+
+#include <errno.h>
+#include <stdio.h>
+
+/* Waits for a change event on one of the array of directory fds,
+ * and returns the one that changed. */
+int waitchange(const int *fds) {
+// if (kqueue(blah, &fds) != 0)
+// return 0; /* errno is set */
+// else
+ errno = 0;
+
+ printf("in waitchange!, %i %i\n", fds[0], fds[1]);
+
+ return fds[0];
+}
diff --git a/Utility/libkqueue.h b/Utility/libkqueue.h
new file mode 100644
index 000000000..75af9eeba
--- /dev/null
+++ b/Utility/libkqueue.h
@@ -0,0 +1 @@
+int waitchange(const int *fds);