diff --git a/crates/kind-pass/src/unbound/mod.rs b/crates/kind-pass/src/unbound/mod.rs index 55d3346c..3b7c9a72 100644 --- a/crates/kind-pass/src/unbound/mod.rs +++ b/crates/kind-pass/src/unbound/mod.rs @@ -258,8 +258,10 @@ impl Visitor for UnboundCollector { TopLevel::RecordType(entr) => { let inside_vars = self.context_vars.clone(); visit_vec!(entr.parameters.iter_mut(), arg => self.visit_argument(arg)); - visit_vec!(entr.fields.iter_mut(), (_, _, typ) => { + + visit_vec!(entr.fields.iter_mut(), (name, _, typ) => { self.visit_expr(typ); + self.context_vars.push((name.range, name.to_string())) }); self.context_vars = inside_vars; diff --git a/crates/kind-tests/suite/checker/issues/RecordFieldDependency.golden b/crates/kind-tests/suite/checker/issues/RecordFieldDependency.golden new file mode 100644 index 00000000..db814b93 --- /dev/null +++ b/crates/kind-tests/suite/checker/issues/RecordFieldDependency.golden @@ -0,0 +1 @@ +Ok! \ No newline at end of file diff --git a/crates/kind-tests/suite/checker/issues/RecordFieldDependency.kind2 b/crates/kind-tests/suite/checker/issues/RecordFieldDependency.kind2 new file mode 100644 index 00000000..a8a6ea53 --- /dev/null +++ b/crates/kind-tests/suite/checker/issues/RecordFieldDependency.kind2 @@ -0,0 +1,4 @@ +record FieldDependency { + ty : Type + snd : ty +} \ No newline at end of file diff --git a/crates/kind-tests/suite/erasure/Ignores.golden b/crates/kind-tests/suite/erasure/Ignores.golden new file mode 100644 index 00000000..abb01985 --- /dev/null +++ b/crates/kind-tests/suite/erasure/Ignores.golden @@ -0,0 +1,2 @@ + +Main = 3 diff --git a/crates/kind-tests/suite/erasure/Ignores.kind2 b/crates/kind-tests/suite/erasure/Ignores.kind2 new file mode 100644 index 00000000..15ee95a9 --- /dev/null +++ b/crates/kind-tests/suite/erasure/Ignores.kind2 @@ -0,0 +1,5 @@ +Kek : U60 +Kek a = a + +Main : U60 +Main = 3 \ No newline at end of file diff --git a/crates/kind-tests/suite/erasure/Removes.golden b/crates/kind-tests/suite/erasure/Removes.golden new file mode 100644 index 00000000..711b7a9e --- /dev/null +++ b/crates/kind-tests/suite/erasure/Removes.golden @@ -0,0 +1,6 @@ + +Main = (Kuk) + +Kuk = (Kek 3) + +Kek a = a diff --git a/crates/kind-tests/suite/erasure/Removes.kind2 b/crates/kind-tests/suite/erasure/Removes.kind2 new file mode 100644 index 00000000..7b3bb0ea --- /dev/null +++ b/crates/kind-tests/suite/erasure/Removes.kind2 @@ -0,0 +1,8 @@ +Kek (a: U60) : U60 +Kek a = a + +Main : U60 +Main = (Kuk) ~(20) + +Kuk : ~(a : U60) -> U60 +Kuk = ~x => Kek 3 diff --git a/crates/kind-tests/suite/erasure/fail/ErrInType.golden b/crates/kind-tests/suite/erasure/fail/ErrInType.golden new file mode 100644 index 00000000..9e63dc14 --- /dev/null +++ b/crates/kind-tests/suite/erasure/fail/ErrInType.golden @@ -0,0 +1,10 @@ + ERROR This irrelevant parameter should not be used in a relevant position. + + /--[suite/erasure/fail/ErrInType.kind2:2:8] + | + 1 | Main : Type + 2 | Main = Type + | v--- + | \It's in relevant position! + + diff --git a/crates/kind-tests/suite/erasure/fail/ErrInType.kind2 b/crates/kind-tests/suite/erasure/fail/ErrInType.kind2 new file mode 100644 index 00000000..683a779a --- /dev/null +++ b/crates/kind-tests/suite/erasure/fail/ErrInType.kind2 @@ -0,0 +1,2 @@ +Main : Type +Main = Type \ No newline at end of file diff --git a/crates/kind-tests/suite/erasure/fail/ShouldErr.golden b/crates/kind-tests/suite/erasure/fail/ShouldErr.golden new file mode 100644 index 00000000..13f76cad --- /dev/null +++ b/crates/kind-tests/suite/erasure/fail/ShouldErr.golden @@ -0,0 +1,11 @@ + ERROR This irrelevant parameter should not be used in a relevant position. + + /--[suite/erasure/fail/ShouldErr.kind2:2:9] + | + 1 | Kek : U60 + 2 | Kek a = a + | v + | \It's in relevant position! + 3 | + + diff --git a/crates/kind-tests/suite/erasure/fail/ShouldErr.kind2 b/crates/kind-tests/suite/erasure/fail/ShouldErr.kind2 new file mode 100644 index 00000000..58884a8c --- /dev/null +++ b/crates/kind-tests/suite/erasure/fail/ShouldErr.kind2 @@ -0,0 +1,8 @@ +Kek : U60 +Kek a = a + +Main : U60 +Main = (Kuk) ~(20) + +Kuk : ~(a : U60) -> U60 +Kuk = ~x => Kek 3 diff --git a/crates/kind-tests/tests/mod.rs b/crates/kind-tests/tests/mod.rs index 2a7b9faf..5b561a4e 100644 --- a/crates/kind-tests/tests/mod.rs +++ b/crates/kind-tests/tests/mod.rs @@ -13,7 +13,7 @@ use walkdir::{Error, WalkDir}; use kind_driver as driver; -fn golden_test(path: &Path, run: fn(&Path) -> String) { +fn golden_test(path: &Path, run: &dyn Fn(&Path) -> String) { let result = run(path); let golden_path = path.with_extension("golden"); @@ -25,12 +25,36 @@ fn golden_test(path: &Path, run: fn(&Path) -> String) { } } -fn test_kind2(path: &Path, run: fn(&Path) -> String) -> Result<(), Error> { +fn test_kind2(path: &Path, run: fn(&PathBuf, &mut Session) -> Option) -> Result<(), Error> { for entry in WalkDir::new(path).follow_links(true) { let entry = entry?; let path = entry.path(); if path.is_file() && path.extension().map(|x| x == "kind2").unwrap_or(false) { - golden_test(path, run); + golden_test(path, &|path| { + let (rx, tx) = std::sync::mpsc::channel(); + let root = PathBuf::from("./suite/lib").canonicalize().unwrap(); + let mut session = Session::new(root, rx); + + let res = run(&PathBuf::from(path), &mut session); + + let diagnostics = tx.try_iter().collect::>>(); + let render = RenderConfig::ascii(2); + + kind_report::check_if_colors_are_supported(true); + + match res { + Some(res) if diagnostics.is_empty() => res, + _ => { + let mut res_string = String::new(); + + for diag in diagnostics { + diag.render(&session, &render, &mut res_string).unwrap(); + } + + res_string + } + } + }); } } Ok(()) @@ -39,31 +63,10 @@ fn test_kind2(path: &Path, run: fn(&Path) -> String) -> Result<(), Error> { #[test] #[timeout(30000)] fn test_checker() -> Result<(), Error> { - test_kind2(Path::new("./suite/checker"), |path| { - let (rx, tx) = std::sync::mpsc::channel(); - let root = PathBuf::from("./suite/lib").canonicalize().unwrap(); - let mut session = Session::new(root, rx); - + test_kind2(Path::new("./suite/checker"), |path, session| { let entrypoints = vec!["Main".to_string()]; - let check = driver::type_check_book(&mut session, &PathBuf::from(path), entrypoints, Some(1)); - - let diagnostics = tx.try_iter().collect::>>(); - let render = RenderConfig::ascii(2); - - kind_report::check_if_colors_are_supported(true); - - match check { - Ok(_) if diagnostics.is_empty() => "Ok!".to_string(), - _ => { - let mut res_string = String::new(); - - for diag in diagnostics { - diag.render(&mut session, &render, &mut res_string).unwrap(); - } - - res_string - } - } + let check = driver::type_check_book(session, path, entrypoints, Some(1)); + check.map(|_| "Ok!".to_string()).ok() })?; Ok(()) } @@ -71,69 +74,35 @@ fn test_checker() -> Result<(), Error> { #[test] #[timeout(15000)] fn test_eval() -> Result<(), Error> { - test_kind2(Path::new("./suite/eval"), |path| { - let (rx, tx) = std::sync::mpsc::channel(); - let root = PathBuf::from("./suite/lib").canonicalize().unwrap(); - let mut session = Session::new(root, rx); - + test_kind2(Path::new("./suite/eval"), |path, session| { let entrypoints = vec!["Main".to_string()]; - let check = driver::erase_book(&mut session, &PathBuf::from(path), entrypoints) - .map(|x| driver::compile_book_to_hvm(x, false)); + let check = driver::erase_book(session, path, entrypoints) + .map(|file| driver::compile_book_to_hvm(file, false)) + .map(|file| driver::execute_file(&file.to_string(), Some(1)).map_or_else(|e| e, |f| f)); - let diagnostics = tx.try_iter().collect::>(); - let render = RenderConfig::ascii(2); - - kind_report::check_if_colors_are_supported(true); - - match check { - Ok(file) if diagnostics.is_empty() => { - driver::execute_file(&file.to_string(), Some(1)).map_or_else(|e| e, |f| f) - } - _ => { - let mut res_string = String::new(); - - for diag in diagnostics { - diag.render(&mut session, &render, &mut res_string).unwrap(); - } - - res_string - } - } + check.ok() })?; Ok(()) } - #[test] #[timeout(15000)] fn test_kdl() -> Result<(), Error> { - test_kind2(Path::new("./suite/kdl"), |path| { - let (rx, tx) = std::sync::mpsc::channel(); - let root = PathBuf::from("./suite/lib").canonicalize().unwrap(); - let mut session = Session::new(root, rx); - + test_kind2(Path::new("./suite/kdl"), |path, session| { let entrypoints = vec!["Main".to_string()]; - let check = driver::compile_book_to_kdl(&PathBuf::from(path), &mut session, "", entrypoints); - - let diagnostics = tx.try_iter().collect::>(); - let render = RenderConfig::ascii(2); - - kind_report::check_if_colors_are_supported(true); - - match check { - Ok(file) if diagnostics.is_empty() => { - file.to_string() - }, - _ => { - let mut res_string = String::new(); - - for diag in diagnostics { - diag.render(&mut session, &render, &mut res_string).unwrap(); - } - - res_string - } - } + let check = driver::compile_book_to_kdl(path, session, "", entrypoints); + check.ok().map(|x| x.to_string()) + })?; + Ok(()) +} + +#[test] +#[timeout(15000)] +fn test_erasure() -> Result<(), Error> { + test_kind2(Path::new("./suite/erasure"), |path, session| { + let entrypoints = vec!["Main".to_string()]; + let check = driver::erase_book(session, path, entrypoints).map(|file| file.to_string()); + check.ok() })?; Ok(()) }