Support RUST_LOG, enable UPnP portmapper and add NAT traversal logging

Previously, `tsunagi-cli` configured clap with a fixed default_value and
`env = "TSUNAGI_LOG"`, which caused `RUST_LOG` to be completely ignored.
In addition, `iroh` was built with `default-features = false` and lacked the
`"portmapper"` feature, which caused it to compile a stub client and disable
UPnP-IGD, PCP, and NAT-PMP port mapping. Furthermore, there was no visibility
into STUN address discovery, UPnP port mapping status, or QUIC transmission path
switching (hole punch vs relay).

Key improvements:
- Enable the `"portmapper"` feature on `iroh` in workspace Cargo.toml, pulling in
  `portmapper` and `igd-next` to actively request port mappings on local routers.
- In `crates/tsunagi-cli/src/main.rs`, support `RUST_LOG` with fallback precedence
  (`--log` > `TSUNAGI_LOG` > `RUST_LOG` > default filter). When debug or trace
  filtering is active, automatically enable `.with_target(true)` so users can see
  which subsystem emitted the log (e.g., portmapper, iroh::magicsock, tsunagi::net).
- In `crates/tsunagi/src/net.rs`, monitor `endpoint.watch_addr()` and
  `endpoint.home_relay_status()`. Emit `DEBUG` logs for local socket binding,
  discovered STUN reflexive/UPnP addresses, and relay connections. If no direct
  addresses are discovered after probe grace, emit a concise `WARN`.
- In `crates/tsunagi/src/agent/session.rs`, monitor connection `path_events()`
  to log when transmission paths are opened, closed, or selected (switching between
  relay and direct hole-punched paths), with bounded task winding down on shutdown.

Validation on Linux:
- cargo fmt --all -- --check passed.
- cargo clippy --locked --workspace --all-targets -- -D warnings passed.
- cargo test --locked --workspace --all-targets passed (349 tests passed).
- Live verification with `RUST_LOG=debug` confirmed SSDP broadcast to 239.255.255.250:1900,
  portmapper logs, STUN QAD discovery, and clean relay shutdown.
This commit is contained in:
Aleksandr Bogomiakov committed 2026-09-30 23:08:23 +01:00
1 parent c0a76f1942
commit 192ab25bbd
6 files changed
+262 -12

No files matched your search

+16 -9
View File
@@ -33,13 +33,10 @@ use tsunagi_wg_quic::{WireguardConfig, WireguardPlugin};
#[command(name = "tsunagi", version, about, long_about = None)]
struct Cli {
/// Log filter, for example `info` or `tsunagi=debug`.
#[arg(
long,
global = true,
env = "TSUNAGI_LOG",
default_value = "info,iroh=warn,quinn=warn,rustls=warn,boringtun=warn,mainline=off"
)]
log: String,
///
/// Can also be set via the `TSUNAGI_LOG` or `RUST_LOG` environment variables.
#[arg(long, global = true)]
log: Option<String>,
#[command(subcommand)]
command: Command,
@@ -696,9 +693,19 @@ fn parse_peer(text: &str) -> Result<EndpointAddr, String> {
fn main() -> std::process::ExitCode {
let cli = Cli::parse();
let log_filter = cli
.log
.or_else(|| std::env::var("TSUNAGI_LOG").ok())
.or_else(|| std::env::var("RUST_LOG").ok())
.unwrap_or_else(|| {
"info,iroh=warn,quinn=warn,rustls=warn,boringtun=warn,mainline=off".to_string()
});
let is_debug = log_filter.contains("debug") || log_filter.contains("trace");
tracing_subscriber::fmt()
.with_env_filter(tracing_subscriber::EnvFilter::new(&cli.log))
.with_target(false)
.with_env_filter(tracing_subscriber::EnvFilter::new(&log_filter))
.with_target(is_debug)
.compact()
.with_writer(std::io::stderr)
.init();