words definition
This commit is contained in:
115
tests/forth/definitions.rs
Normal file
115
tests/forth/definitions.rs
Normal file
@@ -0,0 +1,115 @@
|
||||
use super::harness::*;
|
||||
|
||||
#[test]
|
||||
fn define_and_use_word() {
|
||||
expect_int(": double 2 * ; 5 double", 10);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn define_word_with_multiple_ops() {
|
||||
expect_int(": triple dup dup + + ; 3 triple", 9);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn define_word_using_another_user_word() {
|
||||
expect_int(": double 2 * ; : quad double double ; 3 quad", 12);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn redefine_word_overwrites() {
|
||||
expect_int(": foo 10 ; : foo 20 ; foo", 20);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn word_with_param() {
|
||||
let outputs = expect_outputs(": loud 0.9 gain ; \"kick\" s loud emit", 1);
|
||||
assert!(outputs[0].contains("gain/0.9"));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn word_available_across_evaluations() {
|
||||
let f = forth();
|
||||
let ctx = default_ctx();
|
||||
f.evaluate(": hi 42 ;", &ctx).unwrap();
|
||||
f.evaluate("hi", &ctx).unwrap();
|
||||
assert_eq!(stack_int(&f), 42);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn word_defined_in_one_forth_available_in_same() {
|
||||
let f = forth();
|
||||
let ctx = default_ctx();
|
||||
f.evaluate(": ten 10 ;", &ctx).unwrap();
|
||||
f.clear_stack();
|
||||
f.evaluate("ten ten +", &ctx).unwrap();
|
||||
assert_eq!(stack_int(&f), 20);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn unknown_word_errors() {
|
||||
expect_error("nosuchword", "unknown word");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn missing_semicolon_errors() {
|
||||
expect_error(": foo 10", "missing ';'");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn missing_name_errors() {
|
||||
expect_error(":", "expected word name");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn unexpected_semicolon_errors() {
|
||||
expect_error(";", "unexpected ;");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn apply_executes_quotation() {
|
||||
expect_int("5 { 2 * } apply", 10);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn apply_with_stack_ops() {
|
||||
expect_int("3 4 { + } apply", 7);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn apply_empty_stack_errors() {
|
||||
expect_error("apply", "stack underflow");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn apply_non_quotation_errors() {
|
||||
expect_error("42 apply", "expected quotation");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn apply_nested() {
|
||||
expect_int("2 { { 3 * } apply } apply", 6);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn define_word_containing_quotation() {
|
||||
expect_int(": dbl { 2 * } apply ; 7 dbl", 14);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn define_word_with_sound() {
|
||||
let outputs = expect_outputs(": kick \"kick\" s emit ; kick", 1);
|
||||
assert!(outputs[0].contains("sound/kick"));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn define_word_with_conditional() {
|
||||
let f = forth();
|
||||
let ctx = default_ctx();
|
||||
f.evaluate(": maybe-double dup 5 gt if 2 * then ;", &ctx).unwrap();
|
||||
f.clear_stack();
|
||||
f.evaluate("3 maybe-double", &ctx).unwrap();
|
||||
assert_eq!(stack_int(&f), 3);
|
||||
f.clear_stack();
|
||||
f.evaluate("10 maybe-double", &ctx).unwrap();
|
||||
assert_eq!(stack_int(&f), 20);
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
use rand::rngs::StdRng;
|
||||
use rand::SeedableRng;
|
||||
use cagire::model::forth::{Forth, Rng, StepContext, Value, Variables};
|
||||
use cagire::model::forth::{Dictionary, Forth, Rng, StepContext, Value, Variables};
|
||||
use std::collections::HashMap;
|
||||
use std::sync::{Arc, Mutex};
|
||||
|
||||
@@ -29,16 +29,20 @@ pub fn new_vars() -> Variables {
|
||||
Arc::new(Mutex::new(HashMap::new()))
|
||||
}
|
||||
|
||||
pub fn new_dict() -> Dictionary {
|
||||
Arc::new(Mutex::new(HashMap::new()))
|
||||
}
|
||||
|
||||
pub fn seeded_rng(seed: u64) -> Rng {
|
||||
Arc::new(Mutex::new(StdRng::seed_from_u64(seed)))
|
||||
}
|
||||
|
||||
pub fn forth() -> Forth {
|
||||
Forth::new(new_vars(), seeded_rng(42))
|
||||
Forth::new(new_vars(), new_dict(), seeded_rng(42))
|
||||
}
|
||||
|
||||
pub fn forth_seeded(seed: u64) -> Forth {
|
||||
Forth::new(new_vars(), seeded_rng(seed))
|
||||
Forth::new(new_vars(), new_dict(), seeded_rng(seed))
|
||||
}
|
||||
|
||||
pub fn run(script: &str) -> Forth {
|
||||
|
||||
Reference in New Issue
Block a user