Chris@1706: #!/bin/bash Chris@1706: Chris@1706: # Disable shellcheck warnings for useless-use-of-cat. UUOC is good Chris@1706: # practice, not bad: clearer, safer, less error-prone. Chris@1706: # shellcheck disable=SC2002 Chris@1706: Chris@1706: sml="$VEXT_SML" Chris@1706: Chris@1706: set -eu Chris@1706: Chris@1706: mydir=$(dirname "$0") Chris@1706: program="$mydir/vext.sml" Chris@1706: Chris@1706: # We need one of Poly/ML, SML/NJ, or MLton. Since we're running a Chris@1706: # single-file SML program as if it were a script, our order of Chris@1706: # preference is based on startup speed. Chris@1706: Chris@1706: if [ -z "$sml" ]; then Chris@1718: if sml -h 2>&1 | grep -q 'Standard ML of New Jersey'; then Chris@1718: sml="smlnj" Chris@1706: # I think there may be a race condition in the poly interpreter's Chris@1706: # tests for open or closed I/O streams - without the "echo" here, Chris@1706: # or with stderr redirection, this pipeline will sometimes hang Chris@1718: elif echo | poly -v 2>/dev/null | grep -q 'Poly/ML'; then Chris@1706: sml="poly" Chris@1706: elif mlton 2>&1 | grep -q 'MLton'; then Chris@1706: sml="mlton" Chris@1706: else cat 1>&2 < "$tmp_sml" Chris@1706: echo 'val _ = main ()' >> "$tmp_sml" Chris@1706: mlton -output "$tmp_out" "$tmp_sml" Chris@1706: "$tmp_out" "$@" ;; Chris@1706: smlnj) Chris@1706: cat "$program" | ( Chris@1706: cat < (), flush = fn () => () }; Chris@1706: x Chris@1706: end; Chris@1706: val smlrun__prev = ref ""; Chris@1706: Control.Print.out := { Chris@1706: say = fn s => Chris@1706: (if String.isSubstring " Error" s Chris@1706: then (Control.Print.out := smlrun__cp; Chris@1706: (#say smlrun__cp) (!smlrun__prev); Chris@1706: (#say smlrun__cp) s) Chris@1706: else (smlrun__prev := s; ())), Chris@1706: flush = fn s => () Chris@1706: }; Chris@1706: EOF Chris@1706: cat - Chris@1706: cat < "$tmp_sml" Chris@1706: CM_VERBOSE=false sml "$tmp_sml" ;; Chris@1706: *) Chris@1706: echo "Unknown SML implementation name: $sml"; Chris@1706: exit 2 ;; Chris@1706: esac Chris@1706: