summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Bex <peter@more-magic.net>2012-10-01 18:25:05 +0100
committerPeter Bex <peter@more-magic.net>2012-10-01 18:25:05 +0100
commitae6f4ea76524c69aa701999ab13278193695432a (patch)
tree15d5453d93d25fd4a2a02563353695681ca7a9d4
parentd3cab9cb7d8f2066127db89bc50d38987e393340 (diff)
downloadscsh-process-ae6f4ea76524c69aa701999ab13278193695432a.tar.gz
Implement && and || (which is a bit of a hack in Chicken considering it's the empty symbol)
-rw-r--r--scsh-process.scm10
-rw-r--r--tests/run.scm37
2 files changed, 45 insertions, 2 deletions
diff --git a/scsh-process.scm b/scsh-process.scm
index 63ce220..46a107a 100644
--- a/scsh-process.scm
+++ b/scsh-process.scm
@@ -43,6 +43,7 @@
;; macros
run/collecting run/string run/strings run/port run/file run/sexp run/sexps
+ || &&
(& maybe-symbol->string) (run maybe-symbol->string) (exec-epf maybe-symbol->string))
(import chicken scheme data-structures)
@@ -151,6 +152,13 @@
(syntax-rules ()
((_ ?epf ...) (run/sexps* (lambda () (exec-epf ?epf ...))))))
+(define-syntax &&
+ (syntax-rules ()
+ ((_ ?epf ...) (and (zero? (run ?epf)) ...))))
+(define-syntax ||
+ (syntax-rules ()
+ ((_ ?epf ...) (or (zero? (run ?epf)) ...))))
+
(define-syntax &
(syntax-rules ()
((_ ?epf ...)
@@ -233,7 +241,7 @@
(setup-redirection (= 1 (current-output-port)))
(setup-redirection (= 2 (current-error-port)))
?expr0 ...))
- ((_ (epf ?args ...)) ; TODO: Figure out the point of this
+ ((_ (epf ?args ...)) ; This disambiguates redirection inside && and ||
(exec-epf ?args ...))
;; This is purely for convenience, so you don't need the (epf ...) wrapper
((_ (?prog ?arg0 ...) ?redir0 ...)
diff --git a/tests/run.scm b/tests/run.scm
index c0a2a7e..23220e1 100644
--- a/tests/run.scm
+++ b/tests/run.scm
@@ -51,6 +51,41 @@
"foo\n"
(run/string (pipe+ ((1 0))
(pipe+ ((2 0)) (sh -c "echo foo >&2") (cat))
- (cat)))))
+ (cat))))
+
+ (test "&& runs for all true values"
+ (list #t "bar\n")
+ (list (&& (epf (echo "foo") (> outfile))
+ (true)
+ (epf (echo "bar") (> outfile)))
+ (read-all "outfile")))
+ (delete-file* "outfile")
+
+ (test "&& stops at first false value and returns false"
+ (list #f "foo\n")
+ (list (&& (epf (echo "foo") (> outfile))
+ (false)
+ (epf (echo "bar") (> outfile)))
+ (read-all "outfile")))
+ (delete-file* "outfile")
+
+ (test "|| stops at first true value and returns true"
+ (list #t "foo\n")
+ (list (|| (epf (echo "foo") (> outfile))
+ (true)
+ (epf (echo "bar") (> outfile)))
+ (read-all "outfile")))
+ (delete-file* "outfile")
+
+ (test "|| continues after first false value and returns true"
+ (list #t "bar\n")
+ (list (|| (false)
+ (epf (echo "bar") (> outfile)))
+ (read-all "outfile")))
+ (delete-file* "outfile")
+
+ (test "|| continues beyond all false values and returns false"
+ #f
+ (|| (false) (epf (sh -c "echo hi && false") (- 1)))))
(test-exit) \ No newline at end of file