diff --git a/crates/.cargo/config.toml b/crates/.cargo/config.toml index c44af23b..10dbe3f8 100644 --- a/crates/.cargo/config.toml +++ b/crates/.cargo/config.toml @@ -1,4 +1,5 @@ [target.thumbv7em-none-eabihf] +runner = "../tools/cargo-runner.sh" rustflags = [ # CPU is Cortex-M4 (STM32WB55) "-C", "target-cpu=cortex-m4", diff --git a/crates/flipperzero/Cargo.toml b/crates/flipperzero/Cargo.toml index b6435252..52085ec7 100644 --- a/crates/flipperzero/Cargo.toml +++ b/crates/flipperzero/Cargo.toml @@ -18,7 +18,7 @@ all-features = true [lib] bench = false -test = false +harness = false [dependencies] flipperzero-sys.workspace = true diff --git a/crates/flipperzero/src/lib.rs b/crates/flipperzero/src/lib.rs index 9a1bacb6..ceae86d9 100644 --- a/crates/flipperzero/src/lib.rs +++ b/crates/flipperzero/src/lib.rs @@ -1,6 +1,7 @@ //! High-level bindings for the Flipper Zero. #![no_std] +#![cfg_attr(test, no_main)] #[cfg(feature = "alloc")] extern crate alloc; @@ -16,3 +17,56 @@ pub mod __internal { // Re-export for use in macros pub use ufmt; } + +// Infrastructure for running unit tests. +#[cfg(test)] +mod tests { + // Required for panic handler + extern crate flipperzero_rt; + + // Required for allocator + #[cfg(feature = "alloc")] + extern crate flipperzero_alloc; + + use core::time::Duration; + + use flipperzero_rt::{entry, manifest}; + use flipperzero_sys as sys; + + use crate::{furi::thread, println}; + + manifest!(name = "Rust Unit Tests"); + entry!(main); + + // Test runner entry point + fn main(_args: *mut u8) -> i32 { + let heap_before = unsafe { sys::memmgr_get_free_heap() }; + let cycle_counter = unsafe { sys::furi_get_tick() }; + + // TODO: Collect and run tests + let failed = 0; + + println!(""); + println!("Failed tests: {}\r", failed); + + // Time report + println!( + "Consumed: {} ms\r", + unsafe { sys::furi_get_tick() } - cycle_counter + ); + + // Wait for tested services and apps to deallocate memory + thread::sleep(Duration::from_millis(200)); + let heap_after = unsafe { sys::memmgr_get_free_heap() }; + println!("Leaked: {}\r", heap_before - heap_after); + + // Final Report + if failed == 0 { + println!("Status: PASSED\r"); + 0 + } else { + println!("Status: FAILED\r"); + 1 + } + } +} diff --git a/tools/cargo-runner.sh b/tools/cargo-runner.sh new file mode 100755 index 00000000..538be258 --- /dev/null +++ b/tools/cargo-runner.sh @@ -0,0 +1,11 @@ +#!/usr/bin/env bash + +# Figure out where this script is located (which is also where the tools are). +SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd ) + +# Change directory to the tools directory, to ensure the CWD doesn't contain any +# .cargo/config files that would prevent us from building on the host machine. +cd $SCRIPT_DIR + +# Run the given FAP binary on a connected Flipper Zero. +cargo run --quiet --release --bin run-fap -- $@