Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
97 changes: 97 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
name: CI

on:
pull_request:
push:
branches: [master]

env:
CARGO_TERM_COLOR: always

jobs:
fmt:
name: rustfmt
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@stable
with:
components: rustfmt
- run: cargo fmt --check
- run: cargo fmt --manifest-path nostd-test/Cargo.toml --check

clippy:
name: clippy
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@stable
with:
components: clippy
targets: thumbv7m-none-eabi
- run: cargo clippy --all-targets -- -D warnings
- run: cargo clippy --manifest-path nostd-test/Cargo.toml --target thumbv7m-none-eabi --all-targets -- -D warnings

test:
name: test, doc, examples
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@stable
- run: cargo test -- --test-threads=1
- run: cargo doc --no-deps
- run: cargo run --example helloworld
- run: cargo run --example futures_chain
- run: cargo run --example multi_async_std
- run: cargo run --example signal

msrv:
name: msrv 1.63
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@1.63.0
with:
targets: wasm32-unknown-unknown,thumbv7m-none-eabi
- name: library and no_std targets on 1.63
run: |
# `cargo test` also builds the async-std example stack, whose current
# crates need a newer rustc. The library itself does not.
cargo build --lib
cargo check --target wasm32-unknown-unknown --lib
cargo check --target thumbv7m-none-eabi --lib

nostd:
name: no_std build and qemu
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@stable
with:
targets: wasm32-unknown-unknown,thumbv7m-none-eabi
- name: install qemu
run: sudo apt-get update && sudo apt-get install -y qemu-system-arm
- name: check library on no_std targets
run: |
cargo check --target wasm32-unknown-unknown --lib
cargo check --target thumbv7m-none-eabi --lib
- name: run bare-metal tests under qemu
run: |
cargo build --manifest-path nostd-test/Cargo.toml --release --target thumbv7m-none-eabi
qemu-system-arm \
-cpu cortex-m3 \
-machine lm3s6965evb \
-nographic \
-semihosting-config enable=on,target=native \
-kernel nostd-test/target/thumbv7m-none-eabi/release/executor-nostd-test

miri:
name: miri
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: dtolnay/rust-toolchain@nightly
with:
components: miri
- run: cargo miri setup
- run: cargo miri test -- --test-threads=1
6 changes: 5 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,11 @@ rust-version="1.63"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html

[dependencies]
spin = "0"
# 0.9.9 is the newest `spin` that still builds on the declared MSRV (1.63).
# Newer 0.x releases pull `lock_api` versions that need Rust 1.71+.
# Only the raw spin mutex is used; `lock_api` stays off so that dependency
# cannot bump the MSRV.
spin = { version = "0.9.9", default-features = false, features = ["mutex", "spin_mutex", "lazy"] }

[dev-dependencies]
async-std = "1"
41 changes: 41 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,47 @@ fn main() {
}
```

## Testing / platform support

Host tests cover completion, `is_done`, nested `add_async`, `wake` and `wake_by_ref` (including wakes from another thread), waking during poll, drop of finished tasks, and a short many-wake stress run.

```bash
cargo test -- --test-threads=1
cargo clippy --all-targets -- -D warnings
cargo fmt --check
cargo doc --no-deps
cargo +nightly miri test -- --test-threads=1
```

The library builds on the declared MSRV, Rust 1.63:

```bash
cargo +1.63.0 build --lib
cargo +1.63.0 check --target wasm32-unknown-unknown --lib
cargo +1.63.0 check --target thumbv7m-none-eabi --lib
```

Behavior tests and the `async-std` examples run on stable. Current `async-std` releases pull crates that need a newer compiler than 1.63; the library does not.

`no_std` + `alloc` needs pointer-width atomics (`alloc::sync::Arc` and `spin::Mutex`). Checked targets:

| Target | Support |
| --- | --- |
| `wasm32-unknown-unknown` | `cargo check --target wasm32-unknown-unknown --lib` |
| `thumbv7m-none-eabi` | builds, and `nostd-test` actually runs under QEMU |
| `thumbv6m-none-eabi` (Cortex-M0) | not supported: no pointer-width atomics, so `Arc` is not in `alloc` |

The QEMU harness is a `#![no_std]` `#![no_main]` binary with a bump allocator. It checks `is_done`, a task that completes and is dropped, a task spawned from another task, a self-wake, several tasks, and a `u32` output. Nothing from `std` is linked.

```bash
cargo build --manifest-path nostd-test/Cargo.toml --release --target thumbv7m-none-eabi
qemu-system-arm -cpu cortex-m3 -machine lm3s6965evb -nographic \
-semihosting-config enable=on,target=native \
-kernel nostd-test/target/thumbv7m-none-eabi/release/executor-nostd-test
```

Do not call `update` or `update_woken` from inside a task. Both take a `spin::Mutex` that is not reentrant. Spawn with `add_async`, and wake the waker you were given; the queues exist so that is safe during `update`.

# License

This project is licensed under either of
Expand Down
2 changes: 1 addition & 1 deletion examples/futures_chain.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ async fn async_sleep(print_name: &str, time: Duration) {
println!("{print_name}: after sleep {sleep_time} ms");
}

fn main() -> () {
fn main() {
println!("hello");

executor::add_async(async {
Expand Down
2 changes: 1 addition & 1 deletion examples/helloworld.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ async fn a() {
println!("goodbye world");
}

fn main() -> () {
fn main() {
executor::add_async(async {
a().await;
});
Expand Down
2 changes: 1 addition & 1 deletion examples/signal.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ fn receive_signal_from_somewhere(state: Arc<Mutex<AsyncSignalWaiterState>>) {
});
}

fn main() -> () {
fn main() {
let state = Arc::new(Mutex::new(AsyncSignalWaiterState {
ready: false,
waker: None,
Expand Down
23 changes: 23 additions & 0 deletions nostd-test/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
[package]
name = "executor-nostd-test"
version = "0.0.0"
edition = "2021"
publish = false
description = "Bare-metal no_std tests for the executor crate"

[dependencies]
executor = { path = ".." }

[[bin]]
name = "executor-nostd-test"
path = "src/main.rs"
test = false
bench = false

[profile.dev]
panic = "abort"

[profile.release]
panic = "abort"
lto = false
codegen-units = 1
5 changes: 5 additions & 0 deletions nostd-test/build.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
fn main() {
let manifest = std::env::var("CARGO_MANIFEST_DIR").unwrap();
println!("cargo:rustc-link-arg=-T{manifest}/link.ld");
println!("cargo:rerun-if-changed=link.ld");
}
47 changes: 47 additions & 0 deletions nostd-test/link.ld
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
/* LM3S6965 (QEMU lm3s6965evb): 256K flash at 0x0, 64K SRAM at 0x20000000. */
MEMORY
{
FLASH : ORIGIN = 0x00000000, LENGTH = 256K
RAM : ORIGIN = 0x20000000, LENGTH = 64K
}

ENTRY(Reset)

SECTIONS
{
.vector_table ORIGIN(FLASH) :
{
LONG(ORIGIN(RAM) + LENGTH(RAM));
KEEP(*(.vector_table.reset));
KEEP(*(.vector_table.fault));
} > FLASH

.text :
{
*(.text .text.*);
*(.rodata .rodata.*);
} > FLASH

.data : ALIGN(4)
{
_sdata = .;
*(.data .data.*);
_edata = .;
} > RAM AT > FLASH
_sidata = LOADADDR(.data);

.bss : ALIGN(4)
{
_sbss = .;
*(.bss .bss.*);
*(COMMON);
_ebss = .;
} > RAM

/DISCARD/ :
{
*(.ARM.exidx*);
*(.ARM.extab*);
*(.eh_frame*);
}
}
Loading
Loading