The live process-data runtime: the published image, the cross-thread exchange buffers, and per-object PDO access over them.
More...
|
| bool | healthy () const |
| | True when an image is published and the last working counter meets the expectation.
|
| |
| std::optional< std::vector< uint8_t > > | readPdo (uint16_t slavePosition, uint16_t index, uint8_t subindex) const |
| | Reads a PDO-mapped object's current bytes from the live image. Lock-free.
|
| |
| bool | writePdo (uint16_t slavePosition, uint16_t index, uint8_t subindex, std::span< const uint8_t > bytes) |
| | Stages a PDO output object's bytes into its slot, sent on the next cycle. Lock-free.
|
| |
The live process-data runtime: the published image, the cross-thread exchange buffers, and per-object PDO access over them.
Carries the output (master→slave) and input (slave→master) images across the RT / non-RT boundary, the pointer to the currently published ProcessImage layout, and the working-counter health. DeviceManager owns one of these and drives the whole-buffer exchange each cycle; it also hands a pointer to it to every Device so a device can read and write its own PDO-mapped objects (readPdo / writePdo) without knowing how the image is stored. That single seam is what lets Device::readParameter / Device::writeParameter serve the live IO-map value while exchanging — identically from an HTTP handler or an RT task — and fall back to SDO otherwise.
Both accessors are lock-free, including writes (so an RT task can stage a setpoint without ever blocking on a non-RT writer). The output path is single-writer-per-buffer by construction: each output object owns an atomic staging slot that any number of writers store into independently, and the RT loop is the sole thread that composes those slots into the packed wire image each cycle (DeviceManager::exchangeProcessData). Composing on one thread is what makes bit-packed objects that share a byte safe without a lock — see NEXTGEN.md (Design B).
Defined in a header (rather than pimpl'd) so both device.cc and device_manager.cc can use it; the recorder ring and fixed buffers are heavy, but only those two translation units pull them in (the public device.h / device_manager.h only forward-declare it).
| std::optional< std::vector< uint8_t > > mm::node::ProcessData::readPdo |
( |
uint16_t |
slavePosition, |
|
|
uint16_t |
index, |
|
|
uint8_t |
subindex |
|
) |
| const |
Reads a PDO-mapped object's current bytes from the live image. Lock-free.
Outputs come from their staging slot (our current setpoint — always valid); inputs from the newest recorded cycle (ring head()-1), gated on healthy(). Returns nullopt when no image is published, nothing has been recorded yet, the object is not PDO-mapped, or (inputs only) the bus is unhealthy — in each case the caller reads it over SDO instead. Bytes are little-endian and LSB-aligned.