embedded-deck
TEKNİK REHBER LİNUX NETWORK / NFTABLES GÜVENLİK DUVARI 2026

nftables
Linux'un modern güvenlik duvarı.

iptables'ın halefi, birleşik netfilter ön yüzü — tek syntax ile IPv4/IPv6/ARP/bridge filtreleme, NAT, sets ve maps. IoT gateway'den edge sunucuya kadar tam rehber.

00 nftables nedir?

nftables, Linux kernel 3.13'te tanıtılan ve iptables, ip6tables, arptables ile ebtables'ın yerini alan modern netfilter ön yüzüdür. Tekil bir araç (nft) ile tüm protokol ailelerini yönetebilir, daha güçlü eşleştirme mekanizmaları ve JIT derlemeli kural işleme sunar.

iptables vs nftables

Özellikiptablesnftables
Kernel versiyonu2.4+3.13+
Araçiptables, ip6tables, arptables, ebtablesnft (tek araç)
IPv4/IPv6Ayrı tablolarTek tabloda inet ailesi
Kural değerlendirmeLinear taramaSets/maps ile O(1) lookup
Atomik güncellemeKısıtlıTransaction tabanlı — tüm set tek işlem
DurumLegacy (maintenance mode)Aktif geliştirme, önerilen

Mimari

  Kullanıcı alanı:   nft CLI
                          │
  Kernel alanı:     netlink socket
                          │
                    nf_tables subsystem
                          │
           ┌──────────────┼──────────────────┐
           │              │                  │
       ip table       ip6 table          inet table
      (IPv4 only)   (IPv6 only)       (IPv4 + IPv6)
           │
    ┌──────┼──────┐
    │      │      │
 input  forward output  (+ prerouting, postrouting)
    
GEÇİŞ NOTU

Debian 10+, Ubuntu 20.04+, Fedora 18+ ve RHEL 8+ sistemlerde nftables varsayılan güvenlik duvarı altyapısı haline geldi. iptables-nft wrapper'ı sayesinde eski iptables komutları nftables backend üzerinde çalışır. Yeni projeler için doğrudan nft syntax kullanın.

Bu bölümde

  • nftables = iptables + ip6tables + arptables + ebtables yerini alıyor
  • Tek nft CLI, tüm protokol aileleri, inet = IPv4+IPv6 ortak tablo
  • Sets/maps ile O(1) kural araması; atomik ruleset güncellemeleri

01 Temel kavramlar

nftables'ın veri modeli: table → chain → rule hiyerarşisi ve her katmanın rolü. Hook noktaları paketin kernel içindeki yolculuğunu belirler.

Nesne hiyerarşisi

TableEn üst düzey kapsayıcı. Protokol ailesi (ip, ip6, inet, arp, bridge) ve isme göre tanımlanır. Örn: table inet filter
ChainKuralların sıralı listesi. Base chain (hook'a bağlı) veya regular chain (goto/jump hedefi) olabilir. Priority ile değerlendirme sırası belirlenir.
RuleEşleştirme ifadeleri + eylem. Örn: ip saddr 192.168.1.1 drop
SetIP adresi, port veya başka değerler kümesi. Named set ile kural içinden referans alınır. Dinamik güncelleme destekli.
MapAnahtar-değer çifti. Lookup ile aksiyon seçimi veya değer dönüşümü — DNAT hedef mapping için ideal.

Netfilter hook noktaları

  Gelen paket
       │
  [prerouting]   ← DNAT burada yapılır
       │
  Routing kararı
       ├──── Yerel süreç için ──────► [input] ──► Uygulama
       │
       └──── Forward ────────────► [forward] ──► [postrouting] ──► Çıkış
                                                      ↑
                                              [output] (yerel çıkan)
    

Chain türleri ve priority

HookYönTipik priorityKullanım
preroutingGelen, routing öncesi-100 (raw), 0 (filter), 100 (mangle)DNAT, connection tracking
inputGelen, yerel0 (filter)Gelen bağlantı filtreleme
forwardTransit0 (filter)Router/gateway kural
outputÇıkan, yerel0 (filter)Çıkan trafik kısıtlama
postroutingÇıkan, routing sonrası100 (nat)SNAT, MASQUERADE

Bu bölümde

  • table → chain → rule hiyerarşisi; her katman bağımsız isimlendirme
  • Base chain hook'a bağlı; priority = değerlendirme sırası (küçük = önce)
  • Set ve map: O(1) lookup ile büyük IP/port listelerini verimli yönet

02 nft syntax

nft komutunun genel sözdizimi ve temel işlemler: table/chain/rule ekleme, silme, listeleme ve yapılandırma dosyasından yükleme.

Temel nft komutları

# Tüm ruleset'i göster
nft list ruleset

# Belirli bir tabloyu göster
nft list table inet filter

# Table oluştur
nft add table inet filter

# Chain oluştur (base chain — hook'a bağlı)
nft add chain inet filter input \
    '{ type filter hook input priority 0; policy drop; }'

# Chain oluştur (regular chain)
nft add chain inet filter check_ssh

# Kural ekle (chain'in sonuna)
nft add rule inet filter input \
    ct state established,related accept

# Kural ekle (chain'in başına)
nft insert rule inet filter input \
    iif lo accept

# Tüm kuralları sil
nft flush ruleset

# Tabloyu sil (içindeki tüm chain+rule ile)
nft delete table inet filter

Yapılandırma dosyası kullanımı

# /etc/nftables.conf — systemd tarafından yüklenir
# Dosyadan yükle
nft -f /etc/nftables.conf

# Sözdizimi kontrolü (uygulamadan)
nft -c -f /etc/nftables.conf

# Mevcut ruleset'i dosyaya kaydet
nft list ruleset > /etc/nftables.conf

# systemd ile başlangıçta yükle
systemctl enable nftables
systemctl start  nftables

nftables.conf yapısı

#!/usr/sbin/nft -f
# /etc/nftables.conf

# Önceki kuralları temizle
flush ruleset

table inet filter {
    chain input {
        type filter hook input priority 0; policy drop;

        # Loopback
        iif "lo" accept

        # Kurulu bağlantılar
        ct state { established, related } accept

        # Geçersiz paketleri düşür
        ct state invalid drop

        # SSH
        tcp dport 22 accept

        # ICMP (ping)
        ip protocol icmp accept
        ip6 nexthdr icmpv6 accept
    }

    chain forward {
        type filter hook forward priority 0; policy drop;
    }

    chain output {
        type filter hook output priority 0; policy accept;
    }
}

Bu bölümde

  • nft list ruleset: mevcut tüm kuralları görüntüle
  • nft -f dosya: atomik olarak tüm ruleset'i uygula
  • policy drop: default reddet — yalnızca açıkça izin verilenler geçer

03 Temel kural yazımı

IP adresi, port ve bağlantı durumu eşleştirme ifadeleri — nftables kural sözdiziminin yapı taşları.

IP adresi eşleştirme

# Kaynak IP'ye göre drop
nft add rule inet filter input ip saddr 10.0.0.5 drop

# Hedef IP'ye göre kabul
nft add rule inet filter input ip daddr 192.168.1.1 accept

# Subnet eşleştirme
nft add rule inet filter input ip saddr 192.168.0.0/16 accept

# IPv6 eşleştirme
nft add rule inet filter input ip6 saddr 2001:db8::/32 drop

# inet: hem IPv4 hem IPv6
nft add rule inet filter input ip saddr 10.0.0.0/8 log prefix "RFC1918: " drop

Port ve protokol eşleştirme

# TCP port
nft add rule inet filter input tcp dport 80 accept
nft add rule inet filter input tcp dport 443 accept

# Port aralığı
nft add rule inet filter input tcp dport 8000-8080 accept

# Port listesi (küme)
nft add rule inet filter input tcp dport { 22, 80, 443, 8443 } accept

# UDP
nft add rule inet filter input udp dport 51820 accept   # WireGuard
nft add rule inet filter input udp dport 53 accept      # DNS

# Kaynak + hedef port kombinasyonu
nft add rule inet filter input \
    ip saddr 192.168.1.0/24 tcp dport { 22, 443 } accept

Bağlantı durumu (ct state)

# Stateful firewall — temel şablon
table inet filter {
    chain input {
        type filter hook input priority 0; policy drop;

        # Kurulu ve ilişkili bağlantılar her zaman geçer
        ct state { established, related } accept

        # Geçersiz paket (bozuk durum tablosu)
        ct state invalid counter drop

        # Yeni bağlantı — port bazlı izin
        ct state new tcp dport 22 accept
        ct state new tcp dport { 80, 443 } accept
        ct state new udp dport 51820 accept

        # ICMP: rate limit ile flood koruması
        ip protocol icmp limit rate 10/second accept
        ip6 nexthdr icmpv6 limit rate 10/second accept

        # Gerisi: log ve drop
        counter log prefix "INPUT DROP: " drop
    }
}

Eylemler

EylemAçıklama
acceptPaketi kabul et, chain değerlendirmesini durdur
dropPaketi sessizce düşür — gönderene bildirim yok
rejectPaketi reddet + ICMP unreachable/TCP reset gönder
reject with icmp type port-unreachableICMP port unreachable ile reddet
log prefix "TEXT " level infoKernel log'a yaz (dmesg/journalctl)
counterEşleşen paket/byte sayacı — sonraki eylemle birleşir
goto chain_nameBaşka chain'e git — geri dönüş yok
jump chain_nameBaşka chain'e dal — zincir bitince geri döner

Bu bölümde

  • ct state established,related: stateful firewall temeli — her zaman ilk kurala koy
  • Küme sözdizimi { 80, 443 }: birden fazla değeri tek kuralla eşleştir
  • counter + log: izleme ve hata ayıklama için birlikte kullan

04 NAT

nftables NAT kuralları, ip nat tablosu (veya inet nat) altında prerouting ve postrouting chain'lerinde tanımlanır. MASQUERADE, SNAT, DNAT ve port forwarding örnekleri.

MASQUERADE — dinamik SNAT

flush ruleset

table ip nat {
    chain postrouting {
        type nat hook postrouting priority 100; policy accept;

        # eth0 üzerinden çıkan tüm trafiği masquerade et
        # (dinamik IP için SNAT alternatifi)
        oifname "eth0" masquerade
    }
}

table inet filter {
    chain forward {
        type filter hook forward priority 0; policy drop;

        # LAN'dan WAN'a forward
        iifname "eth1" oifname "eth0" ct state new,established,related accept
        iifname "eth0" oifname "eth1" ct state established,related accept
    }
}

SNAT — sabit kaynak IP

# Sabit IP'li SNAT (MASQUERADE yerine — performans daha iyi)
table ip nat {
    chain postrouting {
        type nat hook postrouting priority 100; policy accept;
        oifname "eth0" snat to 203.0.113.5
    }
}

DNAT — port forwarding

table ip nat {
    chain prerouting {
        type nat hook prerouting priority -100; policy accept;

        # Dış port 2222 → iç sunucu SSH (22)
        iifname "eth0" tcp dport 2222 dnat to 192.168.1.10:22

        # HTTP forward — iç web sunucusuna
        iifname "eth0" tcp dport 80 dnat to 192.168.1.20:80

        # UDP port forward (örn. TFTP)
        iifname "eth0" udp dport 69 dnat to 192.168.1.30:69
    }
}

WireGuard ile NAT — tam örnek

flush ruleset

table inet filter {
    chain input {
        type filter hook input priority 0; policy drop;
        iif "lo" accept
        ct state { established, related } accept
        ct state invalid drop
        tcp dport 22 accept
        udp dport 51820 accept           # WireGuard
        ip protocol icmp accept
    }
    chain forward {
        type filter hook forward priority 0; policy drop;
        iifname "wg0" accept             # VPN'den gelen forward
        oifname "wg0" ct state established,related accept
    }
}

table ip nat {
    chain postrouting {
        type nat hook postrouting priority 100; policy accept;
        oifname "eth0" masquerade        # VPN istemcileri internete çıkar
    }
}

Bu bölümde

  • MASQUERADE: dinamik IP (DHCP) için; SNAT: sabit IP için daha verimli
  • DNAT prerouting'de yapılır; forward chain'de izin kuralı da gereklidir
  • WireGuard + NAT: wg0 forward + eth0 MASQUERADE kombinasyonu

05 Sets ve maps

nftables set'leri, IP adresleri veya portların gruplandırılmasını sağlar. Map'ler ise anahtar-değer eşleştirmesi yaparak DNAT hedeflerini veya counter gruplarını dinamik yönetmeye olanak tanır.

Named set — IP whitelist

table inet filter {
    # Tanımlı IP seti
    set admin_hosts {
        type ipv4_addr
        flags constant
        elements = {
            192.168.1.10,
            192.168.1.11,
            10.10.0.1
        }
    }

    # Dinamik engel listesi (çalışma zamanında güncellenebilir)
    set blocklist {
        type ipv4_addr
        flags dynamic, timeout
        timeout 1h              # 1 saat sonra otomatik temizlenir
        gc-interval 5m
    }

    chain input {
        type filter hook input priority 0; policy drop;

        # Whitelist'ten gelen SSH kabul
        ip saddr @admin_hosts tcp dport 22 accept

        # Blocklist'ten gelen her şeyi düşür
        ip saddr @blocklist drop
    }
}

# Çalışma zamanında set güncellemesi
nft add element inet filter blocklist { 1.2.3.4, 5.6.7.8 }
nft delete element inet filter blocklist { 1.2.3.4 }
nft list set inet filter blocklist

Interval set — subnet kümesi

table inet filter {
    set rfc1918 {
        type ipv4_addr
        flags interval
        elements = {
            10.0.0.0/8,
            172.16.0.0/12,
            192.168.0.0/16
        }
    }

    chain input {
        type filter hook input priority 0; policy drop;
        # RFC1918 adresleri sadece iç arayüzden kabul
        ip saddr @rfc1918 iifname "eth1" accept
        ip saddr @rfc1918 iifname "eth0" drop
    }
}

Map — DNAT hedef mapping

table ip nat {
    # Port → iç sunucu IP:port eşleştirmesi
    map port_forward {
        type inet_service : ipv4_addr . inet_service
        elements = {
            2222 : 192.168.1.10 . 22,   # SSH
            8080 : 192.168.1.20 . 80,   # Web
            8443 : 192.168.1.20 . 443,  # HTTPS
        }
    }

    chain prerouting {
        type nat hook prerouting priority -100; policy accept;
        # Map'ten DNAT hedefini al
        iifname "eth0" tcp dport map @port_forward dnat to
    }
}

Port knocking — state machine

table inet filter {
    # Port knocking için durum takibi
    set knock1 {
        type ipv4_addr; flags dynamic, timeout; timeout 10s;
    }
    set knock2 {
        type ipv4_addr; flags dynamic, timeout; timeout 10s;
    }
    set allowed_ssh {
        type ipv4_addr; flags dynamic, timeout; timeout 60s;
    }

    chain input {
        type filter hook input priority 0; policy drop;

        # Açık olan SSH erişimine izin ver
        ip saddr @allowed_ssh tcp dport 22 accept

        # Port knock sekansı: 7000 → 8000 → SSH açık
        tcp dport 7000 add @knock1 { ip saddr }
        ip saddr @knock1 tcp dport 8000 add @allowed_ssh { ip saddr }

        ct state { established, related } accept
    }
}

Bu bölümde

  • Named set: IP listesi tek yerde tanımla, birden fazla kuralta kullan
  • flags dynamic + timeout: çalışma zamanında eklenip otomatik silinen set
  • Map ile DNAT: port → hedef eşleştirmesi, kural sayısını dramatik azaltır

06 Gömülü güvenlik politikası

Kaynak kısıtlı gömülü sistemler için minimal ama güçlü güvenlik duvarı politikası: default drop, stateful firewall, rate limiting ve flood koruması.

Default drop politikası

flush ruleset

table inet filter {
    chain input {
        type filter hook input priority 0;
        # Default: DROP — yalnızca açıkça izin verilenler geçer
        policy drop;

        # 1. Loopback — hiçbir zaman engelleme
        iif lo accept

        # 2. Kurulu bağlantılar — performans için en başta
        ct state established,related accept

        # 3. Geçersiz — hemen düşür
        ct state invalid drop

        # 4. Servis kuralları (platforma göre özelleştir)
        tcp dport 22 accept          # SSH yönetim
        udp dport 51820 accept       # WireGuard VPN

        # 5. ICMP — rate limit ile
        ip  protocol   icmp   icmp type echo-request limit rate 5/second accept
        ip6 nexthdr    icmpv6 icmpv6 type echo-request limit rate 5/second accept
        # ICMPv6 ND gerekli (Neighbor Discovery)
        ip6 nexthdr icmpv6 icmpv6 type {
            nd-neighbor-solicit, nd-neighbor-advert,
            nd-router-solicit,   nd-router-advert
        } accept
    }

    chain forward {
        type filter hook forward priority 0; policy drop;
    }

    chain output {
        type filter hook output priority 0; policy accept;
    }
}

Rate limiting — brute force koruması

table inet filter {
    chain input {
        type filter hook input priority 0; policy drop;
        iif lo accept
        ct state established,related accept
        ct state invalid drop

        # SSH brute force koruması
        # Dakikada 3'ten fazla yeni SSH bağlantısı: log ve drop
        tcp dport 22 ct state new \
            limit rate over 3/minute burst 5 packets \
            log prefix "SSH BRUTE: " level warn drop

        tcp dport 22 ct state new accept

        # HTTP flood koruması
        tcp dport { 80, 443 } ct state new \
            limit rate over 100/second burst 200 packets drop

        tcp dport { 80, 443 } accept

        # ICMP flood (ping flood)
        ip protocol icmp \
            limit rate over 10/second burst 20 packets drop
        ip protocol icmp accept
    }
}

SYN flood koruması

table inet filter {
    chain input {
        type filter hook input priority 0; policy drop;
        iif lo accept
        ct state established,related accept

        # SYN flood — TCP SYN paketleri için rate limit
        tcp flags syn tcp dport { 80, 443 } \
            limit rate over 200/second burst 500 packets \
            log prefix "SYN FLOOD: " drop

        # Geçersiz TCP bayrakları
        tcp flags & (fin|syn|rst|psh|ack|urg) == 0x0 drop  # NULL scan
        tcp flags & (fin|syn) == (fin|syn) drop             # XMAS scan

        ct state new tcp dport { 22, 80, 443 } accept
        ip protocol icmp accept
    }
}

Bu bölümde

  • policy drop = whitelist modeli; tüm bilinmeyenler bloke edilir
  • limit rate over: eşiği aşan trafiği drop et; burst ile kısa spike'lara tolerans
  • TCP bayrak kontrolü: NULL ve XMAS scan gibi port tarama tekniklerini engelle

07 Pratik: IoT gateway güvenlik duvarı

WAN (eth0), LAN (eth1) ve WireGuard VPN (wg0) arayüzleri olan bir IoT gateway için tam nftables yapılandırması: NAT, rate limit, port forward ve WireGuard entegrasyonu.

Ağ topolojisi

  İnternet
     │
  eth0 (WAN — DHCP, dinamik IP)
     │
  ┌──┴──────────────────────────────────┐
  │  IoT Gateway                         │
  │  nftables güvenlik duvarı             │
  └──┬──────────────────┬────────────────┘
     │                  │
  eth1 (LAN)         wg0 (VPN)
  192.168.2.0/24    10.10.0.0/24
  IoT cihazları     Uzak yönetim
    

Tam gateway nftables.conf

#!/usr/sbin/nft -f
# /etc/nftables.conf — IoT Gateway güvenlik duvarı

flush ruleset

# ─── Değişkenler ─────────────────────────────────────
define WAN    = "eth0"
define LAN    = "eth1"
define VPN    = "wg0"
define LAN_NET = 192.168.2.0/24
define VPN_NET = 10.10.0.0/24

# ─── Engel listesi ───────────────────────────────────
table inet raw {
    set blocklist {
        type ipv4_addr
        flags dynamic, timeout
        timeout 1h
        gc-interval 10m
    }
    chain prerouting {
        type filter hook prerouting priority -300; policy accept;
        ip saddr @blocklist counter drop
    }
}

# ─── NAT ─────────────────────────────────────────────
table ip nat {
    map port_forward {
        type inet_service : ipv4_addr . inet_service
        elements = {
            8022 : 192.168.2.10 . 22,   # IoT cihaz 1 SSH
            8080 : 192.168.2.20 . 80,   # IoT cihaz 2 HTTP
        }
    }

    chain prerouting {
        type nat hook prerouting priority -100; policy accept;
        iifname $WAN tcp dport map @port_forward dnat to
    }

    chain postrouting {
        type nat hook postrouting priority 100; policy accept;
        oifname $WAN masquerade
    }
}

# ─── Filtre ──────────────────────────────────────────
table inet filter {
    chain input {
        type filter hook input priority 0; policy drop;

        iif lo accept
        ct state established,related accept
        ct state invalid counter drop

        # WAN: yalnızca VPN ve ICMP
        iifname $WAN udp dport 51820 accept          # WireGuard
        iifname $WAN ip protocol icmp                \
            limit rate 5/second accept
        iifname $WAN drop                            # diğer WAN girişi yok

        # LAN: güvenilir ağ
        iifname $LAN ip saddr $LAN_NET accept

        # VPN: yönetim arayüzü
        iifname $VPN ip saddr $VPN_NET tcp dport 22 \
            limit rate 3/minute burst 5 packets accept
        iifname $VPN ip saddr $VPN_NET accept
    }

    chain forward {
        type filter hook forward priority 0; policy drop;

        ct state established,related accept
        ct state invalid drop

        # LAN → WAN: internete çıkış
        iifname $LAN oifname $WAN \
            ip saddr $LAN_NET ct state new accept

        # LAN → VPN: VPN ağına ulaşım
        iifname $LAN oifname $VPN accept

        # VPN → LAN: uzak yönetim
        iifname $VPN oifname $LAN ip saddr $VPN_NET accept

        # WAN → LAN: yalnızca port forward ile
        iifname $WAN oifname $LAN ct state dnat accept

        # IoT cihazları arası izolasyon (isteğe bağlı)
        # iifname $LAN oifname $LAN drop
    }

    chain output {
        type filter hook output priority 0; policy accept;
    }
}

Yapılandırmayı uygula ve test et

# Sözdizimi kontrolü
nft -c -f /etc/nftables.conf && echo "Syntax OK"

# Uygula
nft -f /etc/nftables.conf

# Doğrulama
nft list ruleset
nft list counters              # counter değerlerini izle

# Bağlantı testleri
ping -c3 8.8.8.8               # WAN çıkışı
ssh -p 8022 192.168.2.10       # DNAT port forward test
ping -c3 10.10.0.2             # VPN bağlantısı

# Rate limit testleri
hping3 -S --flood -p 22 <gateway_ip>  # SYN flood simülasyonu
nft list set inet raw blocklist          # dinamik engel listesini izle

# systemd ile kalıcı hale getir
systemctl enable nftables
systemctl start  nftables
İPUCU

IoT cihazları genellikle birbirinden izole edilmesi gereken düşük güvenlik profilli cihazlardır. iifname $LAN oifname $LAN drop kuralı etkinleştirilerek LAN izolasyonu sağlanabilir; böylece ele geçirilen bir cihaz diğer LAN cihazlarına saldıramaz. Bu özellikle endüstriyel IoT ve medikal cihazlar için önemlidir.

Bu bölümde

  • WAN/LAN/VPN arayüz ayrımı: her yönün ayrı güvenlik politikası
  • Map ile DNAT port forward: port_forward map tüm yönlendirmeyi tek tanımda toplar
  • inet raw + blocklist set: tüm trafikten önce (-300 priority) engel listesi