何が起きているか
ssh user@192.168.1.50 や curl http://10.0.0.5:8080 を実行すると、以下のエラーが発生します:
connect: No route to host
このエラーは、よく似た2つのエラーとは異なります。Connection refused はサービスが起動しているものの、接続を能動的に拒否していることを意味します。Connection timed out はどこかでパケットが静かに破棄されていることを意味します。「No route to host」はそれらとは異なり、ネットワークスタックが早い段階で処理を中止しています。これは、宛先へのパスが存在しないか、途中の何かがICMP「host unreachable」メッセージを返してきたことが原因です。
主な原因は4つあります:ファイアウォールのREJECTルール、ルーティングテーブルのエントリが欠落または誤っている、接続先ホストが完全にダウンしている、またはネットワークインターフェースの設定ミスです。
デバッグ手順
ステップ1 — ホストに到達できるか確認する
他の操作をする前に、IPレベルから確認しましょう:
# ICMPピング
ping -c 4 192.168.1.50
# pingがブロックされている場合、既知のオープンポートでTCPを試す
nc -zv 192.168.1.50 22
nc -zv 192.168.1.50 80
pingは成功するがTCPが失敗する場合、問題はポート固有のものです — ステップ3に進んでください。両方失敗する場合、ホストはIPレベルで到達不能です — 読み進めてください。
ステップ2 — ルーティングテーブルを確認する
ip route get 192.168.1.50
正常な出力はこのようになります:
192.168.1.50 via 192.168.1.1 dev eth0 src 192.168.1.100 uid 1000
代わりに RTNETLINK answers: Network is unreachable と表示される場合、そのサブネットへのルートがマシンに存在しません。テーブル全体を表示してみましょう:
ip route show
# または
netstat -rn
デフォルトゲートウェイのエントリ(0.0.0.0/0 または default)を探してください。存在しない場合は追加します:
# 一時的なデフォルトゲートウェイ
ip route add default via 192.168.1.1 dev eth0
# または宛先サブネットへの特定ルートのみ追加
ip route add 10.0.0.0/24 via 192.168.1.1 dev eth0
ステップ3 — 両方のマシンのファイアウォールルールを確認する
十中八九、これが原因です。接続先サーバーで以下を実行します:
# iptables
sudo iptables -L -n -v
# nftables(新しいディストリビューション)
sudo nft list ruleset
# firewalld(CentOS/RHEL)
sudo firewall-cmd --list-all
REJECTルール(DROPではなく)があると、クライアント側で即座に No route to host が発生します。iptablesの出力で次のような行が確認できます:
REJECT tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:22 reject-with icmp-host-prohibited
ポートを開放するには:
# iptables: SSHを許可
sudo iptables -A INPUT -p tcp --dport 22 -j ACCEPT
# firewalld: 永続的に開放
sudo firewall-cmd --permanent --add-port=22/tcp
sudo firewall-cmd --reload
# UFW(Ubuntu)
sudo ufw allow 22/tcp
ステップ4 — インターフェースが起動しているか確認する
ip link show
ip addr show
state DOWN と表示されているインターフェースは、起動させる必要があります:
sudo ip link set eth0 up
割り当てられたIPアドレスとサブネットマスクも再確認してください。プレフィックスの誤り — たとえば /24 のところが /25 になっている場合 — 到達可能な範囲が静かに半分に削られ、ローカルサブネットの半分が到達不能に見えてしまいます。
ステップ5 — tracerouteでどこで切れているか特定する
traceroute 192.168.1.50
# または古いシステムでは
tracert 192.168.1.50
ホップが応答を止める箇所を確認してください。そこが問題の原因です — ルートの断絶か、トラフィックを遮断しているファイアウォールのどちらかです。
よくある解決策
解決策1 — リモートファイアウォールにREJECTルールがある
firewalld を実行しているCentOS/RHELシステム(RHEL 7以降のデフォルト)では、明示的に開放するまですべてのポートがブロックされています。これがデフォルトゾーンのポリシーです:
# 必要なポートを開放する
sudo firewall-cmd --permanent --add-port=8080/tcp
sudo firewall-cmd --reload
# 開放されていることを確認
sudo firewall-cmd --list-ports
解決策2 — 再起動後にデフォルトゲートウェイが消えた
最小インストールや再設定されたばかりのサーバーでは、再起動時にデフォルトルートが失われることがあります。一時的な ip route add コマンドは再起動後に残りません — 永続化するには以下を実行します:
# Ubuntu/Debian — netplanを編集
sudo nano /etc/netplan/00-installer-config.yaml
# インターフェースの下に追加:
# routes:
# - to: default
# via: 192.168.1.1
sudo netplan apply
# CentOS/RHEL — ifcfgファイルを編集
sudo nano /etc/sysconfig/network-scripts/ifcfg-eth0
# 追加: GATEWAY=192.168.1.1
sudo systemctl restart NetworkManager
解決策3 — サブネットマスクの誤り(CIDRの不一致)
192.168.1.100/25 として設定されたインターフェースは、192.168.1.1〜126 の範囲のホストにしか到達できません。.128 以降は、同じ物理スイッチ上にあるにもかかわらず到達不能に見えます。実際のプレフィックスを確認してください:
ip addr show eth0
# inet 192.168.1.100/25 → 使用可能なホスト: 192.168.1.1 から 192.168.1.126
自分のCIDRがカバーすべき範囲がわからない場合は、IPアドレスとプレフィックスをToolCraftのサブネット計算ツールに入力してみてください — 正確なホスト範囲、ブロードキャストアドレス、ネットワークアドレスがすぐに表示されます。アカウント登録は不要です。
解決策4 — SELinuxが接続をブロックしている
RHEL/CentOSにはもう一つの層があります。SELinuxは明確なエラーを表示せずに静かに干渉することがあります。まず監査ログを確認してください:
sudo ausearch -m avc -ts recent
sudo sealert -a /var/log/audit/audit.log
SELinuxが接続をブロックしている場合は、ラベルまたはポリシーを修正してください。SELinux全体を無効にしたくなるかもしれませんが、それは誤った対処法です — システム全体の保護が失われてしまいます。
修正の確認
# TCP接続が機能することを確認
nc -zv 192.168.1.50 22
# 期待される結果: Connection to 192.168.1.50 22 port [tcp/ssh] succeeded!
# その後、元のコマンドを再試行
ssh user@192.168.1.50
curl -v http://192.168.1.50:8080/health
nc は成功するがアプリが失敗する場合、良いニュースです:ネットワークは問題ありません。問題はアプリケーション層に移りました — 誤った認証情報、TLSの不一致、またはホスト名の誤りが原因です。これははるかに範囲の絞られた問題です。
まとめ
- 「No route to host」はほぼ常に、ファイアウォールのREJECTルールかルートの欠落を意味します — ホストがダウンしているわけではありません(それはタイムアウトとして現れます)。
- 両端を確認してください:ローカルのルーティングテーブルとリモートサーバーのファイアウォールルールの両方です。
- CentOS/RHELでは、RHEL 7以降
firewalldがデフォルトですべてをブロックします。新しいポートはfirewall-cmd --permanentで明示的に開放する必要があります。 - 再起動やネットワーク再設定の後は、
ip route showを実行してデフォルトゲートウェイが残っているか確認してください。 - TCPポートの素早い確認には
nc -zv host portを使いましょう — アプリケーションのデバッグより速く、ネットワークを原因から排除できます。

