diff --git a/LICENSE b/LICENSE
new file mode 100644
index 00000000..03b1fa90
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,21 @@
+MIT License
+
+Copyright (c) 2019 Brown University, Tim Nelson, and Forge contributors
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/forge/examples/sudoku_opt_viz/sudoku_unrolled.frg b/forge/examples/sudoku_opt_viz/sudoku_unrolled.frg
index 0e5e6221..fc435a45 100644
--- a/forge/examples/sudoku_opt_viz/sudoku_unrolled.frg
+++ b/forge/examples/sudoku_opt_viz/sudoku_unrolled.frg
@@ -48,7 +48,7 @@ fun get_grid[s: BoardState, subgrid: Int]: set Int {
s.board[rows][cols]
}
-pred solution[s: PuzzleState] {
+pred solution[s: BoardState] {
-- ** Rows and Columns **
-- don't use #... = 9 here; instead something like:
all r: values | s.board[r][Int] = values
diff --git a/forge/examples/sudoku_opt_viz/sudoku_with_inst.frg b/forge/examples/sudoku_opt_viz/sudoku_with_inst.frg
index 60fd7558..19b29d6d 100644
--- a/forge/examples/sudoku_opt_viz/sudoku_with_inst.frg
+++ b/forge/examples/sudoku_opt_viz/sudoku_with_inst.frg
@@ -45,7 +45,7 @@ fun values: set Int {
1 + 2 + 3 + 4 + 5 + 6 + 7 + 8 + 9
}
-pred solution[s: PuzzleState] {
+pred solution[s: BoardState] {
-- ** Rows and Columns **
-- don't use #... = 9 here; instead something like:
all r: values | s.board[r][Int] = values
diff --git a/forge/examples/sudoku_opt_viz/sudoku_with_inst_2.frg b/forge/examples/sudoku_opt_viz/sudoku_with_inst_2.frg
index 779df0d4..c1efc4ee 100644
--- a/forge/examples/sudoku_opt_viz/sudoku_with_inst_2.frg
+++ b/forge/examples/sudoku_opt_viz/sudoku_with_inst_2.frg
@@ -46,7 +46,7 @@ fun get_grid[s: BoardState, row_offset, col_offset: Int]: set Int {
s.board[rows][cols]
}
-pred solution[s: PuzzleState] {
+pred solution[s: BoardState] {
-- ** Rows and Columns **
-- don't use #... = 9 here; instead something like:
all r: Helper.values | s.board[r][Int] = Helper.values
diff --git a/forge/run-tests.sh b/forge/run-tests.sh
index 57bb8e95..891c7919 100755
--- a/forge/run-tests.sh
+++ b/forge/run-tests.sh
@@ -35,8 +35,9 @@ for testFile in $testFiles; do
current=`date "+%X"`
echo -e "\nRunning $testFile ($current)"
- #start=`date +%s`
- racket $testFile > /dev/null
+ #start=`date +%s`
+ # Use permanent (-O) option flag to always disable Sterling
+ racket $testFile -O run_sterling \'off > /dev/null
#end=`date +%s`
#echo -e "Testfile took $((end-start)) seconds."
testExitCode=$?
diff --git a/forge/sigs.rkt b/forge/sigs.rkt
index 575ca3fa..94260967 100644
--- a/forge/sigs.rkt
+++ b/forge/sigs.rkt
@@ -176,9 +176,14 @@
(struct-copy State state
[inst-map new-state-inst-map]))
+; this is not managed by Forge's "rolling state"; it should only be set by the command-line.
+(define option-overrides (box '()))
+
(define (set-option! option value #:original-path [original-path #f])
- (cond [(or (equal? option 'verbosity)
- (equal? option 'verbose))
+ (cond [(member option (unbox option-overrides))
+ (printf "Option ~a was given when Forge started with --override option; ignoring assignment to ~a.~n"
+ option value)]
+ [(or (equal? option 'verbosity) (equal? option 'verbose))
(set-verbosity value)]
[else
(update-state! (state-set-option curr-state option value #:original-path original-path))]))
@@ -1133,3 +1138,75 @@
(provide output-all-test-failures
report-test-failure
reset-test-failures!)
+
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+; Support for providing options at the command line
+; sigs-structs.rkt provides an `option-types` value that
+; we can use to cast inputs to the appropriate type.
+;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+
+; The lowercase -o will set an initial option value, but will be OVERRIDDEN
+; by file-level option statements. E.g., this at the command line (note the
+; need to escape the backquote):
+; racket ring_of_lights.frg -o run_sterling \'off -o verbose 1
+; * will NOT run sterling (because the example doesn't give a value for that option)
+; * WILL give verbose 5 output (because the example gives a value of 5 for that option)
+
+; In contrast, the uppercase -O will set the initial option value and disallow it changing.
+; E.g.,
+; racket ring_of_lights.frg -o run_sterling \'off -O verbose 1
+; will give verbose 1 output.
+
+(define (string->option-type name value)
+ (define type-pred (hash-ref option-types name #f))
+ (cond
+ ; Arrived as a number
+ [(string->number value) (string->number value)]
+ ; Arrived as a single-quote prefixed symbol
+ [(equal? (string-ref value 0) #\') (string->symbol (substring value 1))]
+ ; Otherwise, try to infer from the type predicate for the option
+ [(equal? type-pred symbol?) (string->symbol value)]
+ [(equal? type-pred exact-nonnegative-integer?) (string->number value)]
+ [(equal? type-pred exact-positive-integer?) (string->number value)]
+ [(equal? type-pred exact-integer?) (string->number value)]
+ ; This covers too much at the moment (some of the option-types values are /more complex predicates/)
+ [else value]))
+
+(require racket/cmdline)
+
+;; BEWARE: this appears to interact with `raco` when installing the Forge package. E.g.,
+;; printing out `remaining-args` will actually print something when installing Forge, but
+;; with arguments from `raco`:
+;; cl result: (pkg install ./forge ./froglet)
+;; This could technically cause a conflict with any existing `raco` arguments.
+;; -o and -O are not used by `raco pkg install` as of June 14, 2024.
+
+(define remaining-args (command-line
+ ; Default:
+ ;#:program (find-system-path 'run-file)
+ ; Default:
+ ;#:argv (current-command-line-arguments)
+ #:usage-help
+ "When running Forge from the command line, use the -o or --option flag to send options."
+ "Format: -o