web-dev-qa-db-ja.com

nftablesの「iifname」と「iif」の違いは何ですか?

https://wiki.nftables.org/wiki-nftables/index.php/Quick_reference-nftables_in_10_minutes#Meta

iifname(名前以外は文字列)とiifの間に違いはありますか、そして何が推奨されますか?

6
mvorisek

iifは受信したパケットのインターフェースインデックスを検索して比較しますが、iifnameはインターフェース名と文字列を比較します。どちらにも長所と短所があります。

つまり、インターフェイスインデックスは パケットに既に格納されている単純な番号 がネットワークスタックとnftableをトラバースするため、iifが使用するリソースは少なくて済み、すぐに比較に使用できます。しかし、その欠点は、インターフェイスが削除された場合(そしておそらく再作成されたが、新しいインデックス値で)、nftablesの対応するルールが一致しなくなることです。常に保証される唯一のインターフェースインデックスはループバックインターフェースです(デフォルトではloという名前です)。これは常に名前空間で最初に作成され、削除することはできません(2回目に追加することもできません)。したがって、そのインデックス値は常に1

一方、iifnameは、iptablesの--in-interfaceと同様に、現在のインターフェイスの名前と文字列を比較します。これはより多くのリソースを使用しますが、存在しないインターフェースに対して、iifが簡単に実行できない決定的な名前でルールを事前に作成できます。 iifnameは、iifname "ppp*"のようにワイルドカードマッチングを実行することもできます。これは、iifが実行できず、インターフェースが頻繁に作成および削除される場合に便利ですが、命名規則を維持します(PPPリンクのpppで始まるような) )。

例(nftables 0.9.2を使用):

$ unshare -r -n
# ip link
1: lo: <LOOPBACK> mtu 65536 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
# nft add table ip filter
# nft add chain ip filter input '{ type filter hook input priority 0; policy accept; }'
# nft add rule ip filter input iif lo counter
# nft add rule ip filter input iif dummy0 counter
Error: Interface does not exist
add rule ip filter input iif dummy0 counter
                             ^^^^^^
# nft add rule ip filter input iifname dummy0 counter
# ip link add name dummy0 type dummy
# ip link
1: lo: <LOOPBACK> mtu 65536 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
2: dummy0: <BROADCAST,NOARP> mtu 1500 qdisc noop state DOWN mode DEFAULT group default qlen 1000
    link/ether 4a:09:68:3a:34:91 brd ff:ff:ff:ff:ff:ff
# nft add rule ip filter input iif dummy0 counter
# nft list ruleset
table ip filter {
    chain input {
        type filter hook input priority filter; policy accept;
        iif "lo" counter packets 0 bytes 0
        iifname "dummy0" counter packets 0 bytes 0
        iif "dummy0" counter packets 0 bytes 0
    }
}
# ip link delete dev dummy0
# nft list ruleset
table ip filter {
    chain input {
        type filter hook input priority filter; policy accept;
        iif "lo" counter packets 0 bytes 0
        iifname "dummy0" counter packets 0 bytes 0
        iif 2 counter packets 0 bytes 0
    }
}

インターフェイスがなくなったため、代わりにそのインデックス値が表示されます。同様に、ルールを追加するときに、事前であってもインデックス値を使用できます。

# nft add rule ip filter input iif 3 counter
# nft list ruleset
table ip filter {
    chain input {
        type filter hook input priority filter; policy accept;
        iif "lo" counter packets 0 bytes 0
        iifname "dummy0" counter packets 0 bytes 0
        iif 2 counter packets 0 bytes 0
        iif 3 counter packets 0 bytes 0
    }
}
# ip link add name dummy4 type dummy
# ip link add name dummy0 type dummy
# nft list ruleset
table ip filter {
    chain input {
        type filter hook input priority filter; policy accept;
        iif "lo" counter packets 0 bytes 0
        iifname "dummy0" counter packets 0 bytes 0
        iif 2 counter packets 0 bytes 0
        iif "dummy4" counter packets 0 bytes 0
    }
}

インターフェースインデックス値は名前空間内でリサイクルされずに増加するだけなので、インデックス2に関するルールは「失われ」ます(これ以上一致する機会はありません)。次に作成されたインターフェースdummy4にはインデックス3が割り当てられ、ルールセットのdummy4に解決されます。 dummy0はインデックス値4を受け取りました。これは、iifルールで参照されていませんが、iifnameルールと一致します。


何がお勧めですか?

私のアドバイス:

ルールが適用される前に、起動時に使用可能な物理イーサネットインターフェイスのように、作成後に変更されない「安定した」インターフェイスにはiifを使用する必要があります(新しい物理インターフェイスの安定した命名規則を使用している場合、列挙順序が変更されても変更されません) )、そしてもちろんloインターフェース。例には示されていませんが、iif { lo, dummy4 }のように、iifを使用してインターフェイスのリストを一致させることもできます。したがって、複数のインターフェースに一致する単一のiifステートメントを引き続き使用できます。

iifnameは、起動時(およびルールの作成時)にはわからないが後で表示されることが予想される、またはワイルドカード一致を使用するときにインターフェースのグループを命名規則と一致させるために使用する必要があります。

あまり知られていないが、最適化するには、ワイルドカードを使用する代わりに、新しく作成された各インターフェースにグループを割り当て(たとえば、ip link set dev interface group 99を使用)、インターフェースグループをiifgroup +ワイルドカードではなくiifnameと一致させることができます。ただし、これには、新しく作成されたインターフェースをグループ化するための追加のメカニズムが必要です。

インターフェース 名前付きセット を使用して、iifiifnameを使用する一般的なルールを維持し、ルール自体ではなく名前付きセットの内容を変更することもできます。以前のwikiリンクは、セットでのインターフェースの使用については通知していませんが、単に最新ではないことに注意してください。この詳細については、この質問に対するUL SEの回答で説明します。 nftables(インターフェイス名用)に名前付きの文字列セットを作成するにはどうすればよいですか?

6
A.B