The `_is_port_in_use` bind check was wrong for `-R` tunnels: local_port is
the forward target (e.g. a Docker container), so it should be listening,
not free. Drop the check — autossh doesn't require the target to be
reachable at startup.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Exercises the complete PID file lifecycle end-to-end using a real subprocess
with a fake autossh (sleep 60 script), covering start, stop, status, stale PID
cleanup, restart, and idempotency scenarios.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Implements build_autossh_cmd, start_tunnel, and stop_tunnel in process.py.
Adds _reap() helper to handle zombie processes in test environments where
the parent process is long-lived (SIGKILL leaves zombies unless waitpid is called).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Created .gitignore with standard Python patterns
- Removed committed __pycache__/__init__.cpython-314.pyc from git tracking
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>