docs
This commit is contained in:
@@ -193,6 +193,7 @@ MAX_MEMORY=16777216
|
||||
SESSION_TIME=2592000
|
||||
|
||||
HTTP_PORT=8080
|
||||
WS_BROKER_OUTBOUND_TIMEOUT_SECONDS=30
|
||||
```
|
||||
|
||||
Important settings:
|
||||
@@ -204,6 +205,7 @@ Important settings:
|
||||
- `BIN_DIRECTORY` stores generated C++, wasm artifacts, compile output, and runtime caches.
|
||||
- `TMP_UPLOAD_PATH` and `SESSION_PATH` must be writable by the runtime.
|
||||
- `HTTP_PORT` is the built-in HTTP/WebSocket listener used for WebSocket upgrade traffic and direct local probes. Bind/firewall it for local access only; nginx/Apache should be the public entry point.
|
||||
- `WS_BROKER_OUTBOUND_TIMEOUT_SECONDS` controls how long a forwarded WS message can remain queued in the broker before being dropped (default `30`). Set to `0` to disable the timeout.
|
||||
- `WASM_COMPILE_SCRIPT` must point to `scripts/compile_wasm_unit` unless you provide an equivalent compiler. Relative paths are resolved from the runtime root/`COMPILER_SYS_PATH`. That script calls `scripts/check_unit_wasm.py` after linking each unit and uses the pinned WASI SDK on every deployment host.
|
||||
- `WASM_CORE_PATH` must point at the built `core.wasm` file.
|
||||
|
||||
|
||||
@@ -85,6 +85,14 @@ the boundary).
|
||||
See [`docs/wasm-phase1-dvalue-abi.md`](wasm-phase1-dvalue-abi.md) for the wire
|
||||
format details.
|
||||
|
||||
Decoder robustness note: UCEB input is untrusted across the wasm membrane. The
|
||||
UCEB decoder must reject malformed magic/version/varint/length/trailing-data
|
||||
inputs and excessive nesting with explicit errors, not native or wasm traps. Its
|
||||
current hard nesting cap is intentionally low (64 levels) to stay well below the
|
||||
guest stack limit. JSON decoding follows the same rule for malformed strings and
|
||||
unicode escapes: validate bounds before every read and return an empty/partial
|
||||
`DValue` rather than reading beyond the input.
|
||||
|
||||
---
|
||||
|
||||
## 3. Units, handlers, and export naming
|
||||
@@ -144,6 +152,19 @@ suspend the native SIGSEGV/SIGILL recovery handler around the wasm call so that
|
||||
Wasmtime's own trap signals are not escalated into a native fatal signal (see
|
||||
`serve_via_wasm` in `handle_complete`).
|
||||
|
||||
### Task callbacks and workspace lifetime
|
||||
|
||||
`task()` and `task_repeat()` are fork-backed. The `uce_host_task_spawn` hostcall
|
||||
captures the current `WasmWorkspace*`, but `src/lib/sys.cpp::task()` invokes the
|
||||
captured callback only in the forked child, before the hostcall stack unwinds in
|
||||
that child. The parent request may return and destroy its workspace; the child
|
||||
still has its own copy-on-write stack and its own copy of the per-request wasm
|
||||
workspace. This means a delayed task callback can run after the spawning request
|
||||
returns without dereferencing the parent's destroyed workspace. It is still a
|
||||
callback into the inherited child workspace, not a fresh normal request
|
||||
workspace; avoid adding host resources to `WasmWorkspace` that are invalid across
|
||||
`fork()` unless task callback handling is changed to birth a fresh workspace.
|
||||
|
||||
---
|
||||
|
||||
## 5. Request dispatch (`handle_complete`)
|
||||
@@ -198,12 +219,14 @@ broker loop:
|
||||
a non-empty STDIN makes the FastCGI transport flush a premature response
|
||||
before `on_complete` ever runs.
|
||||
3. Connect to `/run/uce.sock` (non-blocking) and queue the encoded request in
|
||||
`ws_broker_outbound[fd]`.
|
||||
`ws_broker_outbound[fd]` with an enqueue timestamp.
|
||||
|
||||
`ws_broker_drain_outbound()` runs after every `process(50)` tick: it finishes
|
||||
writing each queued request, then drains and discards the reply (the unit's
|
||||
output comes back via the command socket, not this reply), closing the fd when
|
||||
the worker closes its end.
|
||||
the worker closes its end. If a forward remains pending beyond
|
||||
`WS_BROKER_OUTBOUND_TIMEOUT_SECONDS` (default `30`), the broker drops and
|
||||
closes it so a wedged worker cannot pin broker fds/memory indefinitely.
|
||||
|
||||
### 6.2 Outbound: `ws_*` commands flushed back to the broker
|
||||
|
||||
@@ -211,8 +234,10 @@ Any unit code — not just WebSocket handlers — may call `ws_send` / `ws_send_
|
||||
/ `ws_close`. In the workspace these **record dispatch commands** rather than
|
||||
touching a socket (the workspace owns no connections); `wasm-core`'s `ws_*`
|
||||
(`src/lib/sys.cpp`) append to `websocket_dispatch_commands`, and
|
||||
`finish_response_meta` (`src/wasm/core.cpp`) emits them as `ws_commands` (plus
|
||||
`ws_connection_state` if the handler mutated per-connection state).
|
||||
`finish_response_meta` (`src/wasm/core.cpp`) emits them as `ws_commands`.
|
||||
If the handler changed per-connection state, the core also emits
|
||||
`ws_connection_state` even when no commands were emitted, and the native
|
||||
backend flushes this state-only batch to the broker.
|
||||
|
||||
`wasm_backend_serve` (`src/wasm/backend.cpp`) flushes that batch at workspace
|
||||
teardown — in **any** scenario, not just WS handlers — to the broker's command
|
||||
@@ -239,9 +264,10 @@ serve_http dispatcher uses, so there is no duplicated request-forwarding code.
|
||||
handlers (it renders nothing, so it accepts every request straight through to
|
||||
`on_complete`), wires `on_complete=ws_broker_complete` and
|
||||
`on_websocket_message=ws_broker_ws_message`, listens on `HTTP_PORT` and the
|
||||
command socket, and loops `process(50)` + `drain_outbound()`. The design is
|
||||
**non-blocking outbound dispatch + async command-socket flush, all in the
|
||||
broker's single epoll loop** — the broker never blocks on a worker.
|
||||
command socket, and loops `process(50)` + `drain_outbound(timeout)`. The
|
||||
`timeout` comes from `WS_BROKER_OUTBOUND_TIMEOUT_SECONDS` (default `30`). The
|
||||
design is **non-blocking outbound dispatch + async command-socket flush, all in
|
||||
the broker's single epoll loop** — the broker never blocks on a worker.
|
||||
|
||||
The parent respawns the broker if it dies (`ws_broker_alive` / `ensure_ws_broker`
|
||||
in `main()`).
|
||||
@@ -288,6 +314,7 @@ header free-functions are `inline`. The wasm backend exposes only declarations
|
||||
| `CLI_SOCKET_PATH` | `/run/uce/cli.sock` | Worker CLI socket. |
|
||||
| `HTTP_PORT` | `8080` | Raw HTTP + WebSocket port — owned by the WS broker. |
|
||||
| `WS_BROKER_SOCKET_PATH` | `/run/uce/ws-broker.sock` | Broker command socket for `ws_*` flushes. |
|
||||
| `WS_BROKER_OUTBOUND_TIMEOUT_SECONDS` | `30` | Max lifetime in seconds for queued WS broker forwards before drop. |
|
||||
| `WORKER_COUNT` | `4` | Number of uniform worker processes. |
|
||||
|
||||
---
|
||||
|
||||
Reference in New Issue
Block a user