Skip to content

Commit

Permalink
m: Add leap_unwrap & make RawTask::TASK_LAYOUT non-optional
Browse files Browse the repository at this point in the history
This PR makes RawTask::TASK_LAYOUT non-optional by panicking in const context in case of not having it. Note that due to MSRV being 1.47 a panic! could not be used in const context, so I resorted to out of bounds array read.
The error message in case of failure is that of the faulty expression ('async_task_failed_to_compile[1]'), which is pretty bad, but in reality we should not be getting there ever.
  • Loading branch information
osiewicz authored Dec 14, 2023
1 parent 918ec72 commit e909f77
Show file tree
Hide file tree
Showing 4 changed files with 19 additions and 14 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ jobs:
matrix:
# When updating this, the reminder to update the minimum supported
# Rust version in Cargo.toml.
rust: ['1.47']
rust: ['1.57']
steps:
- uses: actions/checkout@v4
- name: Install Rust
Expand Down
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ name = "async-task"
version = "4.5.0"
authors = ["Stjepan Glavina <[email protected]>"]
edition = "2018"
rust-version = "1.47"
rust-version = "1.57"
license = "Apache-2.0 OR MIT"
repository = "https://github.com/smol-rs/async-task"
description = "Task abstraction for building executors"
Expand Down
9 changes: 9 additions & 0 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,15 @@ macro_rules! leap {
}};
}

macro_rules! leap_unwrap {
($x: expr) => {{
match ($x) {
Some(val) => val,
None => panic!("called `Option::unwrap()` on a `None` value"),
}
}};
}

mod header;
mod raw;
mod runnable;
Expand Down
20 changes: 8 additions & 12 deletions src/raw.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ pub(crate) struct TaskVTable {
/// debuggers to decode raw task memory blobs. Do not remove
/// the field, even if it appears to be unused.
#[allow(unused)]
pub(crate) layout_info: &'static Option<TaskLayout>,
pub(crate) layout_info: &'static TaskLayout,
}

/// Memory layout of a task.
Expand Down Expand Up @@ -100,11 +100,11 @@ impl<F, T, S, M> Clone for RawTask<F, T, S, M> {
}

impl<F, T, S, M> RawTask<F, T, S, M> {
const TASK_LAYOUT: Option<TaskLayout> = Self::eval_task_layout();
const TASK_LAYOUT: TaskLayout = Self::eval_task_layout();

/// Computes the memory layout for a task.
#[inline]
const fn eval_task_layout() -> Option<TaskLayout> {
const fn eval_task_layout() -> TaskLayout {
// Compute the layouts for `Header`, `S`, `F`, and `T`.
let layout_header = Layout::new::<Header<M>>();
let layout_s = Layout::new::<S>();
Expand All @@ -118,17 +118,17 @@ impl<F, T, S, M> RawTask<F, T, S, M> {

// Compute the layout for `Header` followed `S` and `union { F, T }`.
let layout = layout_header;
let (layout, offset_s) = leap!(layout.extend(layout_s));
let (layout, offset_union) = leap!(layout.extend(layout_union));
let (layout, offset_s) = leap_unwrap!(layout.extend(layout_s));
let (layout, offset_union) = leap_unwrap!(layout.extend(layout_union));
let offset_f = offset_union;
let offset_r = offset_union;

Some(TaskLayout {
TaskLayout {
layout: unsafe { layout.into_std() },
offset_s,
offset_f,
offset_r,
})
}
}
}

Expand Down Expand Up @@ -227,12 +227,8 @@ where
/// Returns the layout of the task.
#[inline]
fn task_layout() -> TaskLayout {
match Self::TASK_LAYOUT {
Some(tl) => tl,
None => abort(),
}
Self::TASK_LAYOUT
}

/// Wakes a waker.
unsafe fn wake(ptr: *const ()) {
// This is just an optimization. If the schedule function has captured variables, then
Expand Down

0 comments on commit e909f77

Please sign in to comment.