diff options
author | alfred <alfred@FreeBSD.org> | 2004-07-14 07:02:03 +0000 |
---|---|---|
committer | alfred <alfred@FreeBSD.org> | 2004-07-14 07:02:03 +0000 |
commit | 9f832c00ba2aa24eade0b2ef01b987cd24e8c55b (patch) | |
tree | cb2d9121acd71de4c8a917a1d42a3c89af1a052c /sys | |
parent | 29fd908e9d3e8beb66f8a8f4c43c3980daddf763 (diff) | |
download | FreeBSD-src-9f832c00ba2aa24eade0b2ef01b987cd24e8c55b.zip FreeBSD-src-9f832c00ba2aa24eade0b2ef01b987cd24e8c55b.tar.gz |
Make FIOASYNC, FIOSETOWN and FIOGETOWN work on kqueues.
Diffstat (limited to 'sys')
-rw-r--r-- | sys/kern/kern_event.c | 31 | ||||
-rw-r--r-- | sys/sys/eventvar.h | 4 |
2 files changed, 32 insertions, 3 deletions
diff --git a/sys/kern/kern_event.c b/sys/kern/kern_event.c index bd0e6d9..4b9a751 100644 --- a/sys/kern/kern_event.c +++ b/sys/kern/kern_event.c @@ -33,10 +33,11 @@ __FBSDID("$FreeBSD$"); #include <sys/lock.h> #include <sys/mutex.h> #include <sys/proc.h> -#include <sys/malloc.h> +#include <sys/malloc.h> #include <sys/unistd.h> #include <sys/file.h> #include <sys/filedesc.h> +#include <sys/filio.h> #include <sys/fcntl.h> #include <sys/selinfo.h> #include <sys/queue.h> @@ -44,6 +45,8 @@ __FBSDID("$FreeBSD$"); #include <sys/eventvar.h> #include <sys/poll.h> #include <sys/protosw.h> +#include <sys/sigio.h> +#include <sys/signalvar.h> #include <sys/socket.h> #include <sys/socketvar.h> #include <sys/stat.h> @@ -811,9 +814,29 @@ kqueue_write(struct file *fp, struct uio *uio, struct ucred *active_cred, /*ARGSUSED*/ static int -kqueue_ioctl(struct file *fp, u_long com, void *data, +kqueue_ioctl(struct file *fp, u_long cmd, void *data, struct ucred *active_cred, struct thread *td) { + struct kqueue *kq; + + kq = fp->f_data; + switch (cmd) { + case FIOASYNC: + if (*(int *)data) { + kq->kq_state |= KQ_ASYNC; + } else { + kq->kq_state &= ~KQ_ASYNC; + } + return (0); + + case FIOSETOWN: + return (fsetown(*(int *)data, &kq->kq_sigio)); + + case FIOGETOWN: + *(int *)data = fgetown(&kq->kq_sigio); + return (0); + } + return (ENOTTY); } @@ -910,6 +933,7 @@ kqueue_close(struct file *fp, struct thread *td) kq->kq_state &= ~KQ_SEL; selwakeuppri(&kq->kq_sel, PSOCK); } + funsetown(&kq->kq_sigio); free(kq, M_KQUEUE); fp->f_data = NULL; @@ -928,6 +952,9 @@ kqueue_wakeup(struct kqueue *kq) kq->kq_state &= ~KQ_SEL; selwakeuppri(&kq->kq_sel, PSOCK); } + if (kq->kq_state & KQ_ASYNC) { + pgsigio(&kq->kq_sigio, SIGIO, 0); + } KNOTE(&kq->kq_sel.si_note, 0); } diff --git a/sys/sys/eventvar.h b/sys/sys/eventvar.h index 3701d44..ef9087b 100644 --- a/sys/sys/eventvar.h +++ b/sys/sys/eventvar.h @@ -35,11 +35,13 @@ struct kqueue { TAILQ_HEAD(kqlist, knote) kq_head; /* list of pending event */ int kq_count; /* number of pending events */ - struct selinfo kq_sel; + struct selinfo kq_sel; + struct sigio *kq_sigio; struct filedesc *kq_fdp; int kq_state; #define KQ_SEL 0x01 #define KQ_SLEEP 0x02 +#define KQ_ASYNC 0x04 struct kevent kq_kev[KQ_NEVENTS]; }; |