From d48456d039bdc0f2dd27690142b77ac1696d3a1d Mon Sep 17 00:00:00 2001 From: Soispha Date: Tue, 26 Mar 2024 17:08:49 +0100 Subject: [PATCH] test(tests): Add the positive tests (and delete the ones in rust) The rust based test were both not sufficient to cover all edge-cases and so unmaintainable that they nearly always didn't even compile. This new test framework should alleviate both concerns. However, one big problem still remains: it does not support test cases that should fail, so these have just been left in the `./tests` directory. --- src/parser/lexing/test.rs | 2 +- src/parser/parsing/checked/mod.rs | 2 - src/parser/parsing/checked/test.rs | 280 ------------------ src/parser/parsing/unchecked/mod.rs | 2 - src/parser/parsing/unchecked/test.rs | 122 -------- tests/.template/expected.md | 202 +++++++++++++ tests/.template/input.tri | 29 ++ tests/.template/main.rs | 17 ++ tests/attribute_doc_comments/expected.md | 74 +++++ tests/attribute_doc_comments/input.tri | 29 ++ tests/attribute_doc_comments/main.rs | 17 ++ tests/derives.tri | 54 ++++ tests/derives_minimal.tri | 6 + tests/doc_comments/expected.md | 0 tests/doc_comments/input.tri | 33 +++ tests/doc_comments/main.rs | 17 ++ tests/empty/expected.md | 0 tests/empty/input.tri | 30 ++ tests/empty/main.rs | 17 ++ tests/failing_derives.tri | 55 ++++ tests/failing_enum_name.tri | 35 +++ tests/failing_types.tri | 30 ++ tests/failing_types_generic.tri | 30 ++ tests/functions/expected.md | 0 tests/functions/input.tri | 31 ++ tests/functions/main.rs | 17 ++ tests/multiple/expected.md | 63 ++++ tests/multiple/input.tri | 31 ++ tests/multiple/main.rs | 17 ++ tests/trinitrix_api/expected.md | 0 .../trinitrix_api/input.tri | 42 ++- tests/trinitrix_api/main.rs | 17 ++ tests/types/expected.md | 0 tests/types/input.tri | 47 +++ tests/types/main.rs | 17 ++ 35 files changed, 949 insertions(+), 416 deletions(-) delete mode 100644 src/parser/parsing/checked/test.rs delete mode 100644 src/parser/parsing/unchecked/test.rs create mode 100644 tests/.template/expected.md create mode 100644 tests/.template/input.tri create mode 100644 tests/.template/main.rs create mode 100644 tests/attribute_doc_comments/expected.md create mode 100644 tests/attribute_doc_comments/input.tri create mode 100644 tests/attribute_doc_comments/main.rs create mode 100644 tests/derives.tri create mode 100644 tests/derives_minimal.tri create mode 100644 tests/doc_comments/expected.md create mode 100644 tests/doc_comments/input.tri create mode 100644 tests/doc_comments/main.rs create mode 100644 tests/empty/expected.md create mode 100644 tests/empty/input.tri create mode 100644 tests/empty/main.rs create mode 100644 tests/failing_derives.tri create mode 100644 tests/failing_enum_name.tri create mode 100644 tests/failing_types.tri create mode 100644 tests/failing_types_generic.tri create mode 100644 tests/functions/expected.md create mode 100644 tests/functions/input.tri create mode 100644 tests/functions/main.rs create mode 100644 tests/multiple/expected.md create mode 100644 tests/multiple/input.tri create mode 100644 tests/multiple/main.rs create mode 100644 tests/trinitrix_api/expected.md rename example/main/src/bin/main/trinitrix_api.tri => tests/trinitrix_api/input.tri (79%) create mode 100644 tests/trinitrix_api/main.rs create mode 100644 tests/types/expected.md create mode 100644 tests/types/input.tri create mode 100644 tests/types/main.rs diff --git a/src/parser/lexing/test.rs b/src/parser/lexing/test.rs index b867f71..880d4ae 100644 --- a/src/parser/lexing/test.rs +++ b/src/parser/lexing/test.rs @@ -19,7 +19,7 @@ * If not, see . */ -use crate::lexing::{Keyword, Token, TokenKind, TokenSpan}; +use crate::parser::lexing::{Keyword, Token, TokenKind, TokenSpan}; use super::TokenStream; diff --git a/src/parser/parsing/checked/mod.rs b/src/parser/parsing/checked/mod.rs index 8557d03..bdb0d60 100644 --- a/src/parser/parsing/checked/mod.rs +++ b/src/parser/parsing/checked/mod.rs @@ -45,8 +45,6 @@ use crate::parser::{ use self::error::{ParsingError, SpannedParsingError}; pub mod error; -#[cfg(test)] -mod test; macro_rules! take_attrs { ($name:expr, $($types:ident),*) => { diff --git a/src/parser/parsing/checked/test.rs b/src/parser/parsing/checked/test.rs deleted file mode 100644 index 86b5bb4..0000000 --- a/src/parser/parsing/checked/test.rs +++ /dev/null @@ -1,280 +0,0 @@ -/* -* Copyright (C) 2023 - 2024: -* The Trinitrix Project -* -* This file is part of the Trixy crate for Trinitrix. -* -* Trixy is free software: you can redistribute it and/or modify -* it under the terms of the Lesser GNU General Public License as -* published by the Free Software Foundation, either version 3 of -* the License, or (at your option) any later version. -* -* This program is distributed in the hope that it will be useful, -* but WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* and the Lesser GNU General Public License along with this program. -* If not, see . -*/ - -use crate::command_spec::checked::{ - Attribute, CommandSpec, DocIdentifier, DocNamedType, Enumeration, Function, Identifier, - NamedType, Namespace, Structure, Type, -}; -use crate::command_spec::Variant; -use crate::lexing::TokenStream; - -use pretty_assertions::assert_eq; - -#[test] -fn test_full() { - let input = " -mod trinitrix { - struct Callback { - func: u32, - timeout: u8, - } - - enum CallbackPriority { - High, - Medium, - Low, - } - - fn execute_callback(callback: Callback, priority: CallbackPriority); -} -"; - let output = TokenStream::lex(&input) - .unwrap() - .parse_unchecked() - .map_err(|err| panic!("{}", err)) - .unwrap() - .process(input.to_owned()) - .map_err(|err| panic!("{}", err)) - .unwrap(); - let expected = CommandSpec { - structures: vec![], - enumerations: vec![], - functions: vec![], - namespaces: vec![Namespace { - name: Identifier { - name: "trinitrix".to_owned(), - variant: Variant::Namespace, - }, - functions: vec![Function { - identifier: Identifier { - name: "execute_callback".to_owned(), - variant: Variant::Function, - }, - inputs: vec![ - NamedType { - name: Identifier { - name: "callback".to_owned(), - variant: Variant::NamedType, - }, - r#type: Type { - identifier: Identifier { - name: "Callback".to_owned(), - variant: Variant::Structure, - }, - generic_args: vec![], - }, - }, - NamedType { - name: Identifier { - name: "priority".to_owned(), - variant: Variant::NamedType, - }, - r#type: Type { - identifier: Identifier { - name: "CallbackPriority".to_owned(), - variant: Variant::Enumeration, - }, - generic_args: vec![], - }, - }, - ], - output: None, - attributes: vec![], - }], - structures: vec![Structure { - identifier: Identifier { - name: "Callback".to_owned(), - variant: Variant::Structure, - }, - contents: vec![ - DocNamedType { - name: Identifier { - name: "func".to_owned(), - variant: Variant::DocNamedType, - }, - r#type: Type { - identifier: Identifier { - name: "u32".to_owned(), - variant: Variant::Primitive, - }, - generic_args: vec![], - }, - attributes: vec![], - }, - DocNamedType { - name: Identifier { - name: "timeout".to_owned(), - variant: Variant::DocNamedType, - }, - r#type: Type { - identifier: Identifier { - name: "u8".to_owned(), - variant: Variant::Primitive, - }, - generic_args: vec![], - }, - attributes: vec![], - }, - ], - attributes: vec![], - }], - enumerations: vec![Enumeration { - identifier: Identifier { - name: "CallbackPriority".to_owned(), - variant: Variant::Enumeration, - }, - states: vec![ - DocIdentifier { - name: "High".to_owned(), - attributes: vec![], - variant: Variant::DocNamedType, - }, - DocIdentifier { - name: "Medium".to_owned(), - attributes: vec![], - variant: Variant::DocNamedType, - }, - DocIdentifier { - name: "Low".to_owned(), - attributes: vec![], - variant: Variant::DocNamedType, - }, - ], - attributes: vec![], - }], - namespaces: vec![], - attributes: vec![], - }], - }; - assert_eq!(output, expected); -} - -#[test] -fn test_failing() { - let input = " -struct Callback { - func: void, - timeout: u32, -} - -// The type \"Name\" should not be defined -fn execute_callback(callback: Name); -"; - let output = TokenStream::lex(&input) - .unwrap() - .parse_unchecked() - .unwrap() - .process(input.to_owned()); - match *(output.unwrap_err().source) { - super::error::ParsingError::TypeNotDeclared { r#type, .. } => { - assert_eq!( - r#type, - Identifier { - name: "void".to_owned(), - variant: Variant::Void, - } - ) - } - _ => panic!("Wrong error in test!"), - }; -} - -#[test] -fn test_comments() { - let input = "fn print(message: String); - -/// First doc comment -// Some more text -mod trinitrix { - /// Second doc comment - fn hi(name: String) -> String; -} -"; - let output = TokenStream::lex(&input) - .unwrap() - .parse_unchecked() - .unwrap() - .process(input.to_owned()) - .unwrap(); - let expected = CommandSpec { - structures: vec![], - enumerations: vec![], - functions: vec![Function { - identifier: Identifier { - name: "print".to_owned(), - variant: Variant::Function, - }, - inputs: vec![NamedType { - name: Identifier { - name: "message".to_owned(), - variant: Variant::NamedType, - }, - r#type: Type { - identifier: Identifier { - name: "String".to_owned(), - variant: Variant::Primitive, - }, - generic_args: vec![], - }, - }], - output: None, - attributes: vec![], - }], - namespaces: vec![Namespace { - name: Identifier { - name: "trinitrix".to_owned(), - variant: Variant::Namespace, - }, - functions: vec![Function { - identifier: Identifier { - name: "hi".to_owned(), - variant: Variant::Function, - }, - inputs: vec![NamedType { - name: Identifier { - name: "name".to_owned(), - variant: Variant::NamedType, - }, - r#type: Type { - identifier: Identifier { - name: "String".to_owned(), - variant: Variant::Primitive, - }, - generic_args: vec![], - }, - }], - output: Some(Type { - identifier: Identifier { - name: "String".to_owned(), - variant: Variant::Primitive, - }, - generic_args: vec![], - }), - attributes: vec![Attribute::doc(" Second doc comment".to_owned())], - }], - structures: vec![], - enumerations: vec![], - namespaces: vec![], - attributes: vec![Attribute::doc(" First doc comment".to_owned())], - }], - }; - assert_eq!(output, expected); -} diff --git a/src/parser/parsing/unchecked/mod.rs b/src/parser/parsing/unchecked/mod.rs index 8201349..949bbe4 100644 --- a/src/parser/parsing/unchecked/mod.rs +++ b/src/parser/parsing/unchecked/mod.rs @@ -36,8 +36,6 @@ use crate::{ use self::error::{ParsingError, SpannedParsingError}; pub mod error; -#[cfg(test)] -mod test; impl TokenStream { pub fn parse_unchecked(self) -> Result { diff --git a/src/parser/parsing/unchecked/test.rs b/src/parser/parsing/unchecked/test.rs deleted file mode 100644 index a44c602..0000000 --- a/src/parser/parsing/unchecked/test.rs +++ /dev/null @@ -1,122 +0,0 @@ -/* -* Copyright (C) 2023 - 2024: -* The Trinitrix Project -* -* This file is part of the Trixy crate for Trinitrix. -* -* Trixy is free software: you can redistribute it and/or modify -* it under the terms of the Lesser GNU General Public License as -* published by the Free Software Foundation, either version 3 of -* the License, or (at your option) any later version. -* -* This program is distributed in the hope that it will be useful, -* but WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* and the Lesser GNU General Public License along with this program. -* If not, see . -*/ - -use pretty_assertions::assert_eq; - -use crate::{ - command_spec::unchecked::{CommandSpec, Function, NamedType, Namespace, Type}, - lexing::{Token, TokenKind, TokenSpan, TokenStream}, -}; - -use super::error::ParsingError; - -#[test] -fn test_failing() { - let input = " -fn print(message: CommandTransferValue); - -mod trinitrix { {} - fn hi honner(name: String) -> String; ; -} - -"; - let parsed = TokenStream::lex(input).unwrap().parse_unchecked(); - let err = parsed.unwrap_err().source; - match *err { - ParsingError::ExpectedKeyword { .. } => {} - _ => panic!("Wrong error"), - } -} - -#[test] -fn test_full() { - let input = "fn print(message: CommandTransferValue); - -mod trinitrix { - fn hi(name: String) -> String; -} -"; - let parsed = TokenStream::lex(input).unwrap().parse_unchecked().unwrap(); - let expected = CommandSpec { - structures: vec![], - enumerations: vec![], - functions: vec![Function { - identifier: Token { - span: TokenSpan { start: 3, end: 8 }, - kind: TokenKind::Identifier("print".to_owned()), - }, - inputs: vec![NamedType { - name: Token { - span: TokenSpan { start: 9, end: 16 }, - kind: TokenKind::Identifier("message".to_owned()), - }, - r#type: Type { - identifier: Token { - span: TokenSpan { start: 18, end: 38 }, - kind: TokenKind::Identifier("CommandTransferValue".to_owned()), - }, - generic_args: vec![], - }, - }], - output: None, - attributes: vec![], - }], - namespaces: vec![Namespace { - name: Token { - span: TokenSpan { start: 46, end: 55 }, - kind: TokenKind::Identifier("trinitrix".to_owned()), - }, - functions: vec![Function { - identifier: Token { - span: TokenSpan { start: 65, end: 67 }, - kind: TokenKind::Identifier("hi".to_owned()), - }, - inputs: vec![NamedType { - name: Token { - span: TokenSpan { start: 68, end: 72 }, - kind: TokenKind::Identifier("name".to_owned()), - }, - r#type: Type { - identifier: Token { - span: TokenSpan { start: 74, end: 80 }, - kind: TokenKind::Identifier("String".to_owned()), - }, - generic_args: vec![], - }, - }], - output: Some(Type { - identifier: Token { - span: TokenSpan { start: 85, end: 91 }, - kind: TokenKind::Identifier("String".to_owned()), - }, - generic_args: vec![], - }), - attributes: vec![], - }], - structures: vec![], - enumerations: vec![], - namespaces: vec![], - attributes: vec![], - }], - }; - - assert_eq!(parsed, expected); -} diff --git a/tests/.template/expected.md b/tests/.template/expected.md new file mode 100644 index 0000000..746dd31 --- /dev/null +++ b/tests/.template/expected.md @@ -0,0 +1,202 @@ +# Host files +File path: `out/dir/api.rs` +```rust +// Host code +/* Rust API */ +#[derive(Debug)] +pub enum Commands { + #[allow(non_camel_case_types)] + print { message: String }, + Trinitrix(trinitrix::Trinitrix), +} +pub mod trinitrix { + #[derive(Debug)] + pub enum Trinitrix { + #[allow(non_camel_case_types)] + hi { trixy_output: trixy::oneshot::Sender, name: String }, + } +} +/* C API */ +#[no_mangle] +pub extern "C" fn print(message: String) -> core::ffi::c_int { + callback_function(print); + return 1; +} +pub mod trinitrix_c {} +#[no_mangle] +pub extern "C" fn trinitrix_hi( + output: *mut trixy::types::String, + name: String, +) -> core::ffi::c_int { + let output_val: trixy::types::String = { + let (tx, rx) = trixy::oneshot::channel(); + callback_function(trinitrix_hi); + let recv = rx + .recv() + .expect("The channel should not be closed until this value is received"); + recv.into() + }; + unsafe { + std::ptr::write(output, output_val); + } + return 1; +} +// vim: filetype=rust +``` + +# Auxiliary files +File path: `dist/interface.h` +```c +#if !defined TRIXY_MAIN_HEADER +#define TRIXY_MAIN_HEADER + +#include "errno.h" +#include "string.h" +#include "vec.h" + +extern int print (const char *message); + +extern int trinitrix_hi (const char **trixy_output, const char *name); + +struct trinitrix +{ + int (*hi) (const char **, const char *); +}; + +const struct trinitrix trinitrix = { + .hi = trinitrix_hi, +}; + +#endif // if !defined TRIXY_MAIN_HEADER +// vim: filetype=c +``` + +File path: `dist/errno.h` +```c +/* + * Copyright (C) 2023 - 2024: + * The Trinitrix Project + * + * This file is part of the Trixy crate for Trinitrix. + * + * Trixy is free software: you can redistribute it and/or modify + * it under the terms of the Lesser GNU General Public License as + * published by the Free Software Foundation, either version 3 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * and the Lesser GNU General Public License along with this program. + * If not, see . + */ + +#ifndef TRIXY_ERRNO_H +#define TRIXY_ERRNO_H +#include + +/** Calculate the number of bytes in the last error's error message **not** + * including any trailing `null` characters. + */ +extern int last_error_length (); + +/** Write the most recent error message into a caller-provided buffer as a + * UTF-8 string, returning the number of bytes written. + * + * # Note + * + * This writes a **UTF-8** string into the buffer. Windows users may need to + * convert it to a UTF-16 “Unicode” afterwards. + * + * If there are no recent errors then this returns `0` (because we wrote 0 + * bytes). `-1` is returned if there are any errors, for example when passed a + * null pointer or a buffer of insufficient size. + */ +extern int last_error_message (char *buffer, uint64_t length); + +#endif // TRIXY_ERRNO_H +``` + +File path: `dist/string.h` +```c +/* + * Copyright (C) 2023 - 2024: + * The Trinitrix Project + * + * This file is part of the Trixy crate for Trinitrix. + * + * Trixy is free software: you can redistribute it and/or modify + * it under the terms of the Lesser GNU General Public License as + * published by the Free Software Foundation, either version 3 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * and the Lesser GNU General Public License along with this program. + * If not, see . + */ + +#ifndef TRIXY_STRING_H +#define TRIXY_STRING_H + +/** + * @brief Frees a rust-allocated string. + */ +extern int string_free (const char *string); + +#endif // TRIXY_STRING_H +``` + +File path: `dist/vec.h` +```c +/* + * Copyright (C) 2023 - 2024: + * The Trinitrix Project + * + * This file is part of the Trixy crate for Trinitrix. + * + * Trixy is free software: you can redistribute it and/or modify + * it under the terms of the Lesser GNU General Public License as + * published by the Free Software Foundation, either version 3 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * and the Lesser GNU General Public License along with this program. + * If not, see . + */ + +#ifndef TRIXY_VEC_H +#define TRIXY_VEC_H +#include + +/** + * @brief A read-only vector from rust. + * + * @detail + * You are must not free it by calling c's `free`. Use `vec_free` + * instead. + */ +struct vec +{ + void *data; + size_t length; +}; + +extern int vec_free (struct vec vector); + +#endif // TRIXY_VEC_H +``` + + diff --git a/tests/.template/input.tri b/tests/.template/input.tri new file mode 100644 index 0000000..67d6721 --- /dev/null +++ b/tests/.template/input.tri @@ -0,0 +1,29 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +fn print(message: String); + +mod trinitrix { + fn hi(name: String) -> String; +} + +// Trixy is sort of a subset of rust +// vim: syntax=rust diff --git a/tests/.template/main.rs b/tests/.template/main.rs new file mode 100644 index 0000000..90bdd3a --- /dev/null +++ b/tests/.template/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn template() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/template/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +} diff --git a/tests/attribute_doc_comments/expected.md b/tests/attribute_doc_comments/expected.md new file mode 100644 index 0000000..0505887 --- /dev/null +++ b/tests/attribute_doc_comments/expected.md @@ -0,0 +1,74 @@ +# Host files +File path: `out/dir/api.rs` +```rust +// Host code +/* Rust API */ +#[derive(Debug)] +pub enum Commands { + #[allow(non_camel_case_types)] + print { message: String }, + Trinitrix(trinitrix::Trinitrix), +} +pub mod trinitrix { + #[derive(Debug)] + pub enum Trinitrix { + #[allow(non_camel_case_types)] + hi { trixy_output: trixy::oneshot::Sender, name: String }, + } +} +/* C API */ +#[no_mangle] +pub extern "C" fn print(message: String) -> core::ffi::c_int { + callback_function(print); + return 1; +} +pub mod trinitrix_c {} +#[no_mangle] +pub extern "C" fn trinitrix_hi( + output: *mut trixy::types::String, + name: String, +) -> core::ffi::c_int { + let output_val: trixy::types::String = { + let (tx, rx) = trixy::oneshot::channel(); + callback_function(trinitrix_hi); + let recv = rx + .recv() + .expect("The channel should not be closed until this value is received"); + recv.into() + }; + unsafe { + std::ptr::write(output, output_val); + } + return 1; +} +// vim: filetype=rust +``` + +# Auxiliary files +File path: `dist/interface.h` +```c +#if !defined TRIXY_MAIN_HEADER +#define TRIXY_MAIN_HEADER + +#include "errno.h" +#include "string.h" +#include "vec.h" + +extern int print (const char *message); + +extern int trinitrix_hi (const char **trixy_output, const char *name); + +struct trinitrix +{ + int (*hi) (const char **, const char *); +}; + +const struct trinitrix trinitrix = { + .hi = trinitrix_hi, +}; + +#endif // if !defined TRIXY_MAIN_HEADER +// vim: filetype=c +``` + + diff --git a/tests/attribute_doc_comments/input.tri b/tests/attribute_doc_comments/input.tri new file mode 100644 index 0000000..3c9b09c --- /dev/null +++ b/tests/attribute_doc_comments/input.tri @@ -0,0 +1,29 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +#[doc = "Attribute doc comment"] +mod trinitrix { + #[doc = r###"Attribute doc comment, but very ##" "## "# " escaped"###] + fn hi(name: String) -> String; +} + +// Trixy is sort of a subset of rust +// vim: syntax=rust diff --git a/tests/attribute_doc_comments/main.rs b/tests/attribute_doc_comments/main.rs new file mode 100644 index 0000000..d651604 --- /dev/null +++ b/tests/attribute_doc_comments/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn attribute_doc_comments() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/attribute_doc_comments/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +} diff --git a/tests/derives.tri b/tests/derives.tri new file mode 100644 index 0000000..dfa2f5e --- /dev/null +++ b/tests/derives.tri @@ -0,0 +1,54 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +/// Call out an outstanding person +fn outstanding(name: String); + +enum DogTraining { + Sheep, + Wolf, + Blind, +} + +#[derive("Error")] +enum TrainingMistake { + GotBitten, +} + +struct Dog { + name: String, +} + +struct TrainedDog { + name: String, + training: DogTraining, +} + +mod one { + /// Say hi to a name + fn hi(name: String) -> String; + + /// Train a dog (if it is there, otherwise do nothing) + fn train_dog(dog: Option) -> Result; +} + +// Trixy is a subset of Rust +// vim: syntax=rust cms=//%s diff --git a/tests/derives_minimal.tri b/tests/derives_minimal.tri new file mode 100644 index 0000000..35ed596 --- /dev/null +++ b/tests/derives_minimal.tri @@ -0,0 +1,6 @@ +#[derive("Error")] +enum A {} + +// This derive should fail (and produce a wrong spanned error) +#[derive("Error")] +mod B {} diff --git a/tests/doc_comments/expected.md b/tests/doc_comments/expected.md new file mode 100644 index 0000000..e69de29 diff --git a/tests/doc_comments/input.tri b/tests/doc_comments/input.tri new file mode 100644 index 0000000..82144c9 --- /dev/null +++ b/tests/doc_comments/input.tri @@ -0,0 +1,33 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +/// First doc comment +// normal comment +mod trinitrix { + // another normal comment + /// Second doc comment + #[doc = "Attribute doc comment"] + #[doc = r###"Attribute doc comment, but very ##" "## "# " escaped"###] + fn hi(name: String) -> String; +} + +// Trixy is sort of a subset of rust +// vim: syntax=rust diff --git a/tests/doc_comments/main.rs b/tests/doc_comments/main.rs new file mode 100644 index 0000000..9f8cda7 --- /dev/null +++ b/tests/doc_comments/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn doc_comments() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/doc_comments/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +} diff --git a/tests/empty/expected.md b/tests/empty/expected.md new file mode 100644 index 0000000..e69de29 diff --git a/tests/empty/input.tri b/tests/empty/input.tri new file mode 100644 index 0000000..411a36b --- /dev/null +++ b/tests/empty/input.tri @@ -0,0 +1,30 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +// an empty comment: +// +/// an empty doc comment: +/// +/// doc comment continued. +mod test {} + +// Trixy is sort of a subset of rust +// vim: syntax=rust diff --git a/tests/empty/main.rs b/tests/empty/main.rs new file mode 100644 index 0000000..9af0de6 --- /dev/null +++ b/tests/empty/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn empty() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/empty/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +} diff --git a/tests/failing_derives.tri b/tests/failing_derives.tri new file mode 100644 index 0000000..df22ea3 --- /dev/null +++ b/tests/failing_derives.tri @@ -0,0 +1,55 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +/// Call out an outstanding person +fn outstanding(name: String); + +enum DogTraining { + Sheep, + Wolf, + Blind, +} + +#[derive("Error")] +enum TrainingMistake { + GotBitten, +} + +struct Dog { + name: String, +} + +struct TrainedDog { + name: String, + training: DogTraining, +} + +#[derive("Error")] +mod one { + /// Say hi to a name + fn hi(name: String) -> String; + + /// Train a dog (if it is there, otherwise do nothing) + fn train_dog(dog: Option) -> Result; +} + +// Trixy is a subset of Rust +// vim: syntax=rust cms=//%s diff --git a/tests/failing_enum_name.tri b/tests/failing_enum_name.tri new file mode 100644 index 0000000..15b3909 --- /dev/null +++ b/tests/failing_enum_name.tri @@ -0,0 +1,35 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +mod trinitrix { + /// This enum can't be called Trinitrix, as that's already the name of the namespace + /// (if it's in Pascal case) + enum Trinitrix { + High, + Medium, + Low, + } + + fn execute_callback(priority: Trinitrix); +} + +// That's a flat out lie, but it results in a rather nice syntax highlight compared to nothing: +// vim: syntax=rust diff --git a/tests/failing_types.tri b/tests/failing_types.tri new file mode 100644 index 0000000..a4c5ca2 --- /dev/null +++ b/tests/failing_types.tri @@ -0,0 +1,30 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +struct Callback { + func: Function, + timeout: Integer, +} + +fn execute_callback(callback: Name); + +// That's a flat out lie, but it results in a rather nice syntax highlight compared to nothing: +// vim: syntax=rust diff --git a/tests/failing_types_generic.tri b/tests/failing_types_generic.tri new file mode 100644 index 0000000..7e7d1c4 --- /dev/null +++ b/tests/failing_types_generic.tri @@ -0,0 +1,30 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +struct A {} +struct B {} + +enum Error {} + +fn execute_callback(callback: String) -> Error; + +// That's a flat out lie, but it results in a rather nice syntax highlight compared to nothing: +// vim: syntax=rust diff --git a/tests/functions/expected.md b/tests/functions/expected.md new file mode 100644 index 0000000..e69de29 diff --git a/tests/functions/input.tri b/tests/functions/input.tri new file mode 100644 index 0000000..e017e0c --- /dev/null +++ b/tests/functions/input.tri @@ -0,0 +1,31 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +/// Call out an outstanding person +fn call_me_back_outstanding(callback: fn(name: String) -> String); + +mod one { + /// Call out a person + fn call_me_back(callback: fn(age: u32)); +} + +// Trixy is sort of a subset of rust +// vim: syntax=rust diff --git a/tests/functions/main.rs b/tests/functions/main.rs new file mode 100644 index 0000000..69850a1 --- /dev/null +++ b/tests/functions/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn functions() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/functions/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +} diff --git a/tests/multiple/expected.md b/tests/multiple/expected.md new file mode 100644 index 0000000..3e4b2cc --- /dev/null +++ b/tests/multiple/expected.md @@ -0,0 +1,63 @@ +# Host files +File path: `out/dir/api.rs` +```rust +// Host code +/* Rust API */ +#[derive(Debug)] +pub enum Commands { + NameOne(name_one::NameOne), +} +pub mod name_one { + #[derive(Debug)] + pub enum NameOne { + #[allow(non_camel_case_types)] + from_first_namespace, + #[allow(non_camel_case_types)] + from_second_namespace, + } +} +/* C API */ +pub mod name_one_c {} +#[no_mangle] +pub extern "C" fn name_one_from_first_namespace() -> core::ffi::c_int { + callback_function(name_one_from_first_namespace); + return 1; +} +#[no_mangle] +pub extern "C" fn name_one_from_second_namespace() -> core::ffi::c_int { + callback_function(name_one_from_second_namespace); + return 1; +} +// vim: filetype=rust +``` + +# Auxiliary files +File path: `dist/interface.h` +```c +#if !defined TRIXY_MAIN_HEADER +#define TRIXY_MAIN_HEADER + +#include "errno.h" +#include "string.h" +#include "vec.h" + +extern int name_one_from_first_namespace (); + +extern int name_one_from_second_namespace (); + +struct name_one +{ + int (*from_first_namespace) (void); + int (*from_second_namespace) (void); +}; + +const struct name_one name_one = { + .from_first_namespace = name_one_from_first_namespace, + .from_second_namespace = name_one_from_second_namespace, +}; + +#endif // if !defined TRIXY_MAIN_HEADER +// vim: filetype=c +``` + + diff --git a/tests/multiple/input.tri b/tests/multiple/input.tri new file mode 100644 index 0000000..a604528 --- /dev/null +++ b/tests/multiple/input.tri @@ -0,0 +1,31 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +mod name_one { + fn from_first_namespace(); +} + +mod name_one { + fn from_second_namespace(); +} + +// Trixy is sort of a subset of rust +// vim: syntax=rust diff --git a/tests/multiple/main.rs b/tests/multiple/main.rs new file mode 100644 index 0000000..9486aff --- /dev/null +++ b/tests/multiple/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn multiple() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/multiple/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +} diff --git a/tests/trinitrix_api/expected.md b/tests/trinitrix_api/expected.md new file mode 100644 index 0000000..e69de29 diff --git a/example/main/src/bin/main/trinitrix_api.tri b/tests/trinitrix_api/input.tri similarity index 79% rename from example/main/src/bin/main/trinitrix_api.tri rename to tests/trinitrix_api/input.tri index 885e471..ea2e5c3 100644 --- a/example/main/src/bin/main/trinitrix_api.tri +++ b/tests/trinitrix_api/input.tri @@ -1,3 +1,24 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + //// Prints to the output, with a newline. // HACK(@soispha): The stdlib Lua `print()` function has stdout as output hardcoded, // redirecting stdout seems too much like a hack thus we are just redefining the print function @@ -34,21 +55,22 @@ mod trinitrix { /// Function that change the UI, or UI state mod ui { - /// Shows the command line - fn command_line_show(); + enum Mode { + /// Default mode (navigation mode) + Normal, + /// Allows you to insert things + Insert, + /// actives the command line + Command + } - /// Hides the command line - fn command_line_hide(); + /// Change the active mode + fn set_mode(mode: Mode); /// Go to the next plane fn cycle_planes(); /// Go to the previous plane fn cycle_planes_rev(); - - /// Sets the current app mode to Normal / navigation mode - fn set_mode_normal(); - /// Sets the current app mode to Insert / editing mode - fn set_mode_insert(); } /// Manipulate keymappings, the mode is specified as a String build up of all mode @@ -114,4 +136,6 @@ mod trinitrix { } } } + +// Trixy is sort of a subset of rust // vim: syntax=rust diff --git a/tests/trinitrix_api/main.rs b/tests/trinitrix_api/main.rs new file mode 100644 index 0000000..06ae62d --- /dev/null +++ b/tests/trinitrix_api/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn trinitrix_api() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/trinitrix_api/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +} diff --git a/tests/types/expected.md b/tests/types/expected.md new file mode 100644 index 0000000..e69de29 diff --git a/tests/types/input.tri b/tests/types/input.tri new file mode 100644 index 0000000..b94f883 --- /dev/null +++ b/tests/types/input.tri @@ -0,0 +1,47 @@ +/* +* Copyright (C) 2023 - 2024: +* The Trinitrix Project +* +* This file is part of the Trixy crate for Trinitrix. +* +* Trixy is free software: you can redistribute it and/or modify +* it under the terms of the Lesser GNU General Public License as +* published by the Free Software Foundation, either version 3 of +* the License, or (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* and the Lesser GNU General Public License along with this program. +* If not, see . +*/ + +mod test { + /// This struct will be used later on (and this is also a struct doc comment test) + struct Callback { + /// Very important field + func: fn(name: String) -> String, + /// Very important field for keeping time constant + timeout: u32, + } + + /// Same thing as above (and a enum doc comment test) + enum CallbackPriority { + /// Callback **now** + High, + /// Maybe do a callback + Medium, + /// Calling back is .. + /// really not important .. + /// like not even think about doing it + Low, + } + + fn execute_callback(callback: Callback, priority: CallbackPriority); +} + +// Trixy is sort of a subset of rust +// vim: syntax=rust diff --git a/tests/types/main.rs b/tests/types/main.rs new file mode 100644 index 0000000..ab5bbfe --- /dev/null +++ b/tests/types/main.rs @@ -0,0 +1,17 @@ +use pretty_assertions::assert_eq; +use trixy::macros::config::{file_tree::FileTree, trixy::TrixyConfig}; + +#[test] +pub fn types() { + let input = include_str!("./expected.md"); + let expected: FileTree = input.parse().unwrap(); + + let config = TrixyConfig::new("callback_function") + .out_dir_path("out/dir") + .trixy_path("./tests/types/input.tri") + .dist_dir_path("dist") + .add_c_headers(false); + + let actual = config.generate(); + assert_eq!(expected, actual); +}