|
|
Please consider the following example:
|
|
|
```common-lisp
|
|
|
(require :asdf)
|
|
|
|
|
|
;; these two functions always need to be called before a process goes
|
|
|
;; out of scope and before it can be garbage-collected. otherwise,
|
|
|
;; certain resources may not be returned to the system (causing the
|
|
|
;; system to slow down or eventually become unable to spawn additional
|
|
|
;; external processes)
|
|
|
(defun wait-and-close-streams (process)
|
|
|
(uiop:wait-process process)
|
|
|
(uiop:close-streams process))
|
|
|
|
|
|
(defun bool->string (x)
|
|
|
(if x "T" "F"))
|
|
|
|
|
|
(let ((p9 (uiop:launch-program '("/bin/sleep" "9")))
|
|
|
(p7 (uiop:launch-program '("/bin/sleep" "7")))
|
|
|
(p5 (uiop:launch-program '("/bin/sleep" "5")))
|
|
|
(p3 (uiop:launch-program '("/bin/sleep" "3")))
|
|
|
(p1 (uiop:launch-program '("/bin/sleep" "1"))))
|
|
|
(format t "Waiting for 1s-sleeper to finish sleeping!~%")
|
|
|
(wait-and-close-streams p1)
|
|
|
(format t "1s-sleeper has finished sleeping!~%")
|
|
|
(format t "# Checking: Are the others still sleeping?~%")
|
|
|
(format t "3s-sleeper still sleeping? ~a (expected: T)~%"
|
|
|
(bool->string (uiop:process-alive-p p3)))
|
|
|
(format t "5s-sleeper still sleeping? ~a (expected: T)~%"
|
|
|
(bool->string (uiop:process-alive-p p5)))
|
|
|
(format t "7s-sleeper still sleeping? ~a (expected: T)~%"
|
|
|
(bool->string (uiop:process-alive-p p7)))
|
|
|
(format t "7s-sleeper still sleeping? ~a (expected: T)~%~%"
|
|
|
(bool->string (uiop:process-alive-p p9)))
|
|
|
|
|
|
(format t "Waiting for 5s-sleeper to finish sleeping!~%")
|
|
|
(wait-and-close-streams p5)
|
|
|
(format t "5s-sleeper has finished sleeping!~%")
|
|
|
(format t "# Checking: Are the others still sleeping?~%")
|
|
|
(format t "3s-sleeper still sleeping? ~a (expected: F)~%"
|
|
|
(bool->string (uiop:process-alive-p p3)))
|
|
|
(format t "7s-sleeper still sleeping? ~a (expected: T)~%"
|
|
|
(bool->string (uiop:process-alive-p p7)))
|
|
|
(format t "9s-sleeper still sleeping? ~a (expected: T)~%~%"
|
|
|
(bool->string (uiop:process-alive-p p9)))
|
|
|
(wait-and-close-streams p3)
|
|
|
|
|
|
(format t "Terminating the 9s-sleeper now, then waiting for it!~%")
|
|
|
(uiop:terminate-process p9)
|
|
|
(wait-and-close-streams p9)
|
|
|
(format t "# Checking: Are the others still sleeping?~%")
|
|
|
(format t "7s-sleeper still sleeping? ~a (expected: T)~%~%"
|
|
|
(bool->string (uiop:process-alive-p p7)))
|
|
|
|
|
|
(format t "Finally, killing the last remaining process and exiting~%")
|
|
|
(uiop:terminate-process p7)
|
|
|
(wait-and-close-streams p7))
|
|
|
```
|
|
|
It should generate the following output:
|
|
|
```
|
|
|
Waiting for 1s-sleeper to finish sleeping!
|
|
|
1s-sleeper has finished sleeping!
|
|
|
# Checking: Are the others still sleeping?
|
|
|
3s-sleeper still sleeping? T (expected: T)
|
|
|
5s-sleeper still sleeping? T (expected: T)
|
|
|
7s-sleeper still sleeping? T (expected: T)
|
|
|
7s-sleeper still sleeping? T (expected: T)
|
|
|
|
|
|
Waiting for 5s-sleeper to finish sleeping!
|
|
|
5s-sleeper has finished sleeping!
|
|
|
# Checking: Are the others still sleeping?
|
|
|
3s-sleeper still sleeping? F (expected: F)
|
|
|
7s-sleeper still sleeping? T (expected: T)
|
|
|
9s-sleeper still sleeping? T (expected: T)
|
|
|
|
|
|
Terminating the 9s-sleeper now, then waiting for it!
|
|
|
# Checking: Are the others still sleeping?
|
|
|
7s-sleeper still sleeping? T (expected: T)
|
|
|
|
|
|
Finally, killing the last remaining process and exiting
|
|
|
```
|
|
|
and return with an exit status of 0.
|
|
|
|
|
|
A few more features of `launch-program` are shown in [delta.lisp](https://github.com/epipping/delta-lisp/blob/master/delta.lisp) of [delta-lisp](https://github.com/epipping/delta-lisp). |
|
|
\ No newline at end of file |