| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | // ====================================================================== | ||
| 2 | // \title WasmSequencer.hpp | ||
| 3 | // \author tumbar | ||
| 4 | // \brief hpp file for WasmSequencer component implementation class | ||
| 5 | // ====================================================================== | ||
| 6 | |||
| 7 | #ifndef Svc_WasmSequencer_HPP | ||
| 8 | #define Svc_WasmSequencer_HPP | ||
| 9 | |||
| 10 | #include "Fw/Cmd/CmdResponseEnumAc.hpp" | ||
| 11 | #include "Fw/DataStructures/FifoQueue.hpp" | ||
| 12 | #include "Fw/Types/FileNameString.hpp" | ||
| 13 | #include "Fw/Types/MemAllocator.hpp" | ||
| 14 | #include "Fw/Types/Serializable.hpp" | ||
| 15 | #include "Fw/Types/StringBase.hpp" | ||
| 16 | #include "Fw/Types/SuccessEnumAc.hpp" | ||
| 17 | #include "Svc/Seq/SeqArgsSerializableAc.hpp" | ||
| 18 | #include "Svc/WasmSequencer/WasmSequencerComponentAc.hpp" | ||
| 19 | #include "Svc/WasmSequencer/WasmSequencer_HostFunctionEnumAc.hpp" | ||
| 20 | #include "Svc/WasmSequencer/WasmSequencer_ModuleIdxAliasAc.hpp" | ||
| 21 | #include "Svc/WasmSequencer/WasmSequencer_RequestContextSerializableAc.hpp" | ||
| 22 | #include "Svc/WasmSequencer/WasmSequencer_TrapReasonEnumAc.hpp" | ||
| 23 | #include "Svc/WasmSequencer/spacewasm_include/spacewasm.h" | ||
| 24 | #include "Utils/Types/CircularBuffer.hpp" | ||
| 25 | #include "config/FwChanIdTypeAliasAc.h" | ||
| 26 | #include "config/FwPrmIdTypeAliasAc.h" | ||
| 27 | #include "config/FwSizeTypeAliasAc.h" | ||
| 28 | #include "config/WasmSequencerConfig.hpp" | ||
| 29 | |||
| 30 | namespace Svc { | ||
| 31 | |||
| 32 | class WasmSequencer final : public WasmSequencerComponentBase { | ||
| 33 | friend class WasmSequencerTester; | ||
| 34 | |||
| 35 | public: | ||
| 36 | // ---------------------------------------------------------------------- | ||
| 37 | // Component construction and destruction | ||
| 38 | // ---------------------------------------------------------------------- | ||
| 39 | |||
| 40 | //! Construct WasmSequencer object | ||
| 41 | WasmSequencer(const char* const compName //!< The component name | ||
| 42 | ); | ||
| 43 | |||
| 44 | //! Destroy WasmSequencer object | ||
| 45 | ✗ | ~WasmSequencer() = default; | |
| 46 | |||
| 47 | //! WasmSequencer owns a raw spacewasm_t* handle and a slot in the | ||
| 48 | //! process-wide global-allocator registry; copying would double-free both. | ||
| 49 | WasmSequencer(const WasmSequencer&) = delete; | ||
| 50 | WasmSequencer& operator=(const WasmSequencer&) = delete; | ||
| 51 | |||
| 52 | //! Configuration to select what happens when a serialIn fills | ||
| 53 | enum class SerialInQueueFullBehavior { | ||
| 54 | DROP_NEWEST, //!< Drop the latest message if it cannot fit in the remaining queue space | ||
| 55 | DROP_OLDEST, //!< Oldest message[s] will be de-queued and dropped to make space for the new message. Keep | ||
| 56 | //!< dropping messages until enough space is made | ||
| 57 | ASSERT, //!< Trigger an assertion if the queue fills and cannot process another message | ||
| 58 | }; | ||
| 59 | |||
| 60 | //! SpaceWasm has a hard-coded memory alignment requirement | ||
| 61 | constexpr static FwSizeType SPACEWASM_MEMORY_ALIGNMENT = 8; | ||
| 62 | |||
| 63 | //! Heap pages must be able to hold IR pages (512 bytes) minimum | ||
| 64 | //! type IrWord = U16 | ||
| 65 | //! type IrPage = [256] IrWord => sizeof(IrPage) == 512 | ||
| 66 | constexpr static FwSizeType SPACEWASM_IR_PAGE_SIZE = 512; | ||
| 67 | static_assert(Svc::WasmSequencerConfig::SPACEWASM_PAGE_SIZE >= SPACEWASM_IR_PAGE_SIZE, | ||
| 68 | "SpaceWasm does not support dynamic memory pages smaller than a single IR page (512 bytes)"); | ||
| 69 | |||
| 70 | //! Per-port serialIn queue configuration. | ||
| 71 | struct SerialInQueueConfig { | ||
| 72 | //! Queue size in bytes. A port left at size 0 gets no queue (all inbound frames on that index are dropped). | ||
| 73 | FwSizeType size = 0; | ||
| 74 | //! Overflow policy applied when a new frame does not fit. | ||
| 75 | SerialInQueueFullBehavior fullBehavior = SerialInQueueFullBehavior::DROP_NEWEST; | ||
| 76 | }; | ||
| 77 | |||
| 78 | //! Memory resource configuration for WasmSequencer. | ||
| 79 | //! See the [sizing guide](docs/sdd.md#sizing-guide) for how to configure this. | ||
| 80 | struct Config { | ||
| 81 | //! Number of `WASM_SEQ_SPACEWASM_PAGE_SIZE` pages to allocate | ||
| 82 | //! for the backing heap memory pool. | ||
| 83 | //! This is used for store the loaded Wasm modules and their IR (executable code) | ||
| 84 | //! but NOT for the guest memory (linear memory). | ||
| 85 | FwSizeType heapPages = 8; | ||
| 86 | |||
| 87 | //! Guest linear memory pool shared across all loaded modules | ||
| 88 | //! Note that a `.wasm` module will specify its linear memory size up-front in multiples of page-sizes | ||
| 89 | //! By default Wasm pages are 64k. if custom-page-sizes is enabled, page sizes are 1 byte. | ||
| 90 | FwSizeType guestMemorySize = 8192; | ||
| 91 | |||
| 92 | //! Wasm operand stack. The operand stack holds function parameters, locals and temporary operands. | ||
| 93 | //! When Wasm code calls another function, its frame will be pushed to the stack. | ||
| 94 | //! | ||
| 95 | //! This size is in units of 32-bit words. | ||
| 96 | //! The Wasm stack will be allocated from the heap memory pool | ||
| 97 | FwSizeType stackSize = 1024; | ||
| 98 | |||
| 99 | //! Allocates an empty list of pointers into the heap (i.e. sizeof(void*) * maxCodePages capacity). | ||
| 100 | //! A fixed capacity for holding decoded Wasm executable instructions in units of _Code Pages_. | ||
| 101 | //! Each page is 512 bytes (256 16-bit words) where each word holds a single resolved instruction (intermediate | ||
| 102 | //! representation - IR). | ||
| 103 | //! | ||
| 104 | //! This should be sized large enough to hold all the code pages you will need. | ||
| 105 | //! Note that this does not allocate the code pages themselves, it just incurs a `maxCodePages * sizeof(void*)` | ||
| 106 | //! allocates to the heap. From there, each code page (512 bytes) will be lazily allocated to the heap as needed | ||
| 107 | //! by .wasm modules. | ||
| 108 | //! | ||
| 109 | //! The larger this number is the higher overhead needed in the Wasm heap. | ||
| 110 | FwSizeType maxCodePages = 256; | ||
| 111 | |||
| 112 | //! Maximum number of Wasm modules that may be loaded into the sequencer's store. | ||
| 113 | U8 maxGuestModules = 8; | ||
| 114 | |||
| 115 | //! Size (in bytes) of the serialOut buffer used to copy a `serial_send` payload out of guest memory | ||
| 116 | //! before invoking the connected serialOut port. A value of 0 leaves serialOut unconfigured (disabled | ||
| 117 | //! serial_send). | ||
| 118 | FwSizeType serialOutMax = 0; | ||
| 119 | |||
| 120 | //! Per-port serialIn queue sizing and overflow policy. Default-construct the Config then populate | ||
| 121 | //! per port index, e.g. | ||
| 122 | //! `Config cfg; cfg.serialIn[0] = {256, SerialInQueueFullBehavior::DROP_OLDEST};` | ||
| 123 | //! A port left at size 0 gets no queue (all inbound frames on that index are dropped). | ||
| 124 | SerialInQueueConfig serialIn[NUM_SERIALIN_INPUT_PORTS]; | ||
| 125 | }; | ||
| 126 | |||
| 127 | //! [REQUIRED] Configure and allocate the dynamic backing pools for heap memory, guest memory, Wasm stack, | ||
| 128 | //! serialIn queues, and the serialOut buffer. | ||
| 129 | void configure(const Config& cfg, Fw::MemAllocator& mallocator); | ||
| 130 | |||
| 131 | //! Tear down the allocations made by `configure()` | ||
| 132 | void deinit() override; | ||
| 133 | |||
| 134 | private: | ||
| 135 | // ---------------------------------------------------------------------- | ||
| 136 | // Handler implementations for typed input ports | ||
| 137 | // ---------------------------------------------------------------------- | ||
| 138 | |||
| 139 | //! Handler implementation for checkTimers | ||
| 140 | //! | ||
| 141 | //! Port to periodically drive sleep-wake and host-function-timeout checks | ||
| 142 | void checkTimers_handler(FwIndexType portNum, //!< The port number | ||
| 143 | U32 context //!< The call order | ||
| 144 | ) override; | ||
| 145 | |||
| 146 | //! Handler implementation for cmdResponseIn | ||
| 147 | //! | ||
| 148 | //! Command response input | ||
| 149 | void cmdResponseIn_handler(FwIndexType portNum, //!< The port number | ||
| 150 | FwOpcodeType opCode, //!< Command Op Code | ||
| 151 | U32 cmdSeq, //!< Command Sequence | ||
| 152 | const Fw::CmdResponse& response //!< The command response argument | ||
| 153 | ) override; | ||
| 154 | |||
| 155 | //! Handler implementation for seqCancelIn | ||
| 156 | //! | ||
| 157 | //! port for requesting to cancel the currently running sequence | ||
| 158 | void seqCancelIn_handler(FwIndexType portNum //!< The port number | ||
| 159 | ) override; | ||
| 160 | |||
| 161 | //! Handler implementation for seqRunIn | ||
| 162 | //! | ||
| 163 | //! port for requests to run sequences | ||
| 164 | void seqRunIn_handler(FwIndexType portNum, //!< The port number | ||
| 165 | const Fw::StringBase& filename, //!< The sequence file | ||
| 166 | const Svc::SeqArgs& args //!< Sequence arguments | ||
| 167 | ) override; | ||
| 168 | |||
| 169 | //! Handler implementation for writeTelemetry | ||
| 170 | //! | ||
| 171 | //! Port to periodically write telemetry channels (optional) | ||
| 172 | void writeTelemetry_handler(FwIndexType portNum, //!< The port number | ||
| 173 | U32 context //!< The call order | ||
| 174 | ) override; | ||
| 175 | |||
| 176 | private: | ||
| 177 | // ---------------------------------------------------------------------- | ||
| 178 | // Handler implementations for serial input ports | ||
| 179 | // ---------------------------------------------------------------------- | ||
| 180 | |||
| 181 | //! Handler implementation for serialIn | ||
| 182 | //! | ||
| 183 | //! Port for receiving serial messages from other components. | ||
| 184 | //! All port indices will be placed into their own internal binary queue to be | ||
| 185 | //! handled by the serial_recv host function. | ||
| 186 | void serialIn_handler(FwIndexType portNum, //!< The port number | ||
| 187 | Fw::LinearBufferBase& buffer //!< The serialization buffer | ||
| 188 | ) override; | ||
| 189 | |||
| 190 | private: | ||
| 191 | // ---------------------------------------------------------------------- | ||
| 192 | // Handler implementations for commands | ||
| 193 | // ---------------------------------------------------------------------- | ||
| 194 | |||
| 195 | //! Handler implementation for command RUN | ||
| 196 | //! | ||
| 197 | //! Run a Wasm module main function on it's own in the interpreter | ||
| 198 | //! This command first resets the store (discarding any modules previously staged | ||
| 199 | //! with LOAD), then is short-hand for: | ||
| 200 | //! | ||
| 201 | //! ```sh | ||
| 202 | //! CANCEL # doesn't actually cancel a sequence, just resets the store | ||
| 203 | //! LOAD [fileName] "" | ||
| 204 | //! INVOKE "" [block] [seqArgs] | ||
| 205 | //! ``` | ||
| 206 | //! | ||
| 207 | //! If $block == Svc.BlockState.BLOCK this command will wait for completion. | ||
| 208 | void RUN_cmdHandler( | ||
| 209 | FwOpcodeType opCode, //!< The opcode | ||
| 210 | U32 cmdSeq, //!< The command sequence number | ||
| 211 | const Fw::CmdStringArg& fileName, //!< The name of the sequence file | ||
| 212 | const Svc::BlockState& block, //!< Block until sequence has finished running | ||
| 213 | const Svc::SeqArgs& seqArgs //!< Optional arguments to execute the sequence with | ||
| 214 | //!< Depending on the sequence being loaded these arguments may differ | ||
| 215 | ) override; | ||
| 216 | |||
| 217 | //! Handler implementation for command LOAD | ||
| 218 | //! | ||
| 219 | //! Loads and validates a WebAssembly module into the store under the given name. | ||
| 220 | //! Naming the module lets its exports be referenced by other modules and lets | ||
| 221 | //! INVOKE, GLOBAL_GET and GLOBAL_SET address it. Use an empty name for a single, | ||
| 222 | //! standalone module. The name must not conflict with a previously loaded module. | ||
| 223 | void LOAD_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 224 | U32 cmdSeq, //!< The command sequence number | ||
| 225 | const Fw::CmdStringArg& fileName, //!< The name of the sequence file | ||
| 226 | const Fw::CmdStringArg& name //!< WebAssembly module name (empty for a single unnamed module) | ||
| 227 | ) override; | ||
| 228 | |||
| 229 | //! Handler implementation for command INVOKE | ||
| 230 | //! | ||
| 231 | //! Invoke a main function from a loaded module | ||
| 232 | void INVOKE_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 233 | U32 cmdSeq, //!< The command sequence number | ||
| 234 | const Fw::CmdStringArg& module, //!< Name of the module to invoke a function from | ||
| 235 | const Svc::BlockState& block, //!< Block until sequence has finished running | ||
| 236 | const Svc::SeqArgs& seqArgs //!< Arguments to invoke the sequence entrypoint with | ||
| 237 | ) override; | ||
| 238 | |||
| 239 | //! Handler implementation for command WAIT | ||
| 240 | //! | ||
| 241 | //! Wait for the interpreter to finish and return it's result as a CmdResponse | ||
| 242 | void WAIT_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 243 | U32 cmdSeq //!< The command sequence number | ||
| 244 | ) override; | ||
| 245 | |||
| 246 | //! Handler implementation for command CANCEL | ||
| 247 | //! | ||
| 248 | //! Cancels a running or validated sequence. After running CANCEL, the sequencer should return to IDLE | ||
| 249 | //! This completely clears the store. | ||
| 250 | void CANCEL_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 251 | U32 cmdSeq //!< The command sequence number | ||
| 252 | ) override; | ||
| 253 | |||
| 254 | //! Handler implementation for command PAUSE | ||
| 255 | //! | ||
| 256 | //! Pauses the execution of the sequencer, just before it is about to start spinning. | ||
| 257 | //! This simply pends a pause flag that will be taken before the sequence engine starts | ||
| 258 | //! up again. | ||
| 259 | //! | ||
| 260 | //! This command completes immediately | ||
| 261 | void PAUSE_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 262 | U32 cmdSeq //!< The command sequence number | ||
| 263 | ) override; | ||
| 264 | |||
| 265 | //! Handler implementation for command CONTINUE | ||
| 266 | //! | ||
| 267 | //! Resume the sequence from a paused state | ||
| 268 | void CONTINUE_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 269 | U32 cmdSeq //!< The command sequence number | ||
| 270 | ) override; | ||
| 271 | |||
| 272 | //! Handler implementation for command GLOBAL_SET_I32 | ||
| 273 | //! | ||
| 274 | //! Set a global variable to a given i32 value. | ||
| 275 | //! Command fails if the module is not found, global is not exported, mutable, or of i32 type | ||
| 276 | void GLOBAL_SET_I32_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 277 | U32 cmdSeq, //!< The command sequence number | ||
| 278 | const Fw::CmdStringArg& moduleName, //!< Name of the module to set global for | ||
| 279 | const Fw::CmdStringArg& name, //!< Name of the global | ||
| 280 | I32 value //!< Value to set global to | ||
| 281 | ) override; | ||
| 282 | |||
| 283 | //! Handler implementation for command GLOBAL_SET_I64 | ||
| 284 | //! | ||
| 285 | //! Set a global variable to a given i64 value. | ||
| 286 | //! Command fails if the module is not found, global is not exported, mutable, or of i64 type | ||
| 287 | void GLOBAL_SET_I64_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 288 | U32 cmdSeq, //!< The command sequence number | ||
| 289 | const Fw::CmdStringArg& moduleName, //!< Name of the module to set global for | ||
| 290 | const Fw::CmdStringArg& name, //!< Name of the global | ||
| 291 | I64 value //!< Value to set global to | ||
| 292 | ) override; | ||
| 293 | |||
| 294 | //! Handler implementation for command GLOBAL_SET_F32 | ||
| 295 | //! | ||
| 296 | //! Set a global variable to a given f32 value. | ||
| 297 | //! Command fails if the module is not found, global is not exported, mutable, or of f32 type | ||
| 298 | void GLOBAL_SET_F32_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 299 | U32 cmdSeq, //!< The command sequence number | ||
| 300 | const Fw::CmdStringArg& moduleName, //!< Name of the module to set global for | ||
| 301 | const Fw::CmdStringArg& name, //!< Name of the global | ||
| 302 | F32 value //!< Value to set global to | ||
| 303 | ) override; | ||
| 304 | |||
| 305 | //! Handler implementation for command GLOBAL_SET_F64 | ||
| 306 | //! | ||
| 307 | //! Set a global variable to a given f64 value. | ||
| 308 | //! Command fails if the module is not found, global is not exported, mutable, or of f64 type | ||
| 309 | void GLOBAL_SET_F64_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 310 | U32 cmdSeq, //!< The command sequence number | ||
| 311 | const Fw::CmdStringArg& moduleName, //!< Name of the module to set global for | ||
| 312 | const Fw::CmdStringArg& name, //!< Name of the global | ||
| 313 | F64 value //!< Value to set global to | ||
| 314 | ) override; | ||
| 315 | |||
| 316 | //! Handler implementation for command GLOBAL_GET | ||
| 317 | //! | ||
| 318 | //! Get the current value of a global variable and emit an event | ||
| 319 | //! Command fails if the module is not found or the global is not exported | ||
| 320 | void GLOBAL_GET_cmdHandler(FwOpcodeType opCode, //!< The opcode | ||
| 321 | U32 cmdSeq, //!< The command sequence number | ||
| 322 | const Fw::CmdStringArg& moduleName, //!< Name of the module to get global for | ||
| 323 | const Fw::CmdStringArg& name //!< Name of the global | ||
| 324 | ) override; | ||
| 325 | |||
| 326 | private: | ||
| 327 | // ---------------------------------------------------------------------- | ||
| 328 | // Implementations for internal state machine actions | ||
| 329 | // ---------------------------------------------------------------------- | ||
| 330 | |||
| 331 | //! Implementation for action processInvoke of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 332 | //! | ||
| 333 | //! Action to save the invoke arguments and emit an 'invoked' signal | ||
| 334 | void Svc_WasmSequencer_ControllerStateMachine_action_processInvoke( | ||
| 335 | SmId smId, //!< The state machine id | ||
| 336 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 337 | const Svc::WasmSequencer_InvokeRequest& value //!< The value | ||
| 338 | ) override; | ||
| 339 | |||
| 340 | //! Implementation for action setCancelRequested of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 341 | //! | ||
| 342 | //! Latch a cancel that arrives while a sequence is loading/resolving | ||
| 343 | void Svc_WasmSequencer_ControllerStateMachine_action_setCancelRequested( | ||
| 344 | SmId smId, //!< The state machine id | ||
| 345 | Svc_WasmSequencer_ControllerStateMachine::Signal signal //!< The signal | ||
| 346 | ) override; | ||
| 347 | |||
| 348 | //! Implementation for action clearCancelRequested of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 349 | //! | ||
| 350 | //! Acknowledge/clear any pending cancel | ||
| 351 | void Svc_WasmSequencer_ControllerStateMachine_action_clearCancelRequested( | ||
| 352 | SmId smId, //!< The state machine id | ||
| 353 | Svc_WasmSequencer_ControllerStateMachine::Signal signal //!< The signal | ||
| 354 | ) override; | ||
| 355 | |||
| 356 | //! Implementation for action cancelPendingRequest of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 357 | //! | ||
| 358 | //! Abort a load/invoke that was cancelled before the engine ran | ||
| 359 | void Svc_WasmSequencer_ControllerStateMachine_action_cancelPendingRequest( | ||
| 360 | SmId smId, //!< The state machine id | ||
| 361 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 362 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 363 | ) override; | ||
| 364 | |||
| 365 | //! Implementation for action respond_noblock_OK of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 366 | //! | ||
| 367 | //! Responds to $block == NO_BLOCK requests with OK | ||
| 368 | void Svc_WasmSequencer_ControllerStateMachine_action_respond_noblock_OK( | ||
| 369 | SmId smId, //!< The state machine id | ||
| 370 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 371 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 372 | ) override; | ||
| 373 | |||
| 374 | //! Implementation for action respond_ERROR of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 375 | //! | ||
| 376 | //! Responds to request with EXECUTION_ERROR | ||
| 377 | void Svc_WasmSequencer_ControllerStateMachine_action_respond_ERROR( | ||
| 378 | SmId smId, //!< The state machine id | ||
| 379 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 380 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 381 | ) override; | ||
| 382 | |||
| 383 | //! Implementation for action incrementSequenceFailure of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 384 | //! | ||
| 385 | //! Increment the SequencesFailed telemetry counter | ||
| 386 | void Svc_WasmSequencer_ControllerStateMachine_action_incrementSequenceFailure( | ||
| 387 | SmId smId, //!< The state machine id | ||
| 388 | Svc_WasmSequencer_ControllerStateMachine::Signal signal //!< The signal | ||
| 389 | ) override; | ||
| 390 | |||
| 391 | //! Implementation for action respondInvoke_BUSY of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 392 | //! | ||
| 393 | //! Responds to request with BUSY | ||
| 394 | //! Emit an event to say why we are rejecting this request in the current state | ||
| 395 | void Svc_WasmSequencer_ControllerStateMachine_action_respondInvoke_BUSY( | ||
| 396 | SmId smId, //!< The state machine id | ||
| 397 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 398 | const Svc::WasmSequencer_InvokeRequest& value //!< The value | ||
| 399 | ) override; | ||
| 400 | |||
| 401 | //! Implementation for action respondInvoke_ERROR of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 402 | //! | ||
| 403 | //! Responds to request with EXECUTION_ERROR | ||
| 404 | //! Emit an event to say why we are rejecting this request in the current state | ||
| 405 | void Svc_WasmSequencer_ControllerStateMachine_action_respondInvoke_ERROR( | ||
| 406 | SmId smId, //!< The state machine id | ||
| 407 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 408 | const Svc::WasmSequencer_InvokeRequest& value //!< The value | ||
| 409 | ) override; | ||
| 410 | |||
| 411 | //! Implementation for action respondLoad_BUSY of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 412 | //! | ||
| 413 | //! Responds to request with BUSY | ||
| 414 | //! Emit an event to say why we are rejecting this request in the current state | ||
| 415 | void Svc_WasmSequencer_ControllerStateMachine_action_respondLoad_BUSY( | ||
| 416 | SmId smId, //!< The state machine id | ||
| 417 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 418 | const Svc::WasmSequencer_LoadRequest& value //!< The value | ||
| 419 | ) override; | ||
| 420 | |||
| 421 | //! Implementation for action respond_block_OK of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 422 | //! | ||
| 423 | //! Responds to $block == BLOCK requests with OK | ||
| 424 | //! Responds to any pending WAIT requests with OK | ||
| 425 | void Svc_WasmSequencer_ControllerStateMachine_action_respond_block_OK( | ||
| 426 | SmId smId, //!< The state machine id | ||
| 427 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 428 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 429 | ) override; | ||
| 430 | |||
| 431 | //! Implementation for action respond_block_ERROR of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 432 | //! | ||
| 433 | //! Responds to $block == BLOCK requests with ERROR. | ||
| 434 | //! Responds to any pending WAIT requests with ERROR | ||
| 435 | void Svc_WasmSequencer_ControllerStateMachine_action_respond_block_ERROR( | ||
| 436 | SmId smId, //!< The state machine id | ||
| 437 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 438 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 439 | ) override; | ||
| 440 | |||
| 441 | //! Implementation for action load of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 442 | //! | ||
| 443 | //! Load a module into the store. | ||
| 444 | //! Emits `loadSucceded` or `loadFailed` depending on result | ||
| 445 | void Svc_WasmSequencer_ControllerStateMachine_action_load( | ||
| 446 | SmId smId, //!< The state machine id | ||
| 447 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 448 | const Svc::WasmSequencer_LoadRequest& value //!< The value | ||
| 449 | ) override; | ||
| 450 | |||
| 451 | //! Implementation for action invokeStart of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 452 | //! | ||
| 453 | //! Invoke the start function on a loaded module | ||
| 454 | void Svc_WasmSequencer_ControllerStateMachine_action_invokeStart( | ||
| 455 | SmId smId, //!< The state machine id | ||
| 456 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 457 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 458 | ) override; | ||
| 459 | |||
| 460 | //! Implementation for action invokeMain of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 461 | //! | ||
| 462 | //! Invoke the main function for module in context | ||
| 463 | void Svc_WasmSequencer_ControllerStateMachine_action_invokeMain( | ||
| 464 | SmId smId, //!< The state machine id | ||
| 465 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 466 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 467 | ) override; | ||
| 468 | |||
| 469 | //! Implementation for action reportModuleInvalidMain of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 470 | //! | ||
| 471 | //! Emit an event noting that a given module has no [valid] main function | ||
| 472 | void Svc_WasmSequencer_ControllerStateMachine_action_reportModuleInvalidMain( | ||
| 473 | SmId smId, //!< The state machine id | ||
| 474 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 475 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 476 | ) override; | ||
| 477 | |||
| 478 | //! Implementation for action reportModuleMainInvokeFailed of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 479 | //! | ||
| 480 | //! Emit an event noting why the invocation of a module main failed | ||
| 481 | void Svc_WasmSequencer_ControllerStateMachine_action_reportModuleMainInvokeFailed( | ||
| 482 | SmId smId, //!< The state machine id | ||
| 483 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 484 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 485 | ) override; | ||
| 486 | |||
| 487 | //! Implementation for action reportModuleStartInvokeFailed of state machine | ||
| 488 | //! Svc_WasmSequencer_ControllerStateMachine | ||
| 489 | //! | ||
| 490 | //! Emit an event noting why the invocation of a module start failed | ||
| 491 | void Svc_WasmSequencer_ControllerStateMachine_action_reportModuleStartInvokeFailed( | ||
| 492 | SmId smId, //!< The state machine id | ||
| 493 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 494 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 495 | ) override; | ||
| 496 | |||
| 497 | //! Implementation for action reportModuleStarted of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 498 | //! | ||
| 499 | //! Reports that a module started running it's main function | ||
| 500 | void Svc_WasmSequencer_ControllerStateMachine_action_reportModuleStarted( | ||
| 501 | SmId smId, //!< The state machine id | ||
| 502 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 503 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 504 | ) override; | ||
| 505 | |||
| 506 | //! Implementation for action reportModuleSucceeded of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 507 | //! | ||
| 508 | //! Emit an event noting a module succeeded during execution. Increment telemetry counters. | ||
| 509 | void Svc_WasmSequencer_ControllerStateMachine_action_reportModuleSucceeded( | ||
| 510 | SmId smId, //!< The state machine id | ||
| 511 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 512 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 513 | ) override; | ||
| 514 | |||
| 515 | //! Implementation for action reportModuleStartFailed of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 516 | //! | ||
| 517 | //! Emit an event noting a module failed during execution of start. Increment telemetry counters. | ||
| 518 | void Svc_WasmSequencer_ControllerStateMachine_action_reportModuleStartFailed( | ||
| 519 | SmId smId, //!< The state machine id | ||
| 520 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 521 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 522 | ) override; | ||
| 523 | |||
| 524 | //! Implementation for action reportModuleMainFailed of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 525 | //! | ||
| 526 | //! Emit an event noting a module failed during execution. Increment telemetry counters. | ||
| 527 | void Svc_WasmSequencer_ControllerStateMachine_action_reportModuleMainFailed( | ||
| 528 | SmId smId, //!< The state machine id | ||
| 529 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 530 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 531 | ) override; | ||
| 532 | |||
| 533 | //! Implementation for action resetStore of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 534 | //! | ||
| 535 | //! Create a new store with N_MODULES (parameter) modules | ||
| 536 | void Svc_WasmSequencer_ControllerStateMachine_action_resetStore( | ||
| 537 | SmId smId, //!< The state machine id | ||
| 538 | Svc_WasmSequencer_ControllerStateMachine::Signal signal //!< The signal | ||
| 539 | ) override; | ||
| 540 | |||
| 541 | //! Implementation for action runEngine of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 542 | //! | ||
| 543 | //! Send a signal to the engine state machine to begin running | ||
| 544 | //! The engine will asynchronously reply with the `engineFinished` signal | ||
| 545 | void Svc_WasmSequencer_ControllerStateMachine_action_runEngine( | ||
| 546 | SmId smId, //!< The state machine id | ||
| 547 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 548 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 549 | ) override; | ||
| 550 | |||
| 551 | //! Implementation for action cmdReplyOK of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 552 | //! | ||
| 553 | //! Respond to a pending command with OK | ||
| 554 | void Svc_WasmSequencer_InterpreterStateMachine_action_cmdReplyOK( | ||
| 555 | SmId smId, //!< The state machine id | ||
| 556 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal, //!< The signal | ||
| 557 | const Svc::WasmSequencer_CommandRequest& value //!< The value | ||
| 558 | ) override; | ||
| 559 | |||
| 560 | //! Implementation for action signalEntered of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 561 | //! | ||
| 562 | //! generic signal raised | ||
| 563 | void Svc_WasmSequencer_InterpreterStateMachine_action_signalEntered( | ||
| 564 | SmId smId, //!< The state machine id | ||
| 565 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 566 | ) override; | ||
| 567 | |||
| 568 | //! Implementation for action spin of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 569 | //! | ||
| 570 | //! spins the interpreter loop, executing up to a bounded number of instructions | ||
| 571 | void Svc_WasmSequencer_InterpreterStateMachine_action_spin( | ||
| 572 | SmId smId, //!< The state machine id | ||
| 573 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 574 | ) override; | ||
| 575 | |||
| 576 | //! Implementation for action reset of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 577 | //! | ||
| 578 | //! resets the engine's state (clears operand stack, pc, fp, sp) | ||
| 579 | void Svc_WasmSequencer_InterpreterStateMachine_action_reset( | ||
| 580 | SmId smId, //!< The state machine id | ||
| 581 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 582 | ) override; | ||
| 583 | |||
| 584 | //! Implementation for action clearExitStatus of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 585 | void Svc_WasmSequencer_InterpreterStateMachine_action_clearExitStatus( | ||
| 586 | SmId smId, //!< The state machine id | ||
| 587 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 588 | ) override; | ||
| 589 | |||
| 590 | //! Implementation for action setExitReason_INTERPRETER_FINISHED of state machine | ||
| 591 | //! Svc_WasmSequencer_InterpreterStateMachine | ||
| 592 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitReason_INTERPRETER_FINISHED( | ||
| 593 | SmId smId, //!< The state machine id | ||
| 594 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 595 | ) override; | ||
| 596 | |||
| 597 | //! Implementation for action setExitReason_INTERPRETER_TRAP of state machine | ||
| 598 | //! Svc_WasmSequencer_InterpreterStateMachine | ||
| 599 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitReason_INTERPRETER_TRAP( | ||
| 600 | SmId smId, //!< The state machine id | ||
| 601 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 602 | ) override; | ||
| 603 | |||
| 604 | //! Implementation for action setExitReason_REPLY_TIMEOUT of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 605 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitReason_REPLY_TIMEOUT( | ||
| 606 | SmId smId, //!< The state machine id | ||
| 607 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 608 | ) override; | ||
| 609 | |||
| 610 | //! Implementation for action setExitReason_HOST_FAILURE of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 611 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitReason_HOST_FAILURE( | ||
| 612 | SmId smId, //!< The state machine id | ||
| 613 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 614 | ) override; | ||
| 615 | |||
| 616 | //! Implementation for action setExitReason_TIMER_INCOMPARABLE of state machine | ||
| 617 | //! Svc_WasmSequencer_InterpreterStateMachine | ||
| 618 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitReason_TIMER_INCOMPARABLE( | ||
| 619 | SmId smId, //!< The state machine id | ||
| 620 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 621 | ) override; | ||
| 622 | |||
| 623 | //! Implementation for action setExitReason_UNEXPECTED_REPLY of state machine | ||
| 624 | //! Svc_WasmSequencer_InterpreterStateMachine | ||
| 625 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitReason_UNEXPECTED_REPLY( | ||
| 626 | SmId smId, //!< The state machine id | ||
| 627 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 628 | ) override; | ||
| 629 | |||
| 630 | //! Implementation for action setExitReason_CANCEL of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 631 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitReason_CANCEL( | ||
| 632 | SmId smId, //!< The state machine id | ||
| 633 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 634 | ) override; | ||
| 635 | |||
| 636 | //! Implementation for action setExitCode of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 637 | void Svc_WasmSequencer_InterpreterStateMachine_action_setExitCode( | ||
| 638 | SmId smId, //!< The state machine id | ||
| 639 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal, //!< The signal | ||
| 640 | I32 value //!< The value | ||
| 641 | ) override; | ||
| 642 | |||
| 643 | //! Implementation for action setTrapReason of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 644 | void Svc_WasmSequencer_InterpreterStateMachine_action_setTrapReason( | ||
| 645 | SmId smId, //!< The state machine id | ||
| 646 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal, //!< The signal | ||
| 647 | const Svc::WasmSequencer_TrapReason& value //!< The value | ||
| 648 | ) override; | ||
| 649 | |||
| 650 | //! Implementation for action setLastHostFunction of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 651 | void Svc_WasmSequencer_InterpreterStateMachine_action_setLastHostFunction( | ||
| 652 | SmId smId, //!< The state machine id | ||
| 653 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 654 | ) override; | ||
| 655 | |||
| 656 | //! Implementation for action finish of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 657 | //! | ||
| 658 | //! Send a signal back to the controller state machine that we have finished executing | ||
| 659 | //! The response codes are stored in m_exit (reason, code, lastTrapReason) | ||
| 660 | void Svc_WasmSequencer_InterpreterStateMachine_action_finish( | ||
| 661 | SmId smId, //!< The state machine id | ||
| 662 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 663 | ) override; | ||
| 664 | |||
| 665 | //! Implementation for action reportPaused of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 666 | //! | ||
| 667 | //! reports that execution was paused at a breakpoint | ||
| 668 | void Svc_WasmSequencer_InterpreterStateMachine_action_reportPaused( | ||
| 669 | SmId smId, //!< The state machine id | ||
| 670 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 671 | ) override; | ||
| 672 | |||
| 673 | //! Implementation for action clearPause of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 674 | //! | ||
| 675 | //! sets the pause flag to false | ||
| 676 | void Svc_WasmSequencer_InterpreterStateMachine_action_clearPause( | ||
| 677 | SmId smId, //!< The state machine id | ||
| 678 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 679 | ) override; | ||
| 680 | |||
| 681 | //! Implementation for action dispatchPendingHostFunction of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 682 | //! | ||
| 683 | //! dispatch a host function port call | ||
| 684 | void Svc_WasmSequencer_InterpreterStateMachine_action_dispatchPendingHostFunction( | ||
| 685 | SmId smId, //!< The state machine id | ||
| 686 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 687 | ) override; | ||
| 688 | |||
| 689 | //! Implementation for action clearPendingHostFunction of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 690 | //! | ||
| 691 | //! clears the pending host function port call | ||
| 692 | void Svc_WasmSequencer_InterpreterStateMachine_action_clearPendingHostFunction( | ||
| 693 | SmId smId, //!< The state machine id | ||
| 694 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 695 | ) override; | ||
| 696 | |||
| 697 | //! Implementation for action setContext of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 698 | //! | ||
| 699 | //! Set the current executing context | ||
| 700 | void Svc_WasmSequencer_InterpreterStateMachine_action_setContext( | ||
| 701 | SmId smId, //!< The state machine id | ||
| 702 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal, //!< The signal | ||
| 703 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 704 | ) override; | ||
| 705 | |||
| 706 | //! Implementation for action clearContext of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 707 | //! | ||
| 708 | //! Clear the current executing context | ||
| 709 | void Svc_WasmSequencer_InterpreterStateMachine_action_clearContext( | ||
| 710 | SmId smId, //!< The state machine id | ||
| 711 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 712 | ) override; | ||
| 713 | |||
| 714 | //! Implementation for action resume of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 715 | //! | ||
| 716 | //! spacewasm_engine_resume | ||
| 717 | void Svc_WasmSequencer_InterpreterStateMachine_action_resume( | ||
| 718 | SmId smId, //!< The state machine id | ||
| 719 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 720 | ) override; | ||
| 721 | |||
| 722 | //! Implementation for action resumeI32 of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 723 | //! | ||
| 724 | //! spacewasm_engine_resume_some(I32(value)) | ||
| 725 | void Svc_WasmSequencer_InterpreterStateMachine_action_resumeI32( | ||
| 726 | SmId smId, //!< The state machine id | ||
| 727 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal, //!< The signal | ||
| 728 | I32 value //!< The value | ||
| 729 | ) override; | ||
| 730 | |||
| 731 | //! Implementation for action checkSleepTimers of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 732 | //! | ||
| 733 | //! A periodic check on the pending timer to see if we can wake up | ||
| 734 | void Svc_WasmSequencer_InterpreterStateMachine_action_checkSleepTimers( | ||
| 735 | SmId smId, //!< The state machine id | ||
| 736 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 737 | ) override; | ||
| 738 | |||
| 739 | //! Implementation for action checkTimeout of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 740 | //! | ||
| 741 | //! A periodic check on any host function to guard against timeouts | ||
| 742 | void Svc_WasmSequencer_InterpreterStateMachine_action_checkTimeout( | ||
| 743 | SmId smId, //!< The state machine id | ||
| 744 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 745 | ) override; | ||
| 746 | |||
| 747 | //! Implementation for action dequeueSerialAndResume of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 748 | //! | ||
| 749 | //! Dequeue a serial message into the host guest memory and resume the interpreter | ||
| 750 | void Svc_WasmSequencer_InterpreterStateMachine_action_dequeueSerialAndResume( | ||
| 751 | SmId smId, //!< The state machine id | ||
| 752 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal, //!< The signal | ||
| 753 | const FwIndexType& value //!< The value | ||
| 754 | ) override; | ||
| 755 | |||
| 756 | private: | ||
| 757 | // ---------------------------------------------------------------------- | ||
| 758 | // Implementations for internal state machine guards | ||
| 759 | // ---------------------------------------------------------------------- | ||
| 760 | |||
| 761 | //! Implementation for guard cancelRequested of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 762 | //! | ||
| 763 | //! True if a cancel was latched since the controller last came to rest. | ||
| 764 | bool Svc_WasmSequencer_ControllerStateMachine_guard_cancelRequested( | ||
| 765 | SmId smId, //!< The state machine id | ||
| 766 | Svc_WasmSequencer_ControllerStateMachine::Signal signal //!< The signal | ||
| 767 | ) const override; | ||
| 768 | |||
| 769 | //! Implementation for guard moduleHasStart of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 770 | //! | ||
| 771 | //! return true if this module has a start function | ||
| 772 | bool Svc_WasmSequencer_ControllerStateMachine_guard_moduleHasStart( | ||
| 773 | SmId smId, //!< The state machine id | ||
| 774 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 775 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 776 | ) const override; | ||
| 777 | |||
| 778 | //! Implementation for guard moduleHasValidMain of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 779 | //! | ||
| 780 | //! return true if this module has a valid main function ([] -> i32) | ||
| 781 | bool Svc_WasmSequencer_ControllerStateMachine_guard_moduleHasValidMain( | ||
| 782 | SmId smId, //!< The state machine id | ||
| 783 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 784 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 785 | ) const override; | ||
| 786 | |||
| 787 | //! Implementation for guard invokeSucceeded of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 788 | //! | ||
| 789 | //! return true if invokeStatus == SPACEWASM_OK. This flag is set as a result of invokeStart/invokeMain | ||
| 790 | bool Svc_WasmSequencer_ControllerStateMachine_guard_invokeSucceeded( | ||
| 791 | SmId smId, //!< The state machine id | ||
| 792 | Svc_WasmSequencer_ControllerStateMachine::Signal signal, //!< The signal | ||
| 793 | const Svc::WasmSequencer_RequestContext& value //!< The value | ||
| 794 | ) const override; | ||
| 795 | |||
| 796 | //! Implementation for guard interpreterSucceeded of state machine Svc_WasmSequencer_ControllerStateMachine | ||
| 797 | //! | ||
| 798 | //! Check if the last engine execution finished executing successfully | ||
| 799 | bool Svc_WasmSequencer_ControllerStateMachine_guard_interpreterSucceeded( | ||
| 800 | SmId smId, //!< The state machine id | ||
| 801 | Svc_WasmSequencer_ControllerStateMachine::Signal signal //!< The signal | ||
| 802 | ) const override; | ||
| 803 | |||
| 804 | //! Implementation for guard pendingPause of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 805 | //! | ||
| 806 | //! return true if execution should pause before spinning the interpreter again | ||
| 807 | bool Svc_WasmSequencer_InterpreterStateMachine_guard_pendingPause( | ||
| 808 | SmId smId, //!< The state machine id | ||
| 809 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 810 | ) const override; | ||
| 811 | |||
| 812 | //! Implementation for guard pendingHostFunction of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 813 | //! | ||
| 814 | //! a host function is waiting to be processed | ||
| 815 | bool Svc_WasmSequencer_InterpreterStateMachine_guard_pendingHostFunction( | ||
| 816 | SmId smId, //!< The state machine id | ||
| 817 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 818 | ) const override; | ||
| 819 | |||
| 820 | //! Implementation for guard pendingHostFunctionIsSleep of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 821 | //! | ||
| 822 | //! the pending host function is a sleep (therefore we need to check the sleep timers) | ||
| 823 | bool Svc_WasmSequencer_InterpreterStateMachine_guard_pendingHostFunctionIsSleep( | ||
| 824 | SmId smId, //!< The state machine id | ||
| 825 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 826 | ) const override; | ||
| 827 | |||
| 828 | //! Implementation for guard blockingSerialIn of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 829 | //! | ||
| 830 | //! Check if we are currently blocking on a serial_recv() for a given serial port index | ||
| 831 | bool Svc_WasmSequencer_InterpreterStateMachine_guard_blockingSerialIn( | ||
| 832 | SmId smId, //!< The state machine id | ||
| 833 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal, //!< The signal | ||
| 834 | const FwIndexType& value //!< The value | ||
| 835 | ) const override; | ||
| 836 | |||
| 837 | //! Implementation for guard dequeueSucceeded of state machine Svc_WasmSequencer_InterpreterStateMachine | ||
| 838 | //! | ||
| 839 | //! Return true `dequeueSerialAndResume` processed a message successfully | ||
| 840 | bool Svc_WasmSequencer_InterpreterStateMachine_guard_dequeueSucceeded( | ||
| 841 | SmId smId, //!< The state machine id | ||
| 842 | Svc_WasmSequencer_InterpreterStateMachine::Signal signal //!< The signal | ||
| 843 | ) const override; | ||
| 844 | |||
| 845 | private: | ||
| 846 | /// The global allocator callbacks | ||
| 847 | U8* globalAlloc(U32 size, U32 align); | ||
| 848 | void globalDealloc(const U8* ptr); | ||
| 849 | |||
| 850 | /// C-callback trampolines for the spacewasm global-allocator registry | ||
| 851 | static U8* globalAllocCallback(void* userdata, size_t size, size_t align); | ||
| 852 | static void globalDeallocCallback(void* userdata, U8* ptr, size_t size, size_t align); | ||
| 853 | |||
| 854 | /// The Wasm guest allocator callbacks for this component | ||
| 855 | U8* guestAlloc(FwSizeType size, U32 align); | ||
| 856 | U8* guestRealloc(U8* ptr, FwSizeType oldSize, FwSizeType newSize, U32 align); | ||
| 857 | void guestDealloc(const U8* ptr, FwSizeType size); | ||
| 858 | |||
| 859 | // Guest allocator callbacks passed to C API | ||
| 860 | static U8* guestAllocCallback(void* userdata, size_t size, size_t align); | ||
| 861 | static U8* guestReallocCallback(void* userdata, U8* ptr, size_t old_size, size_t new_size, size_t align); | ||
| 862 | static void guestDeallocCallback(void* userdata, U8* ptr, size_t size, size_t align); | ||
| 863 | |||
| 864 | //! Create a fresh interpreter store with the given module capacity, | ||
| 865 | //! destroying any existing store first. | ||
| 866 | void createStore(); | ||
| 867 | |||
| 868 | //! Destroy the current interpreter store, if any, releasing its memory. | ||
| 869 | void destroyStore(); | ||
| 870 | |||
| 871 | //! Take control of the spacewasm global allocator on this WasmSequence | ||
| 872 | void takeAllocatorLock(); | ||
| 873 | |||
| 874 | //! Release control of the spacewasm global allocator on this WasmSequence | ||
| 875 | void releaseAllocatorLock(); | ||
| 876 | |||
| 877 | //! Map a spacewasm_trap_t onto the TrapReason event enum. | ||
| 878 | static Svc::WasmSequencer_TrapReason::T mapTrapReason(spacewasm_trap_t trap); | ||
| 879 | |||
| 880 | //! Record the SeqName telemetry for a load. Uses moduleName when non-empty; | ||
| 881 | //! otherwise derives it from the file's basename with any ".wasm" suffix | ||
| 882 | //! stripped (an empty-name RUN / LOAD). | ||
| 883 | void setSequenceName(const Fw::StringBase& filePath, const Fw::StringBase& moduleName); | ||
| 884 | |||
| 885 | //! Return a pointer to the basename of `path` (the segment after the last '/') | ||
| 886 | //! and write its length to `outLen`. `len` is the length of `path`. Pure string | ||
| 887 | //! manipulation, no filesystem access. | ||
| 888 | static const char* pathBaseName(const char* path, FwSizeType len, FwSizeType& outLen); | ||
| 889 | |||
| 890 | //! True if `path` contains a ".." path-traversal component (a segment, delimited | ||
| 891 | //! by '/', that is exactly ".."). Used to keep a ground-supplied sequence file | ||
| 892 | //! name from escaping the configured SEQ_BASE_DIR. | ||
| 893 | static bool pathHasParentTraversal(const Fw::StringBase& path); | ||
| 894 | |||
| 895 | //! Resolve a sequence `fileName` against the SEQ_BASE_DIR parameter, writing the | ||
| 896 | //! result to `filePath`. On failure (a ".." component that would escape the base | ||
| 897 | //! dir, or a joined path that overflows the buffer) it logs the specific event | ||
| 898 | //! and returns false; the caller is responsible for failing the load. | ||
| 899 | bool resolveSequencePath(const Fw::StringBase& fileName, Fw::String& filePath); | ||
| 900 | |||
| 901 | //! Read `len` bytes of guest linear memory at `addr` into `dst` (via | ||
| 902 | //! spacewasm_mem_read on the pending host function's caller). | ||
| 903 | Fw::Success readGuestMemory(WasmSequencer_HostFunction::T kind, U32 addr, U8* dst, FwSizeType len); | ||
| 904 | |||
| 905 | //! Write `len` bytes from `src` into guest linear memory at `addr` (via | ||
| 906 | //! spacewasm_mem_write) | ||
| 907 | Fw::Success writeGuestMemory(WasmSequencer_HostFunction::T kind, U32 addr, const U8* src, FwSizeType len); | ||
| 908 | |||
| 909 | Fw::MemAllocator* m_allocator = nullptr; | ||
| 910 | |||
| 911 | //! Memory-resource configuration captured by configure() | ||
| 912 | Config m_config; | ||
| 913 | |||
| 914 | //! Page pool backing the process-wide spacewasm global page allocator for this instance. | ||
| 915 | //! Each page is `Svc::WasmSequencerConfig::SPACEWASM_PAGE_SIZE` with m_config.heapPages pages. | ||
| 916 | //! Stores dynamic memory allocated to hold each loaded module in the store (and the store itself). | ||
| 917 | U8** m_heapPages; | ||
| 918 | |||
| 919 | //! Number of currently used | ||
| 920 | FwSizeType m_heapPagesUsed; | ||
| 921 | |||
| 922 | //! A deallocation has poisoned the heap allocator | ||
| 923 | //! No more allocations can happen until every page is dropped. | ||
| 924 | //! SpaceWasm will drop everything in one shot so this simply helps us guard this invariant with an assertion | ||
| 925 | bool m_heapPoisoned; | ||
| 926 | |||
| 927 | //! Pool backing the per-load guest linear-memory allocator; a simple | ||
| 928 | //! bump allocator. `memory.grow` is enabled, but a bump allocator can only | ||
| 929 | //! service growth at the tail of the pool; see `guestRealloc`. | ||
| 930 | U8* m_guestPool; | ||
| 931 | |||
| 932 | //! Current bump offset into `m_guestPool`. | ||
| 933 | FwSizeType m_guestPoolOffset; | ||
| 934 | |||
| 935 | //! Opaque handle to the spacewasm engine, or null (before the store is initialized). | ||
| 936 | spacewasm_t* m_wasm; | ||
| 937 | |||
| 938 | //! Opaque handle to the spacewasm guest memory allocator, or null (before store/allocator is initialized) | ||
| 939 | spacewasm_allocator_t* m_guest_allocator; | ||
| 940 | |||
| 941 | //! Pending command waiting for a response | ||
| 942 | struct WaitingCmd { | ||
| 943 | FwOpcodeType opCode; | ||
| 944 | U32 cmdSeq; | ||
| 945 | |||
| 946 | 8 | WaitingCmd() : opCode(0), cmdSeq(0) {} | |
| 947 | ✗ | WaitingCmd(FwOpcodeType opCode_, U32 cmdSeq_) : opCode(opCode_), cmdSeq(cmdSeq_) {} | |
| 948 | }; | ||
| 949 | |||
| 950 | //! WAIT commands waiting for sequence completion | ||
| 951 | Fw::FifoQueue<WaitingCmd, WasmSequencerConfig::MAX_CONCURRENT_WAIT_COMMANDS> m_waiting; | ||
| 952 | |||
| 953 | //! Currently stored sequence arguments | ||
| 954 | Svc::SeqArgs m_args; | ||
| 955 | |||
| 956 | //! File path of the last module load | ||
| 957 | Fw::FileNameString m_lastLoadFileName; | ||
| 958 | |||
| 959 | WasmSequencer_RequestContext m_executingContext; | ||
| 960 | bool m_hasExecutingContext; | ||
| 961 | |||
| 962 | //! Pending timer from sleep host function | ||
| 963 | Fw::Time m_pendingTimer; | ||
| 964 | bool m_hasPendingTimer; | ||
| 965 | |||
| 966 | //! Wall-clock time at which the current blocking async host function | ||
| 967 | //! (COMMAND / blocking SERIAL_RECV) began awaiting its reply. Used to enforce | ||
| 968 | //! HOST_FUNCTION_TIMEOUT_SECS. Only meaningful while awaiting one of those. | ||
| 969 | Fw::Time m_hostFunctionStart; | ||
| 970 | bool m_hasHostFunctionStart; | ||
| 971 | |||
| 972 | bool m_dequeueSucceeded; | ||
| 973 | |||
| 974 | //! Flag indicating a function invocation failed | ||
| 975 | spacewasm_status_t m_invokeStatus; | ||
| 976 | |||
| 977 | //! Flag indicating interpreter is waiting to be paused | ||
| 978 | bool m_pendingPause; | ||
| 979 | |||
| 980 | //! Latches a CANCEL that arrives while a sequence is loading/resolving | ||
| 981 | bool m_cancelRequested; | ||
| 982 | |||
| 983 | //! Backing state for the periodically-written telemetry channels (see | ||
| 984 | //! writeTelemetry_handler). Grouped so the counters read as one unit. | ||
| 985 | struct Telemetry { | ||
| 986 | //! Sequences successfully completed | ||
| 987 | U64 sequencesSucceeded{0}; | ||
| 988 | |||
| 989 | //! Sequences that failed to validate or execute | ||
| 990 | U64 sequencesFailed{0}; | ||
| 991 | |||
| 992 | //! Sequences that were cancelled | ||
| 993 | U64 sequencesCancelled{0}; | ||
| 994 | |||
| 995 | //! Commands dispatched total | ||
| 996 | U64 commandsDispatched{0}; | ||
| 997 | |||
| 998 | //! Number of commands that failed | ||
| 999 | U64 commandsFailed{0}; | ||
| 1000 | |||
| 1001 | //! Currently running sequence name | ||
| 1002 | Fw::FileNameString sequenceName{""}; | ||
| 1003 | }; | ||
| 1004 | |||
| 1005 | Telemetry m_tlm; | ||
| 1006 | |||
| 1007 | //! Sequences started counter (bumped whenever the interpreter | ||
| 1008 | //! begins spinning a freshly-invoked program). The low 16 bits form the | ||
| 1009 | //! high half of the command context (cmdUid) so we can detect a command | ||
| 1010 | //! response that arrives late, after its originating sequence has ended. | ||
| 1011 | U32 m_sequencesStarted; | ||
| 1012 | |||
| 1013 | //! Compose the command context (cmdUid) sent to the command dispatcher from | ||
| 1014 | //! the current sequence counter and the m_tlm.commandsDispatched counter. The | ||
| 1015 | //! low 16 bits of the latter form the low half of the cmdUid, letting us | ||
| 1016 | //! detect a response for a different instance of the same opcode. | ||
| 1017 | U32 makeCmdUid() const; | ||
| 1018 | |||
| 1019 | //! Why the last sequence ended. Set as the program runs and classified into | ||
| 1020 | //! the appropriate completion event (see reportSequenceFailure in the controller). | ||
| 1021 | struct ExitStatus { | ||
| 1022 | //! Reason the current program exited. | ||
| 1023 | //! By default this is INTERPRETER but can be overriden from host functions | ||
| 1024 | WasmSequencer_ExitReason reason{WasmSequencer_ExitReason::UNKNOWN}; | ||
| 1025 | |||
| 1026 | //! Currently stored exit code for non-INTERPRETER exits | ||
| 1027 | I32 code{0}; | ||
| 1028 | |||
| 1029 | //! Last run host function that could have caused the error | ||
| 1030 | WasmSequencer_HostFunction lastHostFunction{WasmSequencer_HostFunction::NONE}; | ||
| 1031 | |||
| 1032 | //! Reason last sequence trapped | ||
| 1033 | WasmSequencer_TrapReason lastTrapReason{WasmSequencer_TrapReason::NONE}; | ||
| 1034 | }; | ||
| 1035 | |||
| 1036 | //! Status codes for exit reason. Set by the interpreter state machine. | ||
| 1037 | ExitStatus m_exit; | ||
| 1038 | |||
| 1039 | //! Buffer to hold the serial output port invocation invoked by the guest | ||
| 1040 | Fw::ExternalSerializeBuffer m_serialOutBuffer; | ||
| 1041 | |||
| 1042 | //! Queues (or queue) that handle inputs on the serial input port. Each is backed by | ||
| 1043 | //! the corresponding row of m_serialInQueueData (see the setup() loop in the ctor). | ||
| 1044 | Types::CircularBuffer m_serialInQueue[NUM_SERIALIN_INPUT_PORTS]; | ||
| 1045 | |||
| 1046 | //! A lock for guarding the serialInQueue | ||
| 1047 | Os::Mutex m_serialInMutex; | ||
| 1048 | |||
| 1049 | //! A host function call the guest requested that is pending dispatch by the | ||
| 1050 | //! engine state machine (see dispatchPendingHostFunction). `kind` selects | ||
| 1051 | //! which arm of the `u` union carries the call's arguments. | ||
| 1052 | struct PendingHostFunction { | ||
| 1053 | 1 | PendingHostFunction() = default; | |
| 1054 | ✗ | bool isPending() const { return kind != WasmSequencer_HostFunction::NONE; } | |
| 1055 | ✗ | void clear() { kind = WasmSequencer_HostFunction::NONE; } | |
| 1056 | |||
| 1057 | WasmSequencer_HostFunction kind{WasmSequencer_HostFunction::NONE}; | ||
| 1058 | |||
| 1059 | // Handle that holds the Wasm guest memory pointer | ||
| 1060 | spacewasm_caller_t* caller{nullptr}; | ||
| 1061 | |||
| 1062 | //! Per-kind call arguments. Only the arm matching `kind` is live. | ||
| 1063 | union Args { | ||
| 1064 | // COMMAND: encoded command payload in guest memory | ||
| 1065 | struct { | ||
| 1066 | U32 ptr; | ||
| 1067 | U32 len; | ||
| 1068 | } command; | ||
| 1069 | |||
| 1070 | // TELEMETRY: channel id plus where to write the serialized time and value | ||
| 1071 | struct { | ||
| 1072 | FwChanIdType chanId; | ||
| 1073 | U32 timePtr; | ||
| 1074 | U32 timeLen; | ||
| 1075 | U32 valuePtr; | ||
| 1076 | U32 valueLen; | ||
| 1077 | } telemetry; | ||
| 1078 | |||
| 1079 | // PARAMETER: parameter id plus where to write the serialized value | ||
| 1080 | struct { | ||
| 1081 | FwPrmIdType prmId; | ||
| 1082 | U32 ptr; | ||
| 1083 | U32 len; | ||
| 1084 | } parameter; | ||
| 1085 | |||
| 1086 | // EVENT: raw guest-requested severity (may be out of range) plus the message | ||
| 1087 | struct { | ||
| 1088 | U32 rawSeverity; | ||
| 1089 | U32 msgPtr; | ||
| 1090 | U32 msgLen; | ||
| 1091 | } event; | ||
| 1092 | |||
| 1093 | // RSLEEP: relative sleep duration | ||
| 1094 | struct { | ||
| 1095 | U64 us; | ||
| 1096 | } rsleep; | ||
| 1097 | |||
| 1098 | // ASLEEP: absolute sleep time | ||
| 1099 | struct { | ||
| 1100 | U64 us; | ||
| 1101 | } asleep; | ||
| 1102 | |||
| 1103 | // ARGS: where to write the stored sequence arguments | ||
| 1104 | struct { | ||
| 1105 | U32 ptr; | ||
| 1106 | U32 len; | ||
| 1107 | } args; | ||
| 1108 | |||
| 1109 | // TIME: where to write the serialized current time | ||
| 1110 | struct { | ||
| 1111 | U32 ptr; | ||
| 1112 | U32 len; | ||
| 1113 | } time; | ||
| 1114 | |||
| 1115 | // SERIAL_OUT: serial output port index plus payload in guest memory | ||
| 1116 | struct { | ||
| 1117 | U32 index; | ||
| 1118 | U32 ptr; | ||
| 1119 | U32 len; | ||
| 1120 | } serialOut; | ||
| 1121 | |||
| 1122 | // SERIAL_RECV: Read a message from the serialIn port queue given a port index | ||
| 1123 | struct { | ||
| 1124 | U32 index; | ||
| 1125 | U32 dataPtr; | ||
| 1126 | U32 dataSize; | ||
| 1127 | U32 actualSizePtr; | ||
| 1128 | Svc::BlockState::T blockingType; | ||
| 1129 | } serialRecv; | ||
| 1130 | |||
| 1131 | 1 | Args() : command{0, 0} {} | |
| 1132 | } u; | ||
| 1133 | }; | ||
| 1134 | |||
| 1135 | PendingHostFunction m_pendingHostFunction; | ||
| 1136 | |||
| 1137 | //! Helper function for checking the signature of a modules main function | ||
| 1138 | spacewasm_status_t validateModuleMain(WasmSequencer_ModuleIdx moduleIdx) const; | ||
| 1139 | |||
| 1140 | //! Report an engine-completion failure as the appropriate distinct event | ||
| 1141 | //! (SequenceExited / SequencePanic / SequenceTrapped / SequenceHostFailure, | ||
| 1142 | //! or SequenceCancelled) and bump the matching telemetry counter. `phase` | ||
| 1143 | //! records whether the failure occurred running the module's start function | ||
| 1144 | //! or its main entrypoint. | ||
| 1145 | void reportSequenceRuntimeFailure(WasmSequencer_ModuleIdx moduleIdx, WasmSequencer_SequencePhase phase); | ||
| 1146 | |||
| 1147 | //! Respond to a request with certain reply | ||
| 1148 | void respondToRequest(const Svc::WasmSequencer_RequestContext& value, const Fw::CmdResponse& response); | ||
| 1149 | |||
| 1150 | //! Send response to all waiting requests | ||
| 1151 | void respondToWaiting(const Fw::CmdResponse& response); | ||
| 1152 | |||
| 1153 | //! Report that a RUN finished on seqDoneOut (if connected) with the given | ||
| 1154 | //! response. Only emits for RUN-sourced requests, matching the RUN-gated | ||
| 1155 | //! seqStartOut in reportModuleStarted, so the seqStart/seqDone pair stays | ||
| 1156 | //! balanced. A no-op for INVOKE/LOAD, so both controller completion actions | ||
| 1157 | //! (respond_block_OK and respond_block_ERROR, which send the final command | ||
| 1158 | //! response) can call it unconditionally. | ||
| 1159 | void reportSeqDone(const Svc::WasmSequencer_RequestContext& value, const Fw::CmdResponse& response); | ||
| 1160 | |||
| 1161 | //! Report that a RUN ended before it ever started running on seqDoneOut (if | ||
| 1162 | //! connected) with the given response: rejected as BUSY, failed to load, failed to | ||
| 1163 | //! resolve an entrypoint, or cancelled while loading. | ||
| 1164 | void reportSeqAborted(const Svc::WasmSequencer_RequestContext& value, const Fw::CmdResponse& response); | ||
| 1165 | |||
| 1166 | //! Set a global to a value given the name of the module, global export name and value | ||
| 1167 | spacewasm_status_t setGlobal(const Fw::StringBase& moduleName, const Fw::StringBase& name, spacewasm_value_t value); | ||
| 1168 | |||
| 1169 | //! Get the value of a global variable given its module name and global name | ||
| 1170 | spacewasm_status_t getGlobal(const Fw::StringBase& moduleName, | ||
| 1171 | const Fw::StringBase& name, | ||
| 1172 | spacewasm_value_t& value); | ||
| 1173 | |||
| 1174 | //! Set up the fprime host interface | ||
| 1175 | void hostFprimeV1(spacewasm_host_t*); | ||
| 1176 | |||
| 1177 | /// FPrime Wasm Interface Host Functions | ||
| 1178 | spacewasm_hostcall_result_t wasmExit(struct spacewasm_caller_t* caller, | ||
| 1179 | const struct spacewasm_value_t* params, | ||
| 1180 | size_t n_params, | ||
| 1181 | struct spacewasm_value_t* out_result); | ||
| 1182 | |||
| 1183 | spacewasm_hostcall_result_t wasmPanic(struct spacewasm_caller_t* caller, | ||
| 1184 | const struct spacewasm_value_t* params, | ||
| 1185 | size_t n_params, | ||
| 1186 | struct spacewasm_value_t* out_result); | ||
| 1187 | |||
| 1188 | spacewasm_hostcall_result_t wasmArgs(struct spacewasm_caller_t* caller, | ||
| 1189 | const struct spacewasm_value_t* params, | ||
| 1190 | size_t n_params, | ||
| 1191 | struct spacewasm_value_t* out_result); | ||
| 1192 | |||
| 1193 | spacewasm_hostcall_result_t wasmTime(struct spacewasm_caller_t* caller, | ||
| 1194 | const struct spacewasm_value_t* params, | ||
| 1195 | size_t n_params, | ||
| 1196 | struct spacewasm_value_t* out_result); | ||
| 1197 | |||
| 1198 | spacewasm_hostcall_result_t wasmReadTelemetry(struct spacewasm_caller_t* caller, | ||
| 1199 | const struct spacewasm_value_t* params, | ||
| 1200 | size_t n_params, | ||
| 1201 | struct spacewasm_value_t* out_result); | ||
| 1202 | |||
| 1203 | spacewasm_hostcall_result_t wasmReadParameter(struct spacewasm_caller_t* caller, | ||
| 1204 | const struct spacewasm_value_t* params, | ||
| 1205 | size_t n_params, | ||
| 1206 | struct spacewasm_value_t* out_result); | ||
| 1207 | |||
| 1208 | spacewasm_hostcall_result_t wasmCommand(struct spacewasm_caller_t* caller, | ||
| 1209 | const struct spacewasm_value_t* params, | ||
| 1210 | size_t n_params, | ||
| 1211 | struct spacewasm_value_t* out_result); | ||
| 1212 | |||
| 1213 | spacewasm_hostcall_result_t wasmEvent(struct spacewasm_caller_t* caller, | ||
| 1214 | const struct spacewasm_value_t* params, | ||
| 1215 | size_t n_params, | ||
| 1216 | struct spacewasm_value_t* out_result); | ||
| 1217 | |||
| 1218 | spacewasm_hostcall_result_t wasmRsleep(struct spacewasm_caller_t* caller, | ||
| 1219 | const struct spacewasm_value_t* params, | ||
| 1220 | size_t n_params, | ||
| 1221 | struct spacewasm_value_t* out_result); | ||
| 1222 | |||
| 1223 | spacewasm_hostcall_result_t wasmAsleep(struct spacewasm_caller_t* caller, | ||
| 1224 | const struct spacewasm_value_t* params, | ||
| 1225 | size_t n_params, | ||
| 1226 | struct spacewasm_value_t* out_result); | ||
| 1227 | |||
| 1228 | spacewasm_hostcall_result_t wasmSerialOut(struct spacewasm_caller_t* caller, | ||
| 1229 | const struct spacewasm_value_t* params, | ||
| 1230 | size_t n_params, | ||
| 1231 | struct spacewasm_value_t* out_result); | ||
| 1232 | |||
| 1233 | spacewasm_hostcall_result_t wasmSerialRecv(struct spacewasm_caller_t* caller, | ||
| 1234 | const struct spacewasm_value_t* params, | ||
| 1235 | size_t n_params, | ||
| 1236 | struct spacewasm_value_t* out_result); | ||
| 1237 | |||
| 1238 | //! COMMAND: forward an encoded command from guest memory to the command dispatcher. | ||
| 1239 | void dispatchCommand(); | ||
| 1240 | |||
| 1241 | //! TELEMETRY: read a telemetry channel and write its value + time into guest memory. | ||
| 1242 | void dispatchTelemetry(); | ||
| 1243 | |||
| 1244 | //! PARAMETER: read a parameter and write it into guest memory. | ||
| 1245 | void dispatchParameter(); | ||
| 1246 | |||
| 1247 | //! EVENT: emit a guest-requested event at the guest-requested severity. | ||
| 1248 | void dispatchEvent(); | ||
| 1249 | |||
| 1250 | //! RSLEEP: arm a relative sleep timer. | ||
| 1251 | void dispatchRelativeSleep(); | ||
| 1252 | |||
| 1253 | //! ASLEEP: arm an absolute sleep timer. | ||
| 1254 | void dispatchAbsoluteSleep(); | ||
| 1255 | |||
| 1256 | //! ARGS: write the stored sequence arguments into guest memory. | ||
| 1257 | void dispatchArgs(); | ||
| 1258 | |||
| 1259 | //! TIME: write the current time into guest memory. | ||
| 1260 | void dispatchTime(); | ||
| 1261 | |||
| 1262 | //! SERIAL_OUT: copy a payload out of guest memory and invoke the serial output port. | ||
| 1263 | void dispatchSerialOut(); | ||
| 1264 | |||
| 1265 | //! SERIAL_RECV: check the serial input queue and either resume or block awaiting a message. | ||
| 1266 | void dispatchSerialRecv(); | ||
| 1267 | |||
| 1268 | // A global static lock. This is needed to allow the global allocator in spacewasm | ||
| 1269 | // to not require to pass context to fine grained context to allocations. | ||
| 1270 | // Read more about this in the SDD. | ||
| 1271 | static Os::Mutex* getGlobalAllocatorLock(); | ||
| 1272 | }; | ||
| 1273 | |||
| 1274 | } // namespace Svc | ||
| 1275 | |||
| 1276 | #endif | ||
| 1277 |