轉自:https://marskid.net/2018/02/05/how-to-verify-ssh-public-key-fingerprint/
使用SSH進行遠程連接新的主機的時候,經常會看到一個提示:
$ ssh 127.0.0.1
The authenticity of host '127.0.0.1 (127.0.0.1)' can't be established. ECDSA key fingerprint is SHA256:QUfCwW6Br5EwwESsulN2TEidBoDNca888RNflZG++bI. Are you sure you want to continue connecting (yes/no)? yes
如果輸入yes
確認,那么服務器SSH公鑰會添加到~/.ssh/known_hosts
里面。雖然知道這是一個驗證步驟,但是應該怎樣驗證?其中原理又是什么?
$ cat ~/.ssh/known_hosts
|1|DdBYclZ+pUHyoiLC2zjmf5Efb4Y=|fdd5RRy2SV0775av/4ktZr30aI8= ecdsa-sha2-nistp256 AAAAE2VjZHN.........K+/urI+pGmsSDz6O5PY=
第一次連接SSH有提示ECDSA類型的公鑰指紋,因為指紋比公鑰的長度要短,所以更容易比較。
SHA256:QUfCwW6Br5EwwESsulN2TEidBoDNca888RNflZG++bI
這個指紋也可以通過ssh-keyscan
命令結合ssh-keygen
得到。ssh-keyscan
命令可獲取服務器公鑰,而 ssh-keygen
命令可以計算公鑰的指紋。只要計算一下服務器上的相應公鑰的指紋,並與客戶端獲取的指紋進行比對一致,就能確定連接的是公鑰對應的服務器。
先在客戶端獲取服務器公鑰:
$ ssh-keyscan -t ECDSA -p 22 127.0.0.1
# 127.0.0.1:22 SSH-2.0-OpenSSH_7.2p2 Ubuntu-4ubuntu2.4
127.0.0.1 ecdsa-sha2-nistp256 AAAAE2VjZHN.........K+/urI+pGmsSDz6O5PY=
可以看到這個公鑰與寫入known_hosts
文件是一致的。
那么這個公鑰從哪里來,怎么確認與服務器的連接是正確的?
可以通過ssh-keygen
命令獲取公鑰的指紋,可通過-E參數指定指紋的類型。
$ ssh-keygen -E sha256 -lf ~/.ssh/known_hosts
256 SHA256:QUfCwW6Br5EwwESsulN2TEidBoDNca888RNflZG++bI |1|DdBYclZ+pUHyoiLC2zjmf5Efb4Y=|fdd5RRy2SV0775av/4ktZr30aI8= (ECDSA)
有的SSH終端默認提供MD5格式的公鑰指紋。
$ ssh-keygen -E md5 -lf ~/.ssh/known_hosts
256 MD5:e6:f0:2b:fa:23:fb:fe:0d:1d:de:2c:71:70:ea:fe:f9 |1|DdBYclZ+pUHyoiLC2zjmf5Efb4Y=|fdd5RRy2SV0775av/4ktZr30aI8= (ECDSA)
這樣就方便與服務器的指紋進行比較,雖然直接比較公鑰是否相同也可以。
進入服務器,可看到/etc/ssh/
目錄下有幾種密鑰,這些文件在安裝openssh-server后生成。SSH服務就是使用這些密鑰與客戶端進行加密通信。
$ ls -1 /etc/ssh/ssh_host*
/etc/ssh/ssh_host_dsa_key
/etc/ssh/ssh_host_dsa_key.pub
/etc/ssh/ssh_host_ecdsa_key
/etc/ssh/ssh_host_ecdsa_key.pub
/etc/ssh/ssh_host_ed25519_key
/etc/ssh/ssh_host_ed25519_key.pub
/etc/ssh/ssh_host_rsa_key
/etc/ssh/ssh_host_rsa_key.pub
根據終端的提示,選擇ECDSA進行比較。可在服務器通過下面的命令生成服務器的公鑰指紋摘要,這是可信的基礎。
$ ssh-keygen -E sha256 -lf /etc/ssh/ssh_host_ecdsa_key.pub
256 SHA256:QUfCwW6Br5EwwESsulN2TEidBoDNca888RNflZG++bI root@localhost (ECDSA)
這是MD5格式。
$ ssh-keygen -E md5 -lf /etc/ssh/ssh_host_ecdsa_key.pub
256 MD5:e6:f0:2b:fa:23:fb:fe:0d:1d:de:2c:71:70:ea:fe:f9 root@localhost (ECDSA)
可以在客戶端使用如下命令通過網絡獲取服務器的公鑰指紋摘要。
$ ssh-keyscan -t ECDSA -p 22 127.0.0.1 2>/dev/null | ssh-keygen -E sha256 -lf -
256 SHA256:QUfCwW6Br5EwwESsulN2TEidBoDNca888RNflZG++bI 127.0.0.1 (ECDSA)
這是MD5格式。
$ ssh-keyscan -t ECDSA -p 22 127.0.0.1 2>/dev/null | ssh-keygen -E md5 -lf -
256 MD5:e6:f0:2b:fa:23:fb:fe:0d:1d:de:2c:71:70:ea:fe:f9 127.0.0.1 (ECDSA)
可以看到,在服務器上直接生成的
256 SHA256:QUfCwW6Br5EwwESsulN2TEidBoDNca888RNflZG++bI root@localhost (ECDSA)
與客戶端獲取的
256 SHA256:QUfCwW6Br5EwwESsulN2TEidBoDNca888RNflZG++bI 127.0.0.1 (ECDSA)
公鑰指紋是一致的,並且~/.ssh/known_hosts
文件中的對應主機的公鑰也與服務器相應類型的公鑰一致。可以據此判斷SSH建立的連接是正確的。