SSH Unprotected Private Key File Warning and How to Fix It
Fix the SSH unprotected private key file warning: set mode 600, fix ownership, handle WSL and Windows mounts, and see why open keys are refused.

The warning is a wall of capitals again: WARNING: UNPROTECTED PRIVATE KEY FILE! followed by Permissions 0644 for '/home/alice/.ssh/id_ed25519' are too open. It is not a bug. A private key readable by other users is no longer private, and OpenSSH refuses to use it. The fix is one command, with some exceptions for virtual machines and mounted drives. It comes up often after copying keys between machines, and relates to the checks in locking down file permissions.
What you see
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@ WARNING: UNPROTECTED PRIVATE KEY FILE! @
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
Permissions 0644 for '/home/alice/.ssh/id_ed25519' are too open.
It is required that your private key files are NOT accessible by others.
This private key will be ignored.
Load key "/home/alice/.ssh/id_ed25519": bad permissions
[email protected]: Permission denied (publickey).
The client ignores the key and moves on, so you also get the generic permission-denied line at the end. The cure is on the client, the machine holding the private key, not the server. The numbers are the mode in octal: 0644 means owner read-write, group and others read.
Fix the permissions
chmod 700 ~/.ssh
chmod 600 ~/.ssh/id_ed25519
chmod 644 ~/.ssh/id_ed25519.pub
ls -l ~/.sshdrwx------ 2 alice alice 4096 Nov 3 09:00 .
-rw------- 1 alice alice 411 Nov 3 09:00 id_ed25519
-rw-r--r-- 1 alice alice 100 Nov 3 09:00 id_ed25519.pub
Mode 600 means only the owner can read and write; 400 also works. The public key may be world-readable, since it is public. Make sure you own the file: a key copied with sudo belongs to root, and ssh run as your user cannot read it; sudo chown alice:alice ~/.ssh/id_ed25519 repairs that. The permission bits are explained in Linux file permissions.
WSL, Windows drives and shared folders
cp /mnt/c/Users/alice/.ssh/id_ed25519 ~/.ssh/
chmod 600 ~/.ssh/id_ed25519
mount | grep -E 'drvfs|9p' | head -2Drives mounted from Windows into WSL, or folders shared with a virtual machine, often show every file as 777 and ignore chmod. The key looks "too open" however many times you change it. Copy it into the Linux file system (your WSL home) and set permissions there. Alternatively, enable the metadata mount option for WSL drives in /etc/wsl.conf. The same applies to Docker bind mounts from some host systems.
Containers and CI
install -m 600 /dev/null ~/.ssh/ci_key
printf '%s\n' "$DEPLOY_KEY" > ~/.ssh/ci_key
ssh-keygen -y -f ~/.ssh/ci_key >/dev/null && echo "key parses"Create the file with a restrictive mode before writing the secret into it, so it is never briefly readable. The final command checks that the key text is intact: a key pasted with lost newlines fails with "invalid format" instead. Keys passed through environment variables often need a trailing newline. See SSH keys and a password manager for keeping keys out of files entirely.
What not to do
Do not run chmod 777, ignore the warning with -o StrictModes=no (a server setting that does not apply here) or patch the client. The check protects against another local user copying your key. Also set a passphrase on keys that live on laptops, so a stolen disk does not expose them: ssh-keygen -p -f ~/.ssh/id_ed25519. See the ssh manual section on files and generating SSH keys.
Why the check exists
The SSH client refuses a key file that other users can read because the file is the credential. Anyone who can copy the bytes of an unprotected private key can authenticate as its owner, from anywhere, without a passphrase if the key has none. On a shared machine, a world-readable key is therefore an open door, and the client treats it as a configuration error instead of letting the user carry on unaware. The refusal is deliberate and early, which is what makes it a good failure: it happens before any network traffic, and it names the file.
The same logic applies to the directory. If ~/.ssh is writable by others, they could replace the authorized_keys file or the config, so servers and clients both examine ownership and mode up the path. A home directory that is group-writable can trigger a refusal on the server side for a different reason: the daemon rejects the authorised keys because the path is too open. Keep the home directory at 755 or tighter, the .ssh directory at 700 and key files at 600.
Fixing it without making things worse
Before changing modes, find out why they are wrong. A key that arrives at 644 after a copy is a one-time fix. A key that returns to 644 every time you log in indicates a process that rewrites it, such as a sync client, a backup restore or a mount with fixed permissions. Look for the source of the files with stat and the mount type, because chmod on a file system that does not store modes does nothing visible. Move the key to a file system that does, and point the configuration to the new path with an IdentityFile line.
Ownership needs attention too. A file owned by root with mode 600 is unreadable by your user, and the client reports a different message, "permission denied", about opening the key. Check ls -ln to see numeric owners, which also exposes the case where a restored backup carries user IDs that map to someone else on this machine.
Handling keys in automation
Pipelines inject keys as secrets, and the file must be created correctly each time. Write the key to a path under a private directory with umask 077, load it into an agent with ssh-add reading from standard input where possible, and remove the file at the end of the job. A key left on a persistent runner is a standing risk for the next job. Prefer short-lived credentials such as certificates signed by an SSH certificate authority, which expire on their own and leave nothing to clean up.
When a key is shared by several jobs, record which jobs use it, and restrict it on the server with options in authorized_keys: a forced command, a source address and disabled forwarding. A deploy key limited to one command and one address is a much smaller loss if it leaks than a general-purpose login key.
Windows and mixed environments
Windows does not store Unix modes, so the native OpenSSH client checks access control lists instead. The warning appears when the list includes groups such as Users or Everyone. Remove inheritance on the key file and grant read access to your account alone with icacls. In Git Bash and WSL the rules follow whichever file system the key lives on, which is why the same key behaves differently in the two shells. Choose one place for keys, preferably the Linux home in WSL, and refer to it from every tool that needs it.
Where this does not apply
If the key has correct permissions and the login still fails, the problem is elsewhere: see permission denied (publickey). Windows' built-in OpenSSH client checks ACLs rather than modes, and reports the same warning when the key file's access list includes other users; fix it with icacls.
For a deeper look at what each permission bit allows, the chmod manual page documents the modes used above.


