🔐 Hardened GitHub Setup with YubiKey on Windows 11
This guide walks through a secure setup of GitHub access using a YubiKey on Windows 11, including:
SSH
authentication with your YubiKeyGPG
commit signing with full hardware isolationTouch
requirement on every cryptographic operation
🔧 Prerequisites
- Windows 11 (no admin rights required)
- Git for Windows
- Gpg4win (Kleopatra, GPG Agent)
- A touch-enabled YubiKey (OpenPGP-capable)
- GitHub account
- PowerShell
1️⃣ Install Gpg4win (if not already)
- Download from: https://gpg4win.org/
- Install with:
Kleopatra
GnuPG
GPG Agent
Smartcard Support
No admin rights are required if using the per-user installer.
2️⃣ Connect YubiKey and Check Status
Check YubiKey status and confirm OpenPGP is detected
gpg --card-status
3️⃣ Generate Keys Directly on the YubiKey
Launch interactive card tool
gpg --edit-card
Then enter:
Before generating the keys, change the default User / Admin PIN
Command: admin
> passwd
Default User PIN: 123456
Default Admin PIN: 12345678
admin
key-attr
generate
Set 1
- RSA
to 4096
if supported by the yubi key.
- Respond to name/email prompts
- Say yes when asked to store the keys on the card
- This generates:
- A signing key
- An encryption key
- An authentication (SSH) key
4️⃣ Export Public SSH
Key
Get your
Authentication key ID
gpg --card-status
[ SNIP ]
Signature key ....:
created ....:
Encryption key....:
created ....:
Authentication key: YOU NEED THIS ONE HERE COMPLETE
created ....:
[ SNIP ]
5️⃣ Configure Git
for GPG
Signing
Get your
GPG Key ID
gpg --list-secret-keys --keyid-format LONG
[ SNIP ]
sec> rsa4096/YOU NEED THIS ONE
[ SNIP ]
Configure
Git
to useGPG
with yourYubiKey
git config --global user.name "YOUR USER NAME"
git config --global user.email "[email protected]"
git config --global user.signingkey YOURKEYID
git config --global commit.gpgsign true
git config --global gpg.program "C:\\Program Files (x86)\\GnuPG\\bin\\gpg.exe"
git config --global core.sshCommand "C:\\Windows\\System32\\OpenSSH\\ssh.exe"
The mail hast to be the same like in your GPG key
generation.
6️⃣ Export Public GPG
Key
Export public key in ASCII format for GitHub
gpg -o pubkey.asc --armor --export YOURKEYID
Upload contents of pubkey.asc
to:
GitHub
→ Settings
→ SSH and GPG Keys
→ New GPG Key
7️⃣ Extract SSH Public Key from YubiKey
Generate SSH public key from GPG Auth subkey
gpg --export-ssh-key Authentication key > id_rsa.pub
Remove all blank spaces
Copy the output (ssh-ed25519 ...
) to:
GitHub
→ Settings
→ SSH and GPG Keys
→ New SSH Key
8️⃣ Hardened gpg-agent.conf (🔒 Secure Session TTL)
Create or edit this file:
notepad "$env:APPDATA\gnupg\gpg-agent.conf"
Paste this secure config:
enable-ssh-support
enable-win32-openssh-support
use-standard-socket
# Cache timeout (seconds)
default-cache-ttl 60
max-cache-ttl 300
default-cache-ttl-ssh 60
max-cache-ttl-ssh 300
# Additional security
no-allow-loopback-pinentry
no-allow-mark-trusted
pinentry-timeout 30
Reload the agent:
gpg-connect-agent killagent /bye
gpg-connect-agent /bye
9️⃣ Enforce Touch for All GPG Keys (YubiKey Only)
Require physical touch for all GPG subkeys
ykman openpgp keys set-touch sig ON
ykman openpgp keys set-touch enc ON
ykman openpgp keys set-touch aut ON
This ensures no operation can happen without you physically tapping the YubiKey.
1️⃣1️⃣ Test GitHub SSH Access
You should see a success message from GitHub
ssh -T [email protected]
Expected output:
Hi yourusername! You've successfully authenticated, but GitHub does not provide shell access.
If you get an error use the following command to get verbose
output.
ssh -vT [email protected]
1️⃣2️⃣ Test GPG-Signed Commit
Try a signed commit to verify YubiKey integration
git clone [email protected]:your/repo.git
cd repo
echo Secure > secure.txt
git add secure.txt
git commit -S -m "Signed commit using YubiKey"
You will be prompted to touch the YubiKey.
🧼 Optional: Manual Agent Cleanup Command
To forcibly wipe out any GPG agent session:
Manual GPG session cleanup for maximum security
gpg-connect-agent killagent /bye
gpg-connect-agent /bye
You can alias this in your PowerShell profile:
Function End-GPGSession {
gpg-connect-agent killagent /bye
gpg-connect-agent /bye
Write-Host "GPG agent session cleared."
}
✅ Summary
Feature | Hardened? | Notes |
---|---|---|
GPG commit signing | ✅ Yes | Key stored only on YubiKey |
SSH via GPG Auth key | ✅ Yes | Hardware-backed with touch |
Agent socket management | ✅ Yes | Safe PowerShell logic only |
TTL-based session expiry | ✅ Yes | 1–5 minute cache window |
Touch requirement enforced | ✅ Yes | All subkeys require tap |
Admin rights needed | ❌ No | All actions run as user |