Files
sausage/userland/ssh

SSH in the world

ssh executes one remote command without a PTY or an interactive shell. It buffers stdin and captures stdout and stderr until the remote channel closes. It returns the remote exit status. Connection, trust, and authentication failures return 255.

ssh -p 2222 -l user -o StrictHostKeyChecking=accept-new host 'echo hi; exit 3'

The default host-key policy requires a matching key in $HOME/.ssh/known_hosts. The client creates .ssh if needed. StrictHostKeyChecking=accept-new appends an unknown key. A changed or revoked key always fails. The client supports Ed25519 keys and curve25519 key exchange, as v2 did.

The private key stays in the host. The client requests a public identity from POST http://host.sausage/ssh/identity. It requests a signature from POST http://host.sausage/ssh/sign. SAUSAGE_HOST_API replaces the base URL for standalone tests. The URL or -l supplies the user. Otherwise, the host identity supplies it. A host denial preserves the item and request information in stderr.

Tests

Build from userland/ after the shared startup object exists:

CARGO_TARGET_DIR=/tmp/p1-ssh/target nix develop .. -c cargo build -p ssh -p git --release --locked

Build the native test fixture from the repository root:

CARGO_TARGET_DIR=/tmp/p1-ssh/server-target nix develop -c cargo build --manifest-path userland/ssh/tests/server/Cargo.toml --locked

Start the fixture through a managed job or a separate terminal:

nix shell nixpkgs#openssh -c /tmp/p1-ssh/server-target/debug/ssh-test-server /tmp/p1-ssh/fixture user

Use the current native user's login name instead of user. The fixture creates ready.json after sshd and the signing server start. It keeps all private keys under fixture/host, outside the guest preopen. It serves the two host routes and a test-only host-key rotation route.

nix develop -c nu userland/ssh/test.nu /tmp/p1-ssh/target/wasm32-wasip2/release/ssh.wasm /tmp/p1-ssh/fixture

The Git script needs a separate fresh fixture because the SSH script changes its host key:

nix develop -c nu userland/git/ssh-test.nu /tmp/p1-ssh/target/wasm32-wasip2/release/git.wasm /tmp/p1-ssh/target/wasm32-wasip2/release/ssh.wasm /tmp/p1-ssh/git-fixture

Both scripts check that the components import only WASI interfaces. They enable TCP, DNS, HTTP, and numeric exit codes through Wasmtime's standard options.