Next: posix process fork textual, Previous: posix process fork fds, Up: posix process fork [Index]
Wrapper for fork
that sets up the file descriptor pipes and
binary input/output ports to communicate with the child process,
fork. When successful: return the same
return value of fork
; otherwise raise the same exception of
fork
.
The procedure parent-proc is called as follows:
(parent-proc child-pid parent->child-stdin parent<-child-stdout parent<-child-stderr)
where the arguments are the following objects:
child-pid
It is a fixnum representing the pid of the child process.
parent->child-stdin
It is a binary output port writing into the standard input of the child process.
parent<-child-stdout
It is a binary input port reading from the standard output of the child process.
parent<-child-stderr
It is a binary input port reading from the standard error of the child process.
The thunk child-thunk is called with no arguments. The child can
use the standard ports returned by standard-input-port
,
standard-output-port
, standard-error-port
which are made
to wrap standard file descriptors distinct from the parent’s standard
file descriptors.
To be called in the child process, after a fork operation and after
calling after-fork/prepare-child-file-descriptors
to prepare
binary input and output ports wrapping the standard file descriptors.
Return 3 values:
0
.
It is the port returned by standard-input-port
.
1
. It
is the port returned by standard-output-port
.
2
. It
is the port returned by standard-error-port
.
To be called in the parent process, after a fork operation, to build Scheme input and output binary ports around standard file descriptors for the child process. The arguments are:
It must be a file descriptor that writes in the standard input of the child process.
It must be a file descriptor that reads from the standard output of the child process.
It must be must be a file descriptor that reads from the standard error of the child process.
Return 3 values:
Here is an example that forks a process, sets up the file descriptors in the child process, sets up binary ports in both the parent and the child, waits for child to terminate.
(import (vicare) (prefix (vicare posix) px.)) (let-values (((child-stdin parent->child-stdin) (px.pipe)) ((parent<-child-stdout child-stdout) (px.pipe)) ((parent<-child-stderr child-stderr) (px.pipe))) (define (parent-proc child-pid) (px.close child-stdin) (px.close child-stdout) (px.close child-stderr) (receive (child-stdin child-stdout child-stderr) (px.after-fork/prepare-parent-binary-input/output-ports parent->child-stdin parent<-child-stdout parent<-child-stderr) (unwind-protect (let ((bufout (make-bytevector 4 0)) (buferr (make-bytevector 4 0))) (put-bytevector child-stdin '#ve(ascii "ciao\n")) (flush-output-port child-stdin) (let ((status (px.waitpid child-pid 0))) (if (and (px.WIFEXITED status) (zero? (px.WEXITSTATUS status))) (begin (get-bytevector-n! child-stdout bufout 0 4) (get-bytevector-n! child-stderr buferr 0 4) (values bufout buferr)) (error #f "child process exited abnormally" status)))) (close-output-port child-stdin) (close-input-port child-stdout) (close-input-port child-stderr)))) (define (child-thunk) (guard (E (else (print-condition E) (exit 1))) (px.close parent->child-stdin) (px.close parent<-child-stdout) (px.close parent<-child-stderr) (px.after-fork/prepare-child-file-descriptors child-stdin child-stdout child-stderr) (receive (stdin-port stdout-port stderr-port) (px.after-fork/prepare-child-binary-input/output-ports) (let ((buf (make-bytevector 5 0))) (get-bytevector-n! stdin-port buf 0 5) (assert (bytevector=? buf '#ve(ascii "ciao\n"))) (put-bytevector stdout-port '#ve(ascii "out\n")) (put-bytevector stderr-port '#ve(ascii "err\n")) (flush-output-port stdout-port) (flush-output-port stderr-port) (exit 0))))) (flush-output-port (console-output-port)) (flush-output-port (console-error-port)) (px.fork parent-proc child-thunk))
here is the same example using fork-with-binary-ports
:
(import (vicare) (prefix (vicare posix) px.)) (define (parent-proc child-pid child-stdin child-stdout child-stderr) (unwind-protect (let ((bufout (make-bytevector 4 0)) (buferr (make-bytevector 4 0))) (put-bytevector child-stdin '#ve(ascii "ciao\n")) (flush-output-port child-stdin) (let ((status (px.waitpid child-pid 0))) (if (and (px.WIFEXITED status) (zero? (px.WEXITSTATUS status))) (begin (get-bytevector-n! child-stdout bufout 0 4) (get-bytevector-n! child-stderr buferr 0 4) (values bufout buferr)) (error #f "child process exited abnormally" status)))) (close-output-port child-stdin) (close-input-port child-stdout) (close-input-port child-stderr))) (define (child-thunk) (guard (E (else (print-condition E) (exit 1))) (define-constant stdin-port (standard-input-port)) (define-constant stdout-port (standard-output-port)) (define-constant stderr-port (standard-error-port)) (let ((buf (make-bytevector 5 0))) (get-bytevector-n! stdin-port buf 0 5) (assert (bytevector=? buf '#ve(ascii "ciao\n"))) (put-bytevector stdout-port '#ve(ascii "out\n")) (put-bytevector stderr-port '#ve(ascii "err\n")) (flush-output-port stdout-port) (flush-output-port stderr-port) (exit 0)))) (px.fork-with-binary-ports parent-proc child-thunk)
Next: posix process fork textual, Previous: posix process fork fds, Up: posix process fork [Index]