OpenSSH: SSH ホストベース認証(HostbasedAuthentication) を実際に触ってみる


0. はじめに
======================

今更なのですが、SSHのホストベース認証の動作を理解する必要がでたので触ってみました。

- 今更感ありますが、インフラエンジニアでもネットワークエンジニアでもないので、やっぱり触る機会あまりないです。これを言い訳に記事としてみます
- 公開のモチベーションとして、このドキュメントどおりコピペすれば、誰でもはまらずに体験することができるというのをめざしました

0.1 やりたいこと
--------------------

もともとのモチベーションとして、System AはWebサービスを構成するあるシステムであり、そこからインターネット経由で別のシステムBと連携することを目指しました。ちなみにSystem B は、REST-API をもたない伝統的なシステムです。

要件としては、

- System B の各ユーザになって、アプリケーションをキックする必要がある
- 運用時、System B のroot権限はない
- System A は one-user にしたい

![Kobito.UpCclJ.png](https://qiita-image-store.s3.amazonaws.com/0/73207/58eada3a-8311-8ba2-6af4-53e5f80a4dc0.png "Kobito.UpCclJ.png")


0.2 参考にしたページ
--------------------

下記(1)は本当に分かりやすかった。ありがとうございます！！
感謝の意味を込めて、本文の一番下ではなく、ここでご紹介したく・・・・

1. [入門OpenSSH: 6.6. Hostbased 認証 を使う](http://www.unixuser.org/~euske/doc/openssh/book/chap6.html#hostbased-authentication)
2. [sshでHostbasedAuthenticationを有効にする場合の落とし穴](http://blogger.tempus.org/2011/05/sshhostbasedauthentication.html)

0.3 テスト環境
--------------------

linux環境を2台用意するために、AWS上から以下の ubuntu-16.04 を2台使いました。これでマシン調達を楽にできます。

- AMI: ubuntu/images/hvm-ssd/ubuntu-xenial-16.04-amd64-server-20170414 (ami-afb09dc8)


1. 設定概要 (Overview)
===========================

概要を §1 に示します。詳細は、§2から示します。


1.1 Server Side
------------------

**/etc/ssh/sshd_config**: DNS設定ではまらないよう今回はIPアドレスに限定 (`UseDNS no`)。rootのログインを認めるとまた設定が変わるので注意

```bash:設定例
HostbasedAuthentication yes
IgnoreRhosts yes
IgnoreUserKnownHosts yes
UseDNS no
```

**/etc/ssh/shosts.equiv**:  `<'クライアントの許可するIPアドレス'> <'クライアント側の許可するユーザ名'>` の順に登録する

```bash:設定例
10.100.0.87 ubuntu
```

**/etc/ssh/ssh_known_hosts**: Client側の `ssh_host_rsa_key.pub` をサーバに登録する

```bash:設定例
10.100.0.87 ssh-rsa AAAAB3NzaC1yc2EA7yzqGd ~~~省略~~~ YJgMfV3wKbL
```

1.2 Client Side
------------------

**/etc/ssh/ssh_config**:  下記２つの項目は必ず設定が必要

```bash:設定例
HostbasedAuthentication yes
EnableSSHKeysign yes
```


-----------------------


2. ServerSide の設定 (detail)
==========================================

2.1 事前準備
---------------

```bash:IPアドレス
echo "export IP_CLIENT='10.100.0.87'" >> ~/.bashrc
echo "export IP_SERVER='10.100.0.20'" >> ~/.bashrc
source ~/.bashrc
```

```bash:確認
cat << ETX

IP_CLIENT: ${IP_CLIENT}
IP_SERVER: ${IP_SERVER}

ETX
```

2.2 /etc/ssh/sshd_config の設定
---------------------------------------------

```bash:sshd_configの編集
sudo vi /etc/ssh/sshd_config
```

```bash:設定内容
HostbasedAuthentication yes
IgnoreRhosts yes
IgnoreUserKnownHosts yes
UseDNS no
```

```bash:設定例
# Package generated configuration file
# See the sshd_config(5) manpage for details

# What ports, IPs and protocols we listen for
Port 22
# Use these options to restrict which interfaces/protocols sshd will bind to
#ListenAddress ::
#ListenAddress 0.0.0.0
Protocol 2
# HostKeys for protocol version 2
HostKey /etc/ssh/ssh_host_rsa_key
HostKey /etc/ssh/ssh_host_dsa_key
HostKey /etc/ssh/ssh_host_ecdsa_key
HostKey /etc/ssh/ssh_host_ed25519_key
#Privilege Separation is turned on for security
UsePrivilegeSeparation yes

# Lifetime and size of ephemeral version 1 server key
KeyRegenerationInterval 3600
ServerKeyBits 1024

# Logging
SyslogFacility AUTH
LogLevel INFO

# Authentication:
LoginGraceTime 120
PermitRootLogin prohibit-password
StrictModes yes

RSAAuthentication yes
PubkeyAuthentication yes
#AuthorizedKeysFile	%h/.ssh/authorized_keys

# Don't read the user's ~/.rhosts and ~/.shosts files
IgnoreRhosts yes
#IgnoreRhosts no
# For this to work you will also need host keys in /etc/ssh_known_hosts
RhostsRSAAuthentication no
# similar for protocol version 2
#HostbasedAuthentication no
HostbasedAuthentication yes
# Uncomment if you don't trust ~/.ssh/known_hosts for RhostsRSAAuthentication
#IgnoreUserKnownHosts yes
IgnoreUserKnownHosts yes

# To enable empty passwords, change to yes (NOT RECOMMENDED)
PermitEmptyPasswords no

# Change to yes to enable challenge-response passwords (beware issues with
# some PAM modules and threads)
ChallengeResponseAuthentication no

# Change to no to disable tunnelled clear text passwords
PasswordAuthentication no

# Kerberos options
#KerberosAuthentication no
#KerberosGetAFSToken no
#KerberosOrLocalPasswd yes
#KerberosTicketCleanup yes

# GSSAPI options
#GSSAPIAuthentication no
#GSSAPICleanupCredentials yes

X11Forwarding yes
X11DisplayOffset 10
PrintMotd no
PrintLastLog yes
TCPKeepAlive yes
#UseLogin no

#MaxStartups 10:30:60
#Banner /etc/issue.net

# Allow client to pass locale environment variables
AcceptEnv LANG LC_*

Subsystem sftp /usr/lib/openssh/sftp-server

# Set this to 'yes' to enable PAM authentication, account processing,
# and session processing. If this is enabled, PAM authentication will
# be allowed through the ChallengeResponseAuthentication and
# PasswordAuthentication.  Depending on your PAM configuration,
# PAM authentication via ChallengeResponseAuthentication may bypass
# the setting of "PermitRootLogin without-password".
# If you just want the PAM account and session checks to run without
# PAM authentication, then enable this but set PasswordAuthentication
# and ChallengeResponseAuthentication to 'no'.
UsePAM yes

# if no, you can only use IP address.
UseDNS no
```

```bash:設定確認
cat /etc/ssh/sshd_config | grep -vE ^# | grep "HostbasedAuthentication"
cat /etc/ssh/sshd_config | grep -vE ^# | grep "IgnoreRhosts"
cat /etc/ssh/sshd_config | grep -vE ^# | grep "IgnoreUserKnownHosts"
cat /etc/ssh/sshd_config | grep -vE ^# | grep "UseDNS"
```

2.3 /etc/ssh/ssh_known_hostsの設定
------------------------------------------------------------


```bash:クライアントの公開鍵を取得
PUBLIC_KEY=$(ssh-keyscan -t rsa ${IP_CLIENT}) && echo ${PUBLIC_KEY}
```

```bash:結果例
# 10.100.0.87:22 SSH-2.0-OpenSSH_7.2p2 Ubuntu-4ubuntu2.1
10.100.0.87 ssh-rsa AAAAB3NzaC1yc2EA7yzqGd ~~~省略~~~ YJgMfV3wKbL
```

```bash:ssh_known_hostsの作成
sudo sh -c "echo ${PUBLIC_KEY} >> /etc/ssh/ssh_known_hosts" && cat /etc/ssh/ssh_known_hosts
```

2.4 /etc/ssh/shosts.equiv の設定
-------------------------------------------

```bash:現状の確認
cat /etc/ssh/shosts.equiv
```

```bash:クライアントの追加
sudo sh -c "echo \"${IP_CLIENT} ubuntu\" > /etc/ssh/shosts.equiv" && cat /etc/ssh/shosts.equiv
```


2.5 sshd再起動
---------------------------------

```bash:sshd再起動
sudo /etc/init.d/ssh restart
```

```bash:結果例
[ ok ] Restarting ssh (via systemctl): ssh.service.
```

3. ClientSide の設定 (detail)
=============================

3.1 事前設定
------------------

```bash:IPアドレス
echo "export IP_CLIENT='10.100.0.87'" >> ~/.bashrc
echo "export IP_SERVER='10.100.0.20'" >> ~/.bashrc
source ~/.bashrc
```

```bash:確認
cat << ETX

IP_CLIENT: ${IP_CLIENT}
IP_SERVER: ${IP_SERVER}

ETX
```

3.2 /etc/ssh/ssh_configの編集
---------------------------------------------

```bash:編集
sudo vi /etc/ssh/ssh_config
```

```bash:設定内容
HostbasedAuthentication yes
EnableSSHKeysign yes
```

```bash:設定例
# This is the ssh client system-wide configuration file.  See
# ssh_config(5) for more information.  This file provides defaults for
# users, and the values can be changed in per-user configuration files
# or on the command line.

# Configuration data is parsed as follows:
#  1. command line options
#  2. user-specific file
#  3. system-wide file
# Any configuration value is only changed the first time it is set.
# Thus, host-specific definitions should be at the beginning of the
# configuration file, and defaults at the end.

# Site-wide defaults for some commonly used options.  For a comprehensive
# list of available options, their meanings and defaults, please see the
# ssh_config(5) man page.

Host *
#   ForwardAgent no
#   ForwardX11 no
#   ForwardX11Trusted yes
#   RhostsRSAAuthentication no
#   RSAAuthentication yes
#   PasswordAuthentication yes
#   HostbasedAuthentication no
    HostbasedAuthentication yes
    EnableSSHKeysign yes
#   GSSAPIAuthentication no
#   GSSAPIDelegateCredentials no
#   GSSAPIKeyExchange no
#   GSSAPITrustDNS no
#   BatchMode no
#   CheckHostIP yes
#   AddressFamily any
#   ConnectTimeout 0
#   StrictHostKeyChecking ask
#   IdentityFile ~/.ssh/identity
#   IdentityFile ~/.ssh/id_rsa
#   IdentityFile ~/.ssh/id_dsa
#   IdentityFile ~/.ssh/id_ecdsa
#   IdentityFile ~/.ssh/id_ed25519
#   Port 22
#   Protocol 2
#   Cipher 3des
#   Ciphers aes128-ctr,aes192-ctr,aes256-ctr,arcfour256,arcfour128,aes128-cbc,3des-cbc
#   MACs hmac-md5,hmac-sha1,umac-64@openssh.com,hmac-ripemd160
#   EscapeChar ~
#   Tunnel no
#   TunnelDevice any:any
#   PermitLocalCommand no
#   VisualHostKey no
#   ProxyCommand ssh -q -W %h:%p gateway.example.com
#   RekeyLimit 1G 1h
    SendEnv LANG LC_*
    HashKnownHosts yes
    GSSAPIAuthentication yes
    GSSAPIDelegateCredentials no
    PreferredAuthentications hostbased,publickey,keyboard-interactive,password
```

```bash:設定確認
cat /etc/ssh/ssh_config | grep -vE ^# | grep "HostbasedAuthentication"
cat /etc/ssh/ssh_config | grep -vE ^# | grep "EnableSSHKeysign"
```


4. 動作テスト
=================

4.1 テストユーザ作成 (サーバー)
------------------------------------------------

```bash:ユーザ作成
sudo adduser tanaka
sudo adduser suzuki
```

4.2 ログイン確認 (クライアント)
------------------------------------------------

テストはうまくいくのですが、`get_socket_address: getnameinfo 8 failed: Name or service not known` のエラーがでます。

この原因の追求まではいたらず・・・だれが知っている方教えて・・・

```bash:現ユーザ確認
whoami
```

```bash:結果
ubuntu
```

### from ubuntu@CLIENT to (指定なし)@SERVER

```bash:ユーザ指定なし
ubuntu@ip-10-100-0-87:~$ ssh ${IP_SERVER}
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
Welcome to Ubuntu 16.04.2 LTS (GNU/Linux 4.4.0-1013-aws x86_64)

 * Documentation:  https://help.ubuntu.com
 * Management:     https://landscape.canonical.com
 * Support:        https://ubuntu.com/advantage

  Get cloud support with Ubuntu Advantage Cloud Guest:
    http://www.ubuntu.com/business/services/cloud

0 packages can be updated.
0 updates are security updates.


Last login: Sun Jun 18 06:21:59 2017 from 106.184.21.20
ubuntu@ip-10-100-0-20:~$ whoami
ubuntu
```

### from ubuntu@CLIENT to tanaka@SERVER

```bash:tanakaを指定
ubuntu@ip-10-100-0-87:~$ ssh tanaka@${IP_SERVER}
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
Welcome to Ubuntu 16.04.2 LTS (GNU/Linux 4.4.0-1013-aws x86_64)

 * Documentation:  https://help.ubuntu.com
 * Management:     https://landscape.canonical.com
 * Support:        https://ubuntu.com/advantage

  Get cloud support with Ubuntu Advantage Cloud Guest:
    http://www.ubuntu.com/business/services/cloud

0 packages can be updated.
0 updates are security updates.



The programs included with the Ubuntu system are free software;
the exact distribution terms for each program are described in the
individual files in /usr/share/doc/*/copyright.

Ubuntu comes with ABSOLUTELY NO WARRANTY, to the extent permitted by
applicable law.

tanaka@ip-10-100-0-20:~$ whoami
tanaka
```

### from ubuntu@CLIENT to suzuki@SERVER

```bash:suzukiを指定
ubuntu@ip-10-100-0-87:~$ ssh suzuki@${IP_SERVER}
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
get_socket_address: getnameinfo 8 failed: Name or service not known
Welcome to Ubuntu 16.04.2 LTS (GNU/Linux 4.4.0-1013-aws x86_64)

 * Documentation:  https://help.ubuntu.com
 * Management:     https://landscape.canonical.com
 * Support:        https://ubuntu.com/advantage

  Get cloud support with Ubuntu Advantage Cloud Guest:
    http://www.ubuntu.com/business/services/cloud

0 packages can be updated.
0 updates are security updates.



The programs included with the Ubuntu system are free software;
the exact distribution terms for each program are described in the
individual files in /usr/share/doc/*/copyright.

Ubuntu comes with ABSOLUTELY NO WARRANTY, to the extent permitted by
applicable law.

suzuki@ip-10-100-0-20:~$ whoami
suzuki
suzuki
```

<!--

memo
========

Default

```bash:default
$ ls -l /usr/libexec/openssh/ssh-keysign
---x--s--x 1 root ssh_keys 452704 Mar 22 00:08 ssh-keysign
```

```bash:所有権をrootへ
$ sudo chown root /usr/libexec/openssh/ssh-keysign
$ ls -l /usr/libexec/openssh/ssh-keysign
---x--x--x 1 root ssh_keys 452704 Mar 22 00:08 ssh-keysign
```

```bash:setuid
$ sudo chmod u+s /usr/libexec/openssh/ssh-keysign
$ ls -l /usr/libexec/openssh/ssh-keysign
---s--x--x 1 root ssh_keys 452704 Mar 22 00:08 ssh-keysign
```

-->