Files
alkssh/src/lib.rs
T
glm-5.3-flash d37cbc0c8a test(fuzz): the four-target fuzz sidecar (w5-fuzz-harness)
The family standing rule (anything worth fuzzing gets fuzzed) on the
crate's ingress surfaces, per the alkgit convention:

- fuzz_targets/{exec_parse,fingerprint,key_decode,terminal_params} —
  thin fuzz_target! wrappers over four ingress surfaces:
  - exec_parse: the production parse path (from_utf8-fallback ingress
    shape), differentially paired against a from-spec grammar oracle;
    typed routing classes + determinism.
  - fingerprint: blob parse + the single fingerprint path; the
    SHA256:/unpadded-base64 contract shape via a from-spec
    base64 round-trip oracle; the committed ssh-keygen -lf vectors
    replayed inside the gate.
  - key_decode: the production decode arm (the #[doc(hidden)]
    decode_key_arm exposure, routed through itself); typed-class +
    bounded-fixed-message invariants; passphrase-shape robustness
    drive on the underlying decode.
  - terminal_params: the pty_request conversion via the #[doc(hidden)]
    terminal_params exposure; exact clamp, verbatim term, the
    reserved-modes {} JSON shape, serialized-shape determinism.
- shared/ — the invariant logic as a stable-clean library; the
  corpus gate (cargo test --manifest-path fuzz/shared/Cargo.toml)
  replays every committed seed through the batteries and joins
  AGENTS.md's verification list.
- corpus/<target>/ committed seeds + the deterministic
  gen_fuzz_seeds.py (no-op-diff verified).
- run-detached.sh + nightly pin; the sidecar excluded from the root
  workspace (workspace + package excludes; publish dry-run clean).

Exposure shape decided + recorded per target (README + lib.rs doc
comments): fingerprint needs none (fully public ingress); the rest
are #[doc(hidden)] re-exports of the production surfaces, never
forks. Detached campaigns ran per target (600 s default budget, fork
mode): all four clean; the two findings of the first round are
recorded in the task file (the harness oracle's double-/-strip bug;
the PPK echo fixed in the preceding commit).

Verification: corpus gate green (11 tests); scripts/matrix.sh green;
taskgraph validate clean.
2026-10-30 11:44:21 +00:00

132 lines
5.7 KiB
Rust
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
//! alkssh — the alk family's SSH adapter (the alkhttp-style door for the
//! SSH protocol): a thin wrapper around russh terminating the vanilla-ssh
//! wire and bridging to/from alkcall channels (the `alk/ssh` ALPN).
//!
//! No SSH framing is authored in-family (family ADR-003): russh owns the
//! wire, and the crate's substance is the channel-type mappings —
//! session/pty → alktty, direct/forwarded-tcpip → alktunnels, git exec →
//! alkgit, sftp → alkfs later (a declining placeholder until then), each
//! behind its cargo feature. Git over SSH is exec-only (ADR-006): a
//! subsystem request can never carry the repository, so it declines. A
//! client opening an unfeatured or unimplemented channel type gets a
//! clean decline — never a half-capability, never a silent fallback; the
//! default build (no features) is structurally incapable of serving
//! anything but declines.
//!
//! Identity is the family's, not SSH's: a verified key's fingerprint →
//! alkcall `IdentityProvider`. Keys the crate holds (client dial keys,
//! host keys) come from alkvault-backed sources — vault-encrypted at
//! rest, decrypted at use (ADR-005), never env vars.
//!
//! Architecture: `docs/architecture/` (phase 1 — ADRs 001–006 accepted;
//! the foundations, the server stack, the server-direction mappings, and
//! the client direction — dial, op rows, the `-R` acceptor leg, and the
//! lifecycle primitives — are landed through wave 4; the validation
//! suite and the release are wave 5). See also `docs/research/`,
//! `docs/plans/implementation.md`, and family ADR-003.
mod adapter;
mod channel_cap;
mod client;
#[cfg(feature = "tunnel")]
mod client_accept;
mod client_handler;
mod client_ops;
mod config;
mod dispatch;
mod error;
#[cfg(any(feature = "session", feature = "git"))]
mod exit_code;
mod fingerprint;
#[cfg(feature = "git")]
mod git_map;
mod handler;
mod host_key;
mod key_source;
mod observe;
mod serve;
#[cfg(feature = "session")]
mod tty_map;
#[cfg(feature = "tunnel")]
mod tunnel_map;
pub use adapter::SshAdapter;
pub use client::SshConnection;
pub use client::dial;
/// Contract-test surface (`#[doc(hidden)]`): the dial surface's
/// config-mapping and handler-skeleton mechanics (the `serve.rs`
/// §Test-surface mirror; see `client.rs` §Test surface). Not
/// documented API.
#[doc(hidden)]
pub use client::russh_client_config;
/// The `-R` leg's acceptor registry + the reverse-listen rows'
/// payload/acceptor types + the listener handles (`w4-reverse-listen`
/// / `w4-lifecycle` — under `tunnel`; the recorded decisions live in
/// the `client_accept` module docs).
#[cfg(feature = "tunnel")]
pub use client_accept::{
AcceptorHeld, AcceptorRegistry, ForwardedStreamlocal, ForwardedTcpip, ReverseEndpoint,
ReverseListener, StreamlocalForwardedAcceptor, TcpipForwardedAcceptor,
};
#[doc(hidden)]
pub use client_handler::ClientHandler;
/// The client op rows' surfaces (`w4-op-rows`):
/// [`RemoteSession`](client_ops::RemoteSession) — the exec/pty rows'
/// family chunk plane (under `session`),
/// [`TunnelChannel`](client_ops::TunnelChannel) — the direct
/// rows' byte duplex (under `tunnel`),
/// [`GitPackSession`](client_ops::GitPackSession) — the upstream git
/// row's pack duplex + consumed exit (under `git`). The op methods
/// live on [`SshConnection`] (the op-row surface). Not a re-export
/// here: the `sftp` row is [`SshConnection::sftp`] itself — the
/// every-build OQ-13 decline placeholder.
#[cfg(feature = "git")]
pub use client_ops::GitPackSession;
#[cfg(feature = "session")]
pub use client_ops::RemoteSession;
#[cfg(feature = "tunnel")]
pub use client_ops::TunnelChannel;
#[cfg(feature = "git")]
pub use config::GitSeam;
#[cfg(feature = "session")]
pub use config::SessionSeam;
#[cfg(feature = "tunnel")]
pub use config::TunnelListenSeam;
pub use config::{DialConfig, Limits, ServeConfig};
/// Fuzz-visible surface (`#[doc(hidden)]`, `w5-fuzz-harness`): the exec
/// grammar's parse path (`dispatch.rs`) — the `fuzz/` sidecar's
/// `exec_parse` target drives the production parse, never a fork. Not
/// documented API: the grammar is the dispatch seam's, not a public-API
/// promise.
#[doc(hidden)]
pub use dispatch::{ExecDecline, ExecRoute, GitServiceRoute, parse_exec};
pub use error::{AdapterError, DialError, KeySourceError, OpError, OpenDeclineReason};
pub use fingerprint::fingerprint;
/// Contract-test surface (`#[doc(hidden)]`): the per-connection auth
/// bridge handler — constructible so the tests drive its hooks directly
/// against the wave-1 doubles (see `handler.rs` §Test surface). Not
/// documented API: the wire-facing surface is exactly `SshAdapter` +
/// the config/error/host/key-source types.
#[doc(hidden)]
pub use handler::SessionHandler;
pub use host_key::{HostKeyPolicy, PresentedHostKey, RejectAll};
/// Fuzz-visible surface (`#[doc(hidden)]`, `w5-fuzz-harness`): the
/// decrypt-at-use chain's decode arm (`key_source.rs`, the production
/// `decrypt_and_decode` conversion). Not documented API.
#[doc(hidden)]
pub use key_source::decode_key_arm;
pub use key_source::{HostKeySource, KeySource, VaultHostKeySource, VaultKeySource};
/// Contract-test surface (`#[doc(hidden)]`): the spawn-and-return
/// plumbing (`ADR-006 decision 4`, see `serve.rs`) — the mechanics the
/// mechanics-proof rows in `tests/spawn_return.rs` compose over the
/// real wire to pin the constraint as tests. Not documented API.
#[doc(hidden)]
pub use serve::{report_exit_status_then_close, spawn_serving_path};
/// Fuzz-visible surface (`#[doc(hidden)]`, `w5-fuzz-harness`, under
/// `session`): the `pty_request` args → `TerminalParamsWire`
/// conversion (`tty_map.rs`, OQ-44's reserved modes). Not documented
/// API.
#[cfg(feature = "session")]
#[doc(hidden)]
pub use tty_map::terminal_params;