| 1 | //! Timer queue operations. |
| 2 | |
| 3 | use core::cell::Cell; |
| 4 | |
| 5 | use super::TaskRef; |
| 6 | |
| 7 | #[cfg (feature = "_timer-item-payload" )] |
| 8 | macro_rules! define_opaque { |
| 9 | ($size:tt) => { |
| 10 | /// An opaque data type. |
| 11 | #[repr(align($size))] |
| 12 | pub struct OpaqueData { |
| 13 | data: [u8; $size], |
| 14 | } |
| 15 | |
| 16 | impl OpaqueData { |
| 17 | const fn new() -> Self { |
| 18 | Self { data: [0; $size] } |
| 19 | } |
| 20 | |
| 21 | /// Access the data as a reference to a type `T`. |
| 22 | /// |
| 23 | /// Safety: |
| 24 | /// |
| 25 | /// The caller must ensure that the size of the type `T` is less than, or equal to |
| 26 | /// the size of the payload, and must ensure that the alignment of the type `T` is |
| 27 | /// less than, or equal to the alignment of the payload. |
| 28 | /// |
| 29 | /// The type must be valid when zero-initialized. |
| 30 | pub unsafe fn as_ref<T>(&self) -> &T { |
| 31 | &*(self.data.as_ptr() as *const T) |
| 32 | } |
| 33 | } |
| 34 | }; |
| 35 | } |
| 36 | |
| 37 | #[cfg (feature = "timer-item-payload-size-1" )] |
| 38 | define_opaque!(1); |
| 39 | #[cfg (feature = "timer-item-payload-size-2" )] |
| 40 | define_opaque!(2); |
| 41 | #[cfg (feature = "timer-item-payload-size-4" )] |
| 42 | define_opaque!(4); |
| 43 | #[cfg (feature = "timer-item-payload-size-8" )] |
| 44 | define_opaque!(8); |
| 45 | |
| 46 | /// An item in the timer queue. |
| 47 | pub struct TimerQueueItem { |
| 48 | /// The next item in the queue. |
| 49 | /// |
| 50 | /// If this field contains `Some`, the item is in the queue. The last item in the queue has a |
| 51 | /// value of `Some(dangling_pointer)` |
| 52 | pub next: Cell<Option<TaskRef>>, |
| 53 | |
| 54 | /// The time at which this item expires. |
| 55 | pub expires_at: Cell<u64>, |
| 56 | |
| 57 | /// Some implementation-defined, zero-initialized piece of data. |
| 58 | #[cfg (feature = "_timer-item-payload" )] |
| 59 | pub payload: OpaqueData, |
| 60 | } |
| 61 | |
| 62 | unsafe impl Sync for TimerQueueItem {} |
| 63 | |
| 64 | impl TimerQueueItem { |
| 65 | pub(crate) const fn new() -> Self { |
| 66 | Self { |
| 67 | next: Cell::new(None), |
| 68 | expires_at: Cell::new(0), |
| 69 | #[cfg (feature = "_timer-item-payload" )] |
| 70 | payload: OpaqueData::new(), |
| 71 | } |
| 72 | } |
| 73 | } |
| 74 | |