Skip to content

UberKitten/ephemeral-agent

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Ephemeral SSH Agent

A memory-only SSH agent for Windows. Keys live in RAM — never written to disk, registry, or DPAPI.

Why?

The built-in Windows OpenSSH agent (ssh-agent service) silently persists every key you add to the Windows registry using DPAPI encryption. Any process running as your user can decrypt those keys without admin privileges, UAC prompts, or any notification. Your "temporary" SSH keys become permanent attack surface.

Ephemeral Agent holds keys in process memory only. When it exits, keys are gone. No registry, no disk, no DPAPI.

Features

  • 🔑 Memory-only key storage — keys never touch disk or registry
  • 🔌 Drop-in replacement — listens on the standard \\.\pipe\openssh-ssh-agent pipe
  • 🖥️ System tray icon — shows key status (grey = empty, green = keys loaded)
  • 📋 Right-click menu — clear keys, exit
  • 🚀 Login autostart--install registers in HKCU\...\Run
  • 📦 Single binary — no installer, no dependencies, no runtime
  • 🪵 Logging — file log for diagnostics, --debug for console output

Quick Start

1. Disable the built-in agent

# Disable the Windows SSH agent service (requires admin)
Set-Service ssh-agent -StartupType Disabled
Stop-Service ssh-agent

If you're using another SSH agent (Bitwarden, 1Password, etc.), disable its agent feature too — only one process can listen on the pipe.

2. Run

Download ephemeral-agent.exe from Releases and place it somewhere permanent (e.g., C:\Users\you\bin\).

# Run it
.\ephemeral-agent.exe

# Register to start on login
.\ephemeral-agent.exe --install

# Remove autostart
.\ephemeral-agent.exe --uninstall

3. Load keys

# Load a key (prompts for passphrase if the key has one)
ssh-add ~/.ssh/id_ed25519

# Load all default key files (~/.ssh/id_rsa, id_ed25519, etc.)
ssh-add

# List loaded keys
ssh-add -l

# Remove all keys
ssh-add -D

The system tray icon turns green when keys are loaded.

Loading Keys at Login

You can create a simple script to load your keys on login. For passphrase-protected keys, ssh-add will prompt you interactively:

# load-keys.ps1 — run at login via scheduled task or shortcut in shell:startup
ssh-add "$env:USERPROFILE\.ssh\id_ed25519"
ssh-add "$env:USERPROFILE\.ssh\work_key"

To run automatically at login, create a scheduled task:

$action = New-ScheduledTaskAction -Execute "powershell.exe" `
    -Argument "-NoProfile -File `"$env:USERPROFILE\bin\load-keys.ps1`""
$trigger = New-ScheduledTaskTrigger -AtLogOn -User $env:USERNAME
Register-ScheduledTask -TaskName "Load SSH Keys" -Action $action -Trigger $trigger

How It Works

Ephemeral Agent uses Go's golang.org/x/crypto/ssh/agent package, which provides a complete implementation of the SSH agent protocol. Keys are stored in an in-memory keyring (agent.NewKeyring()).

The agent listens on a Windows named pipe at \\.\pipe\openssh-ssh-agent — the same endpoint that ssh.exe, ssh-add.exe, and other OpenSSH tools expect. The pipe's default security descriptor restricts access to the creating user and SYSTEM.

There is no persistence layer. When the process exits, all keys are gone.

Building

# Cross-compile from any OS
GOOS=windows GOARCH=amd64 CGO_ENABLED=0 go build -ldflags="-H=windowsgui -s -w" -o ephemeral-agent.exe

# The -H=windowsgui flag prevents a console window from appearing on launch

Or grab a prebuilt binary from Releases.

Debug Mode

Run with --debug to get console output instead of the system tray:

.\ephemeral-agent.exe --debug
# [ephemeral-agent] 2026/03/15 22:02:49 starting ephemeral-agent
# [ephemeral-agent] 2026/03/15 22:02:49 listening on \\.\pipe\openssh-ssh-agent
# [ephemeral-agent] 2026/03/15 22:02:54 connection #1 accepted
# [ephemeral-agent] 2026/03/15 22:02:54 connection #1 ended: EOF

In normal (GUI) mode, logs are written to %TEMP%\ephemeral-agent.log.

Security

Property Built-in ssh-agent Ephemeral Agent
Key storage Registry (DPAPI) Process memory
Persistence Survives reboot Until process exits
Extraction requires Any same-user process SeDebugPrivilege (admin)

Threat model

Keys in memory can be extracted by a process with SeDebugPrivilege (typically requires admin). This is the same security boundary as SSH agent forwarding, GPG agent, and similar tools.

The key advantage over the built-in agent is that keys are not persisted to a location readable by any unprivileged same-user process.

Loading Keys from Bitwarden

If you store SSH keys in Bitwarden, a helper script is included at scripts/load-ssh-keys.ps1. It:

  1. Prompts for your master password
  2. Unlocks the vault, syncs, and finds all SSH Key items (Bitwarden type 5) and PEM keys stored in notes
  3. Pipes each private key to ssh-add
  4. Immediately locks the vault
# Requires: bw CLI installed and logged in (bw login)
.\scripts\load-ssh-keys.ps1

This is entirely optional — Ephemeral Agent works with any key source. The Bitwarden script is just a convenience for users who keep their keys in a password manager.

License

MIT

About

Lightweight memory-only SSH agent for Windows

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors