pub trait Kernel {
type BlockOn: Future<Output = ()> + 'static = Pending<()>;
// Provided methods
fn block_on(&mut self) -> Option<Pin<&mut Self::BlockOn>> { ... }
fn work(
&mut self,
_io: &mut WorkIo,
_mo: &mut MessageOutputs,
_b: &mut BlockMeta,
) -> impl Future<Output = Result<()>> { ... }
fn init(
&mut self,
_mo: &mut MessageOutputs,
_b: &mut BlockMeta,
) -> impl Future<Output = Result<()>> { ... }
fn deinit(
&mut self,
_mo: &mut MessageOutputs,
_b: &mut BlockMeta,
) -> impl Future<Output = Result<()>> { ... }
}Expand description
Processing logic for a block.
Kernel is the central trait custom block authors implement. The
#[derive(Block)] macro declares stream and message ports from annotated
fields and methods; the Kernel implementation supplies initialization,
work, and shutdown behavior.
The runtime calls Kernel::init once, then repeatedly calls
Kernel::work until the block marks itself finished or the flowgraph is
stopped, and finally calls Kernel::deinit. A work() implementation
should consume and produce exactly the number of stream items it handled and
use WorkIo to request another immediate call, wait on a future, or finish.
Normal runtime entry points accept only kernels whose value, block-on future,
and returned futures are Send. Kernels that do not satisfy these bounds can
still run in a local domain.
use futuresdr::runtime::dev::prelude::*;
#[derive(Block)]
struct Scale {
#[input]
input: DefaultCpuReader<f32>,
#[output]
output: DefaultCpuWriter<f32>,
gain: f32,
}
impl Kernel for Scale {
async fn work(
&mut self,
io: &mut WorkIo,
_mo: &mut MessageOutputs,
_meta: &mut BlockMeta,
) -> Result<()> {
let input = self.input.slice();
let output = self.output.slice();
let n = input.len().min(output.len());
for i in 0..n {
output[i] = input[i] * self.gain;
}
self.input.consume(n);
self.output.produce(n);
if self.input.finished() {
io.finished = true;
}
Ok(())
}
}Provided Associated Types§
Provided Methods§
Sourcefn block_on(&mut self) -> Option<Pin<&mut Self::BlockOn>>
fn block_on(&mut self) -> Option<Pin<&mut Self::BlockOn>>
Return the typed future that should wake this block again.
This is queried after WorkIo::block_on has been set. Returning
None falls back to waiting only for inbox/stream notifications.
Sourcefn work(
&mut self,
_io: &mut WorkIo,
_mo: &mut MessageOutputs,
_b: &mut BlockMeta,
) -> impl Future<Output = Result<()>>
fn work( &mut self, _io: &mut WorkIo, _mo: &mut MessageOutputs, _b: &mut BlockMeta, ) -> impl Future<Output = Result<()>>
Process stream data and emit messages.
Implementations inspect their input buffers, write output buffers, update
consume/produce counts, optionally post PMTs through MessageOutputs,
and update WorkIo flags before returning.
Sourcefn init(
&mut self,
_mo: &mut MessageOutputs,
_b: &mut BlockMeta,
) -> impl Future<Output = Result<()>>
fn init( &mut self, _mo: &mut MessageOutputs, _b: &mut BlockMeta, ) -> impl Future<Output = Result<()>>
Initialize the kernel before normal work starts.
This is the place to allocate runtime resources, send initial messages,
or update BlockMeta. Stream ports have already been initialized and
validated when this method is called.
Sourcefn deinit(
&mut self,
_mo: &mut MessageOutputs,
_b: &mut BlockMeta,
) -> impl Future<Output = Result<()>>
fn deinit( &mut self, _mo: &mut MessageOutputs, _b: &mut BlockMeta, ) -> impl Future<Output = Result<()>>
De-initialize the kernel after work has stopped.
This is called during block shutdown even when the block stopped because the flowgraph was terminated. It should release resources owned by the block and may post final messages.
Dyn Compatibility§
This trait is not dyn compatible.
In older versions of Rust, dyn compatibility was called "object safety", so this trait is not object safe.