====== NetworkManager(nmcli)でGREトンネルを作成する ====== {{tag>gre network-manager centos7 rhel8-clone}} ===== GREトンネルとは ===== GREとはGeneric Routing Encapsulationの略で簡単な設定で作成できるIPトンネル。 トンネル始端でIPヘッダの前にトンネル用のIPヘッダとGREヘッダを付加してトンネル終端へ転送。 トンネル終端では始端が付加したIPヘッダとGREヘッダを除去してからパケットを処理する。 外側のIPヘッダに設定するGREのプロトコル番号は47。 {{:articles:gre_header.png?nolink|GREパケット}} 通常は、トンネルの両端で送信用の設定をすると、その相手先からのGREパケットを受け付けるようになる。 言い換えると、片方向だけトンネルを設定して送信しても受信側はパケットを破棄する。 他のVPNとは異なり本格的な認証や暗号化等のセキュリティ機能はない。 両端で共有するkeyが設定されているかどうかをチェックするオプションがある程度。 LinuxではL2のブリッジに接続してEoIPで転送する''gretap''、''ip6gretap''もある。[[https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/8/html/configuring_and_managing_networking/configuring-a-gretap-tunnel-to-transfer-ethernet-frames-over-ipv4_configuring-ip-tunnels|RHEL8 ネットワークの設定および管理]] ===== GREトンネルをNetworkManagerで作成するには ===== typeが''ip-tunnel''でmodeが''gre''または''ip6gre''のコネクションを作成すると、GREのトンネルデバイスを作成できる。 そのコネクションにipv4やipv6の設定を加えるとパケットの転送(ルーティング)が出来るようになる。 参照: ''nm-settings(5)'' ''ip-tunnel(8)'' CentOS 7では、''ipv6.method disabled''を''ipv6.method ignore''にすること。 firewalldを実行している場合は、GREプロトコルの受信を許可する。 # firewall-cmd --add-service gre # firewall-cmd --runtime-to-permanent 他のサーバから受信したパケットを別のサーバに転送(フォワーディング)するならカーネルパラメータを変更する。 # cat < /etc/sysctl.d/ip_forward.conf net.ipv4.ip_forward = 1 EOF # sysctl --system ===== 構成1: GREトンネル作成時のパラメータによる違い ===== {{:articles:gre_nm_1.png?nolink|GREトンネル構成1}} サーバAとサーバBをつなぐ単純であまり実用的でない、トンネル作成時のパラメータによる違いを説明するための構成。 色々なパラメータとその組み合わせで作成できるが、 対向が''remote''に設定したアドレスで送信しないと受け取ってもらえないため、 ネットワーク的に自明であっても''remote''と''local''を設定するのが無難。 ここでは割愛するが''local''と''dev''を両方とも設定することも可能。 ==== 構成1 設定例1 トンネルのremoteだけでlocalもdevも設定しない場合 ==== === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 \ ipv4.method manual ip4 192.168.0.0/31 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 \ ipv4.method manual ip4 192.168.0.1/31 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local any ttl inherit # ip link show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 0.0.0.0 peer 172.31.0.102 # ip addr show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 0.0.0.0 peer 172.31.0.102 inet 192.168.0.0/31 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 100 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 100 192.168.0.0/31 dev tun2b proto kernel scope link src 192.168.0.0 metric 675 ==== 構成1 設定例2 トンネルのremoteとdevを設定する場合 ==== === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 dev eth0 \ ipv4.method manual ip4 192.168.0.0/31 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 dev eth0 \ ipv4.method manual ip4 192.168.0.1/31 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local any dev eth0 ttl inherit # ip link show dev tun2b 8: tun2b@eth0: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 0.0.0.0 peer 172.31.0.102 # ip addr show dev tun2b 8: tun2b@eth0: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 0.0.0.0 peer 172.31.0.102 inet 192.168.0.0/31 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 100 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 100 192.168.0.0/31 dev tun2b proto kernel scope link src 192.168.0.0 metric 675 ==== 構成1 設定例3 トンネルのremoteとlocalを設定する場合 ==== === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 local 172.31.0.101 \ ipv4.method manual ip4 192.168.0.0/31 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 local 172.31.0.102 \ ipv4.method manual ip4 192.168.0.1/31 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local 172.31.0.101 ttl inherit # ip link show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 # ip addr show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 inet 192.168.0.0/31 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 100 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 100 192.168.0.0/31 dev tun2b proto kernel scope link src 192.168.0.0 metric 675 ==== 構成1 設定例4 事前共有キーを設定する場合 ==== ''input-key''と''output-key''に設定可能な値は、数値またはIPアドレスのように"."で区切った4つの数値。 ''input-key''と''output-key''に同じ値を設定できる。 その場合、トンネルデバイスのパラメータは''ikey''と''okey''の二つではなく''key''一つになる。 当然ながら''output-key''と対向の''input-key''が一致しない場合、パケットは破棄される。 === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 \ ip-tunnel.input-key 1234 ip-tunnel.output-key 5678 \ ipv4.method manual ip4 192.168.0.0/31 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 \ ip-tunnel.input-key 5678 ip-tunnel.output-key 1234 \ ipv4.method manual ip4 192.168.0.1/31 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local any ttl inherit ikey 1234 okey 5678 # ip link show dev tun2b 8: tun2b@NONE: mtu 1472 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 0.0.0.0 peer 172.31.0.102 # ip addr show dev tun2b 8: tun2b@NONE: mtu 1472 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 0.0.0.0 peer 172.31.0.102 inet 192.168.0.0/31 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 100 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 100 192.168.0.0/31 dev tun2b proto kernel scope link src 192.168.0.0 metric 675 ===== 構成2 IPv4 over IPv4 ===== {{:articles:gre_nm_2.png?nolink|GREトンネル構成2}} WAN側の172.31.0.101と172.31.0.102を終端としてGREトンネルを作成。 LAN側の192.168.10.0/24と192.168.20.0/24が疎通するようにする。 === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 local 172.31.0.101 \ ipv4.method manual ip4 192.168.0.0/31 ipv4.routes 192.168.20.0/24 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 local 172.31.0.102 \ ipv4.method manual ip4 192.168.0.1/31 ipv4.routes 192.168.10.0/24 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local 172.31.0.101 ttl inherit # ip link show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 # ip addr show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 inet 192.168.0.0/31 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 103 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 103 192.168.0.0/31 dev tun2b proto kernel scope link src 192.168.0.0 metric 675 192.168.20.0/24 dev tun2b proto static scope link metric 675 ===== 構成3 IPv6 over IPv4 ===== {{:articles:gre_nm_3.png?nolink|GREトンネル構成3}} WAN側の172.31.0.101と172.31.0.102を終端としてGREトンネルを作成。 LAN側の2001:db8:10::/64と2001:db8:20::/64が疎通するようにする。 === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 local 172.31.0.101 \ ipv4.method disabled ipv6.method manual ip6 2001:db8:aa::1/64 ipv6.routes 2001:db8:20::/64 === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 local 172.31.0.102 \ ipv4.method disabled ipv6.method manual ip6 2001:db8:aa::2/64 ipv6.routes 2001:db8:10::/64 === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local 172.31.0.101 ttl inherit # ip link show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 # ip addr show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 inet6 2001:db8:aa::1/64 scope global noprefixroute valid_lft forever preferred_lft forever inet6 fe80::d781:253b:3686:8174/64 scope link noprefixroute valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 103 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 103 # ip -6 route ::1 dev lo proto kernel metric 256 pref medium 2001:db8:10::/64 dev eth1 proto kernel metric 104 pref medium 2001:db8:20::/64 dev tun2b proto static metric 675 pref medium 2001:db8:aa::/64 dev tun2b proto kernel metric 675 pref medium fe80::/64 dev eth1 proto kernel metric 1024 pref medium fe80::/64 dev tun2b proto kernel metric 1024 pref medium ===== 構成4 IPv4 over IPv6 ===== {{:articles:gre_nm_4.png?nolink|GREトンネル構成4}} WAN側の2001:db8::101と2001:db8::102を終端としてGREトンネルを作成。 LAN側IPの192.168.10.0/24と192.168.20.0/24が疎通するようにする。 === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode ip6gre remote 2001:db8::102 local 2001:db8::101 \ ipv4.method manual ip4 192.168.0.0/31 ipv4.routes 192.168.20.0/24 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode ip6gre remote 2001:db8::101 local 2001:db8::102 \ ipv4.method manual ip4 192.168.0.1/31 ipv4.routes 192.168.10.0/24 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc # ip -6 tun ip6tnl0: ipv6/ipv6 remote :: local :: encaplimit 0 hoplimit inherit tclass 0x00 flowlabel 0x00000 (flowinfo 0x00000000) ip6gre0: gre/ipv6 remote :: local :: encaplimit 0 hoplimit inherit tclass 0x00 flowlabel 0x00000 (flowinfo 0x00000000) tun2b: gre/ipv6 remote 2001:db8::102 local 2001:db8::101 encaplimit 0 hoplimit inherit tclass 0x00 flowlabel 0x00000 (flowinfo 0x00000000) # ip link show dev tun2b 12: tun2b@NONE: mtu 1448 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre6 2001:db8::101 peer 2001:db8::102 permaddr 26ad:541e:f5ea:: # ip addr show dev tun2b 12: tun2b@NONE: mtu 1448 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre6 2001:db8::101 peer 2001:db8::102 permaddr 26ad:541e:f5ea:: inet 192.168.0.0/31 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip route 192.168.0.0/31 dev tun2b proto kernel scope link src 192.168.0.0 metric 675 192.168.10.0/24 dev eth1 proto kernel scope link src 192.168.10.1 metric 104 192.168.20.0/24 dev tun2b proto static scope link metric 675 # ip -6 route ::1 dev lo proto kernel metric 256 pref medium 2001:db8::/64 dev eth0 proto kernel metric 105 pref medium fe80::/64 dev eth0 proto kernel metric 1024 pref medium === 注意点1 === ''local''を設定しないと、journalctlに''manager: (tun2b) couldn't create the device: Failed to create IPv6 tunnel interface 'tun2b' for 'tun2b': File exists''と出力してトンネルデバイスの作成に失敗する。 === 注意点2 === Rocky Linux 8.7では疎通しない。 conntrackのstateがinvalidになっているようでfirewalldが''STATE_INVALID_DROP''で破棄してしまう。 %%--add-rich-rule%%や%%--add-protocol%%で許可設定をしてもルールに''ct state { new, untracked }''が追加されてしまうので解決しない。 firewalldを停止すると疎通するが脆弱になる。 ip6tablesやnftでfilterテーブルのINPUTチェーンにルールを追加してもfirewalld.direct(5)のCAVEATSで説明されているように、 netfilterの仕様によりfirewalldのチェーンとINPUTチェーンの両方に通らないと破棄されてしまうので意味が無い。 firewalld.direct(5)にあるように、firewalldのバックエンドをnftablesからiptablesに変更してdirectルールを追加すると、 firewalldによる保護を受けつつip6greのパケットが疎通するようになる。 # grep ^FirewallBackend /etc/firewalld/firewalld.conf FirewallBackend=iptables # systemctl restart firewalld # firewall-cmd --direct --add-rule ipv6 filter INPUT 0 -p gre -j ACCEPT ==== 構成5 3拠点メッシュ構成 ==== {{:articles:gre_nm_5.png?nolink|GREトンネル構成5}} 拠点3つをGREトンネルのメッシュでつなぐ。LAN側ネットワークは相互に通信可能。 === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 local 172.31.0.101 \ ipv4.method manual ip4 192.168.0.0/31 ipv4.routes 192.168.20.0/24 ipv6.method disabled # nmcli con add con-name tun2c ifname tun2c type ip-tunnel mode gre remote 172.31.0.103 local 172.31.0.101 \ ipv4.method manual ip4 192.168.0.2/31 ipv4.routes 192.168.30.0/24 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 local 172.31.0.102 \ ipv4.method manual ip4 192.168.0.1/31 ipv4.routes 192.168.10.0/24 ipv6.method disabled # nmcli con add con-name tun2c ifname tun2c type ip-tunnel mode gre remote 172.31.0.103 local 172.31.0.102 \ ipv4.method manual ip4 192.168.0.4/31 ipv4.routes 192.168.30.0/24 ipv6.method disabled === サーバC === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 local 172.31.0.103 \ ipv4.method manual ip4 192.168.0.3/31 ipv4.routes 192.168.10.0/24 ipv6.method disabled # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 local 172.31.0.103 \ ipv4.method manual ip4 192.168.0.5/31 ipv4.routes 192.168.20.0/24 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local 172.31.0.101 ttl inherit tun2c: gre/ip remote 172.31.0.103 local 172.31.0.101 ttl inherit # ip link show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 # ip link show dev tun2c 9: tun2c@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.103 # ip addr show dev tun2b 8: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 inet 192.168.0.0/31 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip addr show dev tun2c 9: tun2c@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.103 inet 192.168.0.2/31 scope global noprefixroute tun2c valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 100 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 100 192.168.0.0/31 dev tun2b proto kernel scope link src 192.168.0.0 metric 675 192.168.0.2/31 dev tun2c proto kernel scope link src 192.168.0.2 metric 676 192.168.20.0/24 dev tun2b proto static scope link metric 675 192.168.30.0/24 dev tun2c proto static scope link metric 676 ==== 構成6 3拠点メッシュ構成 IPアドレス共有版 ==== {{:articles:gre_nm_6.png?nolink|GREトンネル構成6}} 拠点3つをGREトンネルのメッシュでつなぐ。LAN側ネットワークは相互に通信可能。 トンネルデバイスに設定するIPアドレスは、複数のトンネルデバイスで同じIPアドレスを使用できる。 また、物理ネットワークインタフェースのIPアドレスも使用できる。 この構成ではトンネルデバイスにeth1のIPアドレスを設定している。 === サーバA === # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 local 172.31.0.101 \ ipv4.method manual ip4 192.168.10.1 ipv4.routes 192.168.20.0/24 ipv6.method disabled # nmcli con add con-name tun2c ifname tun2c type ip-tunnel mode gre remote 172.31.0.103 local 172.31.0.101 \ ipv4.method manual ip4 192.168.10.1 ipv4.routes 192.168.30.0/24 ipv6.method disabled === サーバB === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 local 172.31.0.102 \ ipv4.method manual ip4 192.168.20.1 ipv4.routes 192.168.10.0/24 ipv6.method disabled # nmcli con add con-name tun2c ifname tun2c type ip-tunnel mode gre remote 172.31.0.103 local 172.31.0.102 \ ipv4.method manual ip4 192.168.20.1 ipv4.routes 192.168.30.0/24 ipv6.method disabled === サーバC === # nmcli con add con-name tun2a ifname tun2a type ip-tunnel mode gre remote 172.31.0.101 local 172.31.0.103 \ ipv4.method manual ip4 192.168.30.1 ipv4.routes 192.168.10.0/24 ipv6.method disabled # nmcli con add con-name tun2b ifname tun2b type ip-tunnel mode gre remote 172.31.0.102 local 172.31.0.103 \ ipv4.method manual ip4 192.168.30.1 ipv4.routes 192.168.20.0/24 ipv6.method disabled === サーバAの状態(Rocky Linux 8.7の場合) === # ip tun gre0: gre/ip remote any local any ttl inherit nopmtudisc tun2b: gre/ip remote 172.31.0.102 local 172.31.0.101 ttl inherit tun2c: gre/ip remote 172.31.0.103 local 172.31.0.101 ttl inherit # ip link show dev tun2b 10: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 # ip link show dev tun2c 11: tun2c@NONE: mtu 1476 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.103 # ip addr show dev tun2b 10: tun2b@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.102 inet 192.168.10.1/32 scope global noprefixroute tun2b valid_lft forever preferred_lft forever # ip addr show dev tun2c 11: tun2c@NONE: mtu 1476 qdisc noqueue state UNKNOWN group default qlen 1000 link/gre 172.31.0.101 peer 172.31.0.103 inet 192.168.10.1/32 scope global noprefixroute tun2c valid_lft forever preferred_lft forever # ip route default via 172.31.0.1 dev eth0 proto static metric 100 172.31.0.0/24 dev eth0 proto kernel scope link src 172.31.0.101 metric 100 192.168.20.0/24 dev tun2b proto static scope link metric 675 192.168.30.0/24 dev tun2c proto static scope link metric 676