diff options
author | jkim <jkim@FreeBSD.org> | 2012-04-16 21:22:02 +0000 |
---|---|---|
committer | jkim <jkim@FreeBSD.org> | 2012-04-16 21:22:02 +0000 |
commit | e210f689a88fc9c69c2a71393cc5e81321bd8320 (patch) | |
tree | 0929b9d6ba911ed85df4be1049f50e0052c10a5d /sys/kern | |
parent | 10552859c1b4a35e872654ec21f766ebac5186ee (diff) | |
download | FreeBSD-src-e210f689a88fc9c69c2a71393cc5e81321bd8320.zip FreeBSD-src-e210f689a88fc9c69c2a71393cc5e81321bd8320.tar.gz |
- Implement pipe2 syscall for Linuxulator. This syscall appeared in 2.6.27
but GNU libc used it without checking its kernel version, e. g., Fedora 10.
- Move pipe(2) implementation for Linuxulator from MD files to MI file,
sys/compat/linux/linux_file.c. There is no MD code for this syscall at all.
- Correct an argument type for pipe() from l_ulong * to l_int *. Probably
this was the source of MI/MD confusion.
Reviewed by: emulation
Diffstat (limited to 'sys/kern')
-rw-r--r-- | sys/kern/sys_pipe.c | 24 |
1 files changed, 19 insertions, 5 deletions
diff --git a/sys/kern/sys_pipe.c b/sys/kern/sys_pipe.c index 6719bda..43c39fc 100644 --- a/sys/kern/sys_pipe.c +++ b/sys/kern/sys_pipe.c @@ -129,6 +129,9 @@ __FBSDID("$FreeBSD$"); #include <vm/vm_page.h> #include <vm/uma.h> +/* XXX */ +int do_pipe(struct thread *td, int fildes[2], int flags); + /* * Use this define if you want to disable *fancy* VM things. Expect an * approx 30% decrease in transfer rate. This could be useful for @@ -405,11 +408,18 @@ pipe_dtor(struct pipe *dpipe) int kern_pipe(struct thread *td, int fildes[2]) { + + return (do_pipe(td, fildes, 0)); +} + +int +do_pipe(struct thread *td, int fildes[2], int flags) +{ struct filedesc *fdp; struct file *rf, *wf; struct pipe *rpipe, *wpipe; struct pipepair *pp; - int fd, error; + int fd, fflags, error; fdp = td->td_proc->p_fd; error = pipe_paircreate(td, &pp); @@ -417,7 +427,7 @@ kern_pipe(struct thread *td, int fildes[2]) return (error); rpipe = &pp->pp_rpipe; wpipe = &pp->pp_wpipe; - error = falloc(td, &rf, &fd, 0); + error = falloc(td, &rf, &fd, flags); if (error) { pipeclose(rpipe); pipeclose(wpipe); @@ -426,14 +436,18 @@ kern_pipe(struct thread *td, int fildes[2]) /* An extra reference on `rf' has been held for us by falloc(). */ fildes[0] = fd; + fflags = FREAD | FWRITE; + if ((flags & O_NONBLOCK) != 0) + fflags |= FNONBLOCK; + /* * Warning: once we've gotten past allocation of the fd for the * read-side, we can only drop the read side via fdrop() in order * to avoid races against processes which manage to dup() the read * side while we are blocked trying to allocate the write side. */ - finit(rf, FREAD | FWRITE, DTYPE_PIPE, rpipe, &pipeops); - error = falloc(td, &wf, &fd, 0); + finit(rf, fflags, DTYPE_PIPE, rpipe, &pipeops); + error = falloc(td, &wf, &fd, flags); if (error) { fdclose(fdp, rf, fildes[0], td); fdrop(rf, td); @@ -442,7 +456,7 @@ kern_pipe(struct thread *td, int fildes[2]) return (error); } /* An extra reference on `wf' has been held for us by falloc(). */ - finit(wf, FREAD | FWRITE, DTYPE_PIPE, wpipe, &pipeops); + finit(wf, fflags, DTYPE_PIPE, wpipe, &pipeops); fdrop(wf, td); fildes[1] = fd; fdrop(rf, td); |