SSHの認証プロセスでは、アクセスユーザーの認証の前に接続ホストを認証しています。 初回アクセス時にフィンガープリント文字列が表示され、適切であれば受け入れて接続します。
このプロセスは目視確認で、フィンガープリントを知っている前提です。sshdの公開鍵由来の文字列で、セキュリティ上まじめに確認する意味はあります。
2回目以降のアクセスでは~/.ssh/known_hostsに接続済ホストの鍵がリストされており、接続時に一致しないとエラーになります。
よって接続ホストの構成を変更した場合など、known_hostsを変更すべき場合があります。
基本的には、既存のエントリを削除のうえ、新しい鍵を登録します。または、IPの変化のようなアドレスが変わるケースについては、HostKeyAliasでIPアドレスに依存しない設定も可能です。
公開鍵検証をスキップしてホスト確認しない接続設定もよく知られてはいますが、中間者攻撃などを発見できなくなるため避けるべきでしょう。
known_hostsエントリの削除
古いエントリを削除するには、ssh-keygen -Rコマンドを用います。
known_hostsにホスト名が記載されているケースでは手動編集しても問題ありませんが、ハッシュ化されている場合、どの行が該当のホストなのか区別するためにコマンド実行が必要です。
$ ssh-keygen -R host.example.com
# ポート指定する場合
$ ssh-keygen -R [host.example.com]:1000
# ファイル指定する場合
$ ssh-keygen -R host.example.com -f /path/to/known_hosts
上の例のとおり、単純なホスト名のみのケース(22番ポートにアクセス)ではとくに問題ありませんが、ポート指定する場合の書式が独特であるため、注意が必要です。
known_hostsエントリの追加
known_hostsに記載できるホスト鍵を取得するには、ssh-keyscanを用います。
なお、攻撃などによりssh-keyscan実行時点で接続先がすり替えられていると防衛の意味がないため、接続ホストが適切であることの保証が必要です。
$ ssh-keyscan host.example.com
# ポート指定する場合
$ ssh-keyscan -p 1000 host.example.com
# ハッシュ化する場合
$ ssh-keyscan -H host.example.com
# リダイレクトで追記
$ ssh-keyscan host.example.com >> /path/to/known_hosts
単純な構成の場合は疑問の余地は少ないのですが、ポート指定はssh-keygenと異なります。
また、known_hostsがハッシュ化されているケースでは-Hオプションが必要です。
IPアクセス構成のIP変化を吸収
sshではDNS解決するホスト名だけでなく、固定IPホストにも接続できます。 この場合、のちにIPが変わるとknown_hostsもキーが変わってしまいホスト認証時が通過しません。
HostKeyAliasで名前をつけると、known_hostsはIPに依存しなくなります。
次のようなssh_configでsshアクセスすると、フィンガープリントを再確認して名前ベースのエントリが追加されます。
Host <ssh-host>
HostName <ip-address>
HostKeyAlias <ssh-host>
ssh-keyscanはssh_configをサポートしておらず、出力するエントリのキーがIPになるため、一度ダンプしてIPを名前に書き換え→ハッシュ化、という手順になります。
HostとHostKeyAliasは別物ですが、実用上は揃えた方が管理しやすいでしょう。
なお、CheckHostIP yesを指定していると、known_hostsをIP解決してしまうのでエラーになります。デフォルトはnoのようです。