firewalldコマンドでLinuxのファイアウォールを設定する方法|ポート開放やゾーン設定も


図解60p「Linuxサーバー構築入門マニュアル」無料
登録10秒/自動返信でDL/合わなければ解除3秒
HOMELinux技術 リナックスマスター.JP(Linuxマスター.JP)Linuxコマンド, LinuxコマンドF-J, セキュリティ管理コマンド, ネットワーク管理コマンド > firewalldコマンドでLinuxのファイアウォールを設定する方法|ポート開放やゾーン設定も
「firewalldでポートを開放したはずなのに、外からアクセスできない」  「iptablesとfirewalldの違いがよく分からず、どちらを使えばいいのか迷っている」  Linuxサーバーを運用する以上、ファイアウォールの設定は避けて通れません。ネットで断片的な情報をコピペしただけでは、なぜその設定が必要なのかが分からず、トラブル時に手も足も出なくなります。

この記事では、RHEL/CentOS/AlmaLinux/Rocky Linuxで標準採用されている firewalld の実践的な使い方を解説します。
基本的なポート開放やサービスの許可から、ゾーンの仕組み、リッチルールを使った細かいアクセス制御、そしてよくあるトラブルの対処法まで、現場で必要な知識を網羅しました。

※firewalldの操作には root 権限(または sudo)が必要です。以降のコマンド例は全て root 権限で実行するものとします。

なぜファイアウォール設定が必要なのか

サーバーをインターネットに公開すると、SSHへの不正ログイン試行、ポートスキャンなど、外部からの攻撃は日常的に発生します。ファイアウォールは「必要な通信だけを許可し、それ以外は全て遮断する」ための仕組みです。

たとえばWebサーバーであれば、HTTP(80番ポート)とHTTPS(443番ポート)だけを開放し、それ以外のポートへのアクセスは拒否するのが基本です。この「必要最小限だけ開ける」という考え方を最小権限の原則と呼び、サーバーセキュリティの基本中の基本です。

firewalldの基本(ゾーンとサービス)

firewalldには2つの重要な概念があります。

ゾーン(zone)とは

ゾーンは「ネットワークインターフェースに適用するセキュリティレベルのテンプレート」です。firewalldにはあらかじめ複数のゾーンが用意されています。

public:デフォルトゾーン。外部ネットワーク向け。SSHとDHCPv6クライアントのみ許可
trusted:全ての通信を許可する(社内LANなど信頼できるネットワーク向け)
drop:全ての受信パケットを破棄する(応答も返さない)
dmz:DMZ(非武装地帯)向け。限定的なサービスのみ許可
internal:内部ネットワーク向け。publicよりやや緩い設定
work:職場ネットワーク向け
home:家庭ネットワーク向け
external:外部ネットワーク向け。NATマスカレードが有効
block:全ての受信パケットを拒否する(ICMP拒否応答を返す)

実務で最もよく使うのは public ゾーンです。特に指定しなければ、このゾーンが適用されます。

サービス(service)とは

サービスは「ポート番号とプロトコルの組み合わせに名前を付けたもの」です。たとえば http というサービスは「TCP 80番ポート」、https は「TCP 443番ポート」を意味します。

ポート番号を直接指定するよりも、サービス名で管理した方が設定の見通しがよくなります。firewalldに定義済みのサービスは以下のコマンドで一覧表示できます。

# firewall-cmd --get-services

基本的な使い方

1. 現在の状態を確認する

まずはfirewalldが動作しているか、現在どのような設定になっているかを確認しましょう。

# firewalldの動作状態を確認する # firewall-cmd --state running

running と表示されれば正常に動作しています。

現在のゾーンに適用されている設定の全体像を確認するには、--list-all を使います。

# デフォルトゾーンの設定を一覧表示する # firewall-cmd --list-all public (active) target: default icmp-block-inversion: no interfaces: eth0 sources: services: cockpit dhcpv6-client ssh ports: protocols: forward: yes masquerade: no forward-ports: source-ports: icmp-blocks: rich rules:

この出力から、現在 public ゾーンが eth0 インターフェースに適用されていて、sshdhcpv6-clientcockpit のサービスが許可されていることが分かります。

2. ポートを開放する

特定のポート番号を直接指定して開放する方法です。たとえば、TCP 8080番ポートを開放するには以下のように実行します。

# TCP 8080番ポートを開放する(即時反映・一時的) # firewall-cmd --add-port=8080/tcp success

開放されたポートを確認するには --list-ports を使います。

# 開放中のポートを確認する # firewall-cmd --list-ports 8080/tcp

ポートを閉じるには --remove-port を使います。

# TCP 8080番ポートを閉じる # firewall-cmd --remove-port=8080/tcp success

重要:上記の設定は「ランタイム(一時的)」な変更です。firewalldを再起動したり、サーバーを再起動すると設定が消えます。永続化する方法はこの後のセクションで解説します。

3. サービスを許可する

ポート番号を直接指定する代わりに、サービス名で許可する方法です。Webサーバーを公開する場合は以下のように設定します。

# HTTPサービス(TCP 80番ポート)を許可する # firewall-cmd --add-service=http success # HTTPSサービス(TCP 443番ポート)を許可する # firewall-cmd --add-service=https success

現在許可されているサービスの一覧を確認するには --list-services を使います。

# 許可済みサービスの一覧を表示する # firewall-cmd --list-services cockpit dhcpv6-client http https ssh

サービスを削除するには --remove-service を使います。

# HTTPサービスの許可を取り消す # firewall-cmd --remove-service=http success

4. 設定を永続化する(--permanent)

firewalldの設定には「ランタイム(実行中のみ有効)」と「永続(再起動後も有効)」の2種類があります。

永続的な設定を行うには、コマンドに --permanent オプションを付けます。

# HTTPサービスを永続的に許可する # firewall-cmd --permanent --add-service=http success

ここが落とし穴です。--permanent を付けた設定は、永続設定ファイルに書き込まれるだけで、実行中のfirewalldにはすぐに反映されません。反映するには --reload が必要です。

# 永続設定をランタイムに反映する # firewall-cmd --reload success

現場でおすすめの手順は以下の通りです。

手順1:まず --permanent なしで設定を追加し、即座に動作確認する
手順2:動作に問題がなければ --permanent 付きで同じコマンドを実行する
手順3:--reload で永続設定を反映する

この手順なら、設定ミスがあっても firewalld を reload すれば永続設定(=変更前の状態)に戻せます。

5. ゾーンを確認・変更する

デフォルトゾーンを確認するには --get-default-zone を使います。

# デフォルトゾーンを確認する # firewall-cmd --get-default-zone public

デフォルトゾーンを変更するには --set-default-zone を使います。

# デフォルトゾーンを internal に変更する # firewall-cmd --set-default-zone=internal success

特定のインターフェースに対してゾーンを指定するには --zone オプションを使います。

# eth1 インターフェースを trusted ゾーンに割り当てる # firewall-cmd --zone=trusted --change-interface=eth1 success

全てのゾーンの設定を一覧で確認するには以下のコマンドが便利です。

# 全ゾーンの設定を表示する # firewall-cmd --list-all-zones

応用・実務Tips

リッチルールで細かいアクセス制御

リッチルール(rich rule)は、単純なサービス許可やポート開放では対応できない、より詳細な条件を指定するための仕組みです。

たとえば「特定のIPアドレスからのSSH接続だけを許可する」といった設定が可能です。

# 192.168.1.100 からのSSH接続のみ許可する # firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="192.168.1.100" service name="ssh" accept' success

逆に、特定のIPアドレスからの全通信を拒否することもできます。

# 10.0.0.50 からの全通信を拒否する # firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="10.0.0.50" drop' success

設定済みのリッチルールを確認するには --list-rich-rules を使います。

# リッチルールの一覧を表示する # firewall-cmd --list-rich-rules

リッチルールを削除する場合は --remove-rich-rule で、追加時と同じルール文字列を指定します。

# リッチルールを削除する # firewall-cmd --permanent --remove-rich-rule='rule family="ipv4" source address="192.168.1.100" service name="ssh" accept' success

特定のIPアドレスだけ許可する

「社内ネットワークからのみ管理画面にアクセスさせたい」という要件は実務で頻繁に出てきます。リッチルールを使って、特定のネットワークからだけポートを開放する方法を紹介します。

# 192.168.1.0/24 のネットワークからのみ TCP 3306(MySQL)を許可する # firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="192.168.1.0/24" port port="3306" protocol="tcp" accept' success # 設定を反映する # firewall-cmd --reload success

このように設定すれば、データベースポートを全世界に開放することなく、社内ネットワークだけに限定できます。

iptablesとfirewalldの違い

RHEL 6以前は iptables でファイアウォールを直接管理していました。RHEL 7以降では firewalld が標準となっています。

iptables:ルールを順番に記述する。変更時はルール全体を再読み込みする必要があり、ルールの追加・削除時に一瞬だけ全通信が遮断されるリスクがあった
firewalld:ゾーンという概念でルールを管理する。ランタイムと永続設定を分離でき、--reload 時もアクティブな接続を切断しない

firewalldは内部的にnftables(RHEL 8以降)またはiptablesをバックエンドとして使っています。つまり、firewalldは「iptables/nftablesを人間にとって扱いやすくするフロントエンド」という位置づけです。

現在のRHEL系ディストリビューションを使っているなら、firewalldを使ってください。iptablesを直接操作する必要はほとんどありません。

トラブルシュート・エラー対処

「FirewallD is not running」が出た時の対処法

firewall-cmd を実行した際に以下のエラーが出ることがあります。

# firewall-cmd --state not running

このエラーはfirewalldサービスが停止している状態です。以下の手順で起動してください。

# firewalldを起動する # systemctl start firewalld # 動作確認 # firewall-cmd --state running # サーバー再起動時にも自動起動するようにする # systemctl enable firewalld

もし systemctl start firewalld でエラーが出る場合は、iptablesサービスと競合している可能性があります。

# iptablesサービスが動いていないか確認する # systemctl status iptables # 動いている場合は停止して無効化する # systemctl stop iptables # systemctl disable iptables # その後、firewalldを起動する # systemctl start firewalld

ポートを開放したのにアクセスできない時の確認手順

「firewall-cmdでポートを開けたのに、外部からアクセスできない」というトラブルは非常に多いです。以下の手順で原因を切り分けてください。

1. firewalldの設定を再確認する

まずは本当にポートが開放されているか確認します。

# 現在の設定を確認する # firewall-cmd --list-all

--permanent で追加した後に --reload を忘れていないか、ゾーンが正しいかを確認してください。

2. サービスがポートをリッスンしているか確認する

ファイアウォールでポートを開放しても、そのポートで待ち受けるサービスが起動していなければアクセスできません。

# 指定ポートでサービスが待ち受けているか確認する # ss -tlnp | grep 8080

何も表示されなければ、対象のサービスが起動していないか、別のポートでリッスンしています。

3. SELinuxが通信をブロックしていないか確認する

RHEL系ではSELinux(Security-Enhanced Linux)が有効になっていることが多く、firewalldとは別にアクセスをブロックする場合があります。

# SELinuxの状態を確認する # getenforce Enforcing # SELinux の拒否ログを確認する # ausearch -m AVC --start recent

SELinuxが原因の場合は、semanage port コマンドでポートにラベルを付与する必要があります。

# SELinuxで HTTP用ポートとして 8080 を許可する # semanage port -a -t http_port_t -p tcp 8080

semanage がインストールされていない場合は dnf install policycoreutils-python-utils でインストールしてください。

4. クラウド環境のセキュリティグループを確認する

AWS・Azure・GCPなどのクラウド環境では、OS上のfirewalldとは別にクラウド側のセキュリティグループ(またはネットワークセキュリティグループ)でも通信を制御しています。firewalldで開放してもクラウド側で許可していなければアクセスできません。

本記事のまとめ

やりたいこと コマンド
firewalldの状態を確認する firewall-cmd --state
現在の設定を一覧表示する firewall-cmd --list-all
ポートを開放する(一時的) firewall-cmd --add-port=ポート番号/tcp
ポートを開放する(永続的) firewall-cmd --permanent --add-port=ポート番号/tcp
サービスを許可する firewall-cmd --add-service=サービス名
サービスを許可する(永続的) firewall-cmd --permanent --add-service=サービス名
永続設定を反映する firewall-cmd --reload
デフォルトゾーンを確認する firewall-cmd --get-default-zone
デフォルトゾーンを変更する firewall-cmd --set-default-zone=ゾーン名
リッチルールでIP制限する firewall-cmd --permanent --add-rich-rule='rule family="ipv4" source address="IPアドレス" service name="サービス名" accept'
firewalldを起動する systemctl start firewalld
firewalldを自動起動に設定する systemctl enable firewalld

ファイアウォール設定、自信を持ってできますか?

firewalldの設定は、Linuxサーバーを安全に運用するための第一歩です。しかし、セキュリティはファイアウォールだけでは完結しません。
ネットの切れ端の情報をコピペするだけでなく、現場で通用する安全なLinuxサーバー構築の「型」を体系的に身につけたい方へ、『Linuxサーバー構築入門マニュアル(図解60P)』を完全無料でプレゼントしています。

「独学の時間がもったいない」「プロから直接、現場の技術を最短で学びたい」という本気の方には、2日で実務レベルのスキルが身につく【初心者向けハンズオンセミナー】も開催しています。



無料プレゼント
図解60p「Linuxサーバー構築入門マニュアル」
独学で詰まる前に、“型(手順書)”で最初の環境構築をサクッと終わらせましょう。
登録10秒/自動返信でDL/合わなければ解除3秒
無料で受け取る ※メールアドレスだけでもOK(必須項目は最小限)

宮崎 智広

この記事を書いた人

宮崎 智広(みやざき ともひろ)

株式会社イーネットマーキュリー代表。現役のLinuxサーバー管理者として15年以上の実務経験を持ち、これまでに累計3,100名以上のエンジニアを指導してきたLinux教育のプロフェッショナル。「現場で本当に使える技術」を体系的に伝えることをモットーに、実践型のLinuxセミナーの開催や無料マニュアルの配布を通じてLinux人材の育成に取り組んでいる。

図解60pのLinux無料マニュアル
登録10秒/自動返信でDL
無料で受け取る