skillmake
← marketplace
devopstoolsha:1a300940a7ca1792manual

ssh-doctor

Use when working with sSH triage: Remote Login, launchd sshd, pre-auth closes, stale sessions from steipete/agent-scripts.

Install confidence
curl --create-dirs -fsSL https://skillmake.xyz/i/ssh-doctor -o ~/.claude/skills/ssh-doctor/SKILL.md
Pinned content
sha:1a300940a7ca1792
Generated with
manual
Source
github.com

The file served at /api/marketplace/ssh-doctor-1a300940/raw matches this hash. Inspect before install, then copy the command.

5,164 chars · ~1,291 tokens
---
name: ssh-doctor
description: "Use when working with sSH triage: Remote Login, launchd sshd, pre-auth closes, stale sessions from steipete/agent-scripts."
source: https://github.com/steipete/agent-scripts/tree/main/skills/ssh-doctor
generated: 2026-05-27T20:56:35.345Z
category: tool
audience: devops
---

## When to use

- SSH connects then closes before auth, Remote Login seems advertised but unusable, or local/remote Mac SSH needs diagnosis.
- Using the ssh-doctor skill's upstream workflow, guardrails, and local-tool assumptions.
- Auditing commands or operational steps before changing ssh doctor behavior.
- Needing a compact agent reference for sSH triage: Remote Login, launchd sshd, pre-auth closes, stale sessions.

## Key concepts

### Rules

Do not print secrets, tokens, full env, or broad secret grep output. Validate locally first: loopback failure means server-side sshd/launchd/config; loopback success plus remote failure means network/firewall/filter/listen path. Report suspicious config lines before changing /etc/ssh/sshdconfig. Prefer non-interactive SSH:.

### Baseline

Use BatchMode=yes only when password fallback would hang or prompt.

### Config

Suspicious: DenyUsers matching target user restrictive AllowUsers / AllowGroups Match block accidentally applying tiny MaxStartups tiny LoginGraceTime ListenAddress missing target interface.

### Logs

Important Mac symptom: client: kexexchangeidentification: Connection closed by remote host server log: Could not create new instance of inetd service: 67: Too many processes launchctl print system/com.openssh.sshd: high copy count many sshd-session: USER processes parented by PID 1 This means launchd accepted TCP but refused to spawn more sshd inetd copies.

### Stale sshd-session Fix

Inspect first: If stale sessions are clearly stranded and blocking new SSH, terminate by selected command-line match: If TERM leaves blockers, re-check ownership and active shells before using KILL.

### Firewall

Only after loopback works but remote fails: Also check listen address and target interface:.

## API reference

```
npx skills add steipete/agent-scripts --skill ssh-doctor
```

Install the ssh-doctor skill from steipete/agent-scripts.

```
npx skills add steipete/agent-scripts --skill ssh-doctor
```

```
ssh -o RequestTTY=no -o RemoteCommand=none HOST 'hostname; id -un'.
```

Command or snippet documented by the upstream ssh-doctor skill.

```
ssh -o RequestTTY=no -o RemoteCommand=none HOST 'hostname; id -un'
```

```
hostname; id -un; swvers.
```

Command or snippet documented by the upstream ssh-doctor skill.

```
hostname; id -un; sw_vers
ipconfig getifaddr en0
ipconfig getifaddr en1 2>/dev/null || true
ipconfig getifaddr en7 2>/dev/null || true
sudo systemsetup -getremotelogin
sudo systemsetup -setremotelogin on
sudo launchctl print system/com.openssh.sshd 2>&1 | head -80
sudo launchctl kickstart -k system/com.openssh.sshd
sudo lsof -nP -iTCP:22 -sTCP:LISTEN
nc -vz 127.0.0.1 22
ssh -4 -F /dev/null -o RequestTTY=no -o RemoteCommand=none USER@127.0.0.1 'hostname; id -un'
```

```
sudo sshd -T 2>&1 | egrep -i '^(allowusers|denyusers|allowgroups|denygroups|listenaddress|maxstartups|logingracetime|...
```

Command or snippet documented by the upstream ssh-doctor skill.

```
sudo sshd -T 2>&1 | egrep -i '^(allowusers|denyusers|allowgroups|denygroups|listenaddress|maxstartups|logingracetime|usepam|passwordauthentication|pubkeyauthentication|authenticationmethods)'
sudo egrep -n '^[[:space:]]*(AllowUsers|DenyUsers|AllowGroups|DenyGroups|Match|MaxStartups|LoginGraceTime|ListenAddress|AuthenticationMethods|UsePAM|PasswordAuthentication|PubkeyAuthentication)\b' /etc/ssh/sshd_config /etc/ssh/sshd_config.d/* 2>/dev/null || true
```

```
sudo log show --last 30m --predicate 'process == "sshd" OR process == "launchd"' --style compact | tail -160.
```

Command or snippet documented by the upstream ssh-doctor skill.

```
sudo log show --last 30m --predicate 'process == "sshd" OR process == "launchd"' --style compact | tail -160
```

```
sudo launchctl print system/com.openssh.sshd 2>&1 | egrep 'active count|copy count|state =|last exit code|runs ='.
```

Command or snippet documented by the upstream ssh-doctor skill.

```
sudo launchctl print system/com.openssh.sshd 2>&1 | egrep 'active count|copy count|state =|last exit code|runs ='
ps -axo pid,ppid,uid,user,state,lstart,etime,comm,args | awk '/sshd-session:/ && !/awk/ {print}'
sudo lsof -nP -c sshd-session -iTCP 2>/dev/null | head -120
```

```
ps -axo pid=,args= | awk '/sshd-session: / && !/awk/ {print $1}' | xargs sudo kill -TERM.
```

Command or snippet documented by the upstream ssh-doctor skill.

```
ps -axo pid=,args= | awk '/sshd-session: / && !/awk/ {print $1}' | xargs sudo kill -TERM
sleep 2
ps -axo pid=,args= | awk '/sshd-session: / && !/awk/ {print}'
```

## Gotchas

- Do not print secrets, tokens, full env, or broad secret grep output.
- Prefer non-interactive SSH:.
- never echo the token.

---
Generated by SkillMake from https://github.com/steipete/agent-scripts/tree/main/skills/ssh-doctor on 2026-05-27T20:56:35.345Z.
Verify against source before relying on details.

File: ~/.claude/skills/ssh-doctor/SKILL.md