Debian bástyagép tűzfal (Stretch)

Innen: AdminWiki
A lap korábbi változatát látod, amilyen KZoli (vitalap | szerkesztései) 2018. május 29., 21:59-kor történt szerkesztése után volt. (Új oldal, tartalma: „A Hálózati házirend szerint valamennyi szervert ''bastion host''-ként kell kialakítani, azaz saját (csomagszűrő) tűzfallal kell rendelkezzen. A gyakorlatba…”)
(eltér) ← Régebbi változat | Aktuális változat (eltér) | Újabb változat→ (eltér)

A Hálózati házirend szerint valamennyi szervert bastion host-ként kell kialakítani, azaz saját (csomagszűrő) tűzfallal kell rendelkezzen. A gyakorlatban ez az iptables (netfilter) konfigurálását jelenti, amelyet ebben a leírásban a Shorewall parser segítségével valósítunk meg. A Shorewall relatív egyszerű és átlátható konfigurációs állományok alapján állítja elő a natív iptables konfigurációt és szükség szerint módosítja a routing beállításokat is.

  • Ez a leírás a majdani publikus eléréshez szükséges, alapvető csomagszűrést valósít meg, egy darab hálózati interface-szel rendelkező szervergépen.
  • Ez a leírás csak IPv4-re vonatkozik - IPv6 TODO!
  • Magasabb szintű forgalomszűrés: TODO!


Előfeltételek


Telepítés

Debian csomagból telepíthető:

apt-get install shorewall shorewall-doc # + kevés függőség

Telepítés után a konfigurálatlan Shorewall még nem indul el.

Beállítások

Beállításához a /usr/share/shorewall/configfiles tartalmát másoljuk be a /etc/shorewall könyvtárba, egyben szigorítsuk meg a jogosultságokat:

cp /usr/share/shorewall/configfiles/* /etc/shorewall/  # Zömmel üres template-ek, a szükségeseket ki kell tölteni
rm /etc/shorewall/*.annotated                          # a dokumentációra itt nem lesz szükség
chmod 640 /etc/shorewall/*

Ezután szerkesszük meg a következő állományokat:

shorewall.conf

A Shorewall általános beállításait az alábbiak szerint módosítjuk:

  • a naplófájlok elárasztását megakadályozandó, a naplóbejegyzések számát limitáljuk (az alábbi beállítás hosszú távon másodpercenként legfeljebb egy bejegyzést engedélyez - részletesen ld. itt);
  • a dinamikus (a Shorewall futása közben létrehozott) szabályokat a már kialakított kapcsolatokra is érvényesítjük és naplózzuk (ez szükséges a fail2ban integrációhoz);
  • a jelen leírásban nem foglalkozunk az IPv6 beállításával, hanem ezt a forgalmat egyszerűen letiltjuk (TODO!).
-rw-r----- root root /etc/shorewall/shorewall.conf

[...]
BLACKLIST_LOG_LEVEL=info
[...]
LOGLIMIT="1/sec:60"
[...]
#BLACKLIST="NEW,INVALID,UNTRACKED"
BLACKLIST="ALL"
[...]
DISABLE_IPV6=Yes
[...]

vardir

A Shorewall indításakor összeállít egy .start scriptet, amelyet szeretne a /var/lib/shorewall könyvtárban lefuttatni. Ez a biztonsági beállításainkkal ütközik, ezért kénytelenségből ezt a könyvtárat átmozgatjuk az írható és futtatható partíción lévő /etc/shorewall könyvtárba:

mv /var/lib/shorewall /etc/shorewall/tmp
chmod 700 /etc/shorewall/tmp # Szigorú hozzáférés

A Shorewall számára egy (a maintainer által nem biztosított, létrehozandó) konfigurációs állományban meg kell adni e könyvtár helyét:

touch /etc/shorewall/vardir
chmod 640 /etc/shorewall/vardir
mcedit /etc/shorewall/vardir
-rw-r----- root root /etc/shorewall/vardir

# Fixup to avoid creating .start script on a non-executable partition
VARDIR=/etc/shorewall/tmp

params

Ebben az állományban tetszőleges, a Shorewall-on belül érvényes környezeti változók definiálhatóak (ld. itt). Ebben a leírásban ezt arra fogjuk használni, hogy a Debian Stretch-ben debütáló interface névkonvenciót (predictable network interface names) a Shorewall beállító állományaiban egységesen használható logikai névre fordítsuk.

-rw-r----- root root /etc/shorewall/params

[...]
###############################################################################
# Primary network interface
NET_IF=enp0s25

Ügyeljünk arra, hogy ebben a sorban a telepítés alatti gép tényleges interface megnevezése szerepeljen!

zones

A Shorewall forgalomszűrő szabályait nem konkrét IP címekre vagy hálózati interface-ekre, hanem logikai hálózatokra (IP tartományok, zónák) szokás megadni; ezek deklarálására szolgál ez az állomány.

A már deklarált tűzfalgép (fw) zóna mellett deklaráljuk a legtágabb (minden, külön nem definiált forrást és célt tartalmazó) logikai net zónát és egy megbízható(bbnak tekintett) logikai trs zónát (pl. biztonsági mentések fogadása számára):

-rw-r----- root root /etc/shorewall/zones

[...]
###############################################################################
#ZONE           TYPE            OPTIONS         IN_OPTIONS      OUT_OPTIONS

fw              firewall
trs             ipv4
net             ipv4

Megjegyzendő, hogy ezek csak deklarációk, a fw kivételével itt még semmilyen IP tartományt vagy jogosultságot nem rendeltünk ezekhez a zónákhoz.

interfaces

Itt deklarálható az összes hálózati interface (hálózati kártya) és (amennyiben van ilyen) az általuk definiált logikai tűzfal zóna. Egyetlen (a params állományban már megnevezett) hálózati interface esetén:

-rw-r----- root root /etc/shorewall/interfaces

?FORMAT 2
###############################################################################
#ZONE           INTERFACE              OPTIONS
#
net             $NET_IF                arp_filter,dhcp,logmartians,nosmurfs,routefilter,tcpflags #,norfc1918

Amennyiben több hálózati interface is van, mindegyiket külön sorban kell deklarálni. Az alábbi példában az első interface egy belső hálózaton van és DHCP-vel kap címet, míg a második az Internetre csatlakozik, statikus IP címmel (a params állományban mindkét interface valódi nevét előzetesen meg kell adni!):

-rw-r----- root root /etc/shorewall/interfaces

?FORMAT 2
###############################################################################
#ZONE           INTERFACE               OPTIONS
#
net             $INL_IF                 arp_filter,dhcp,logmartians,nosmurfs,routefilter,tcpflags #,norfc1918
net             $NET_IF                 arp_filter,logmartians,norfc1918,nosmurfs,routefilter,tcpflags #,dhcp

A megadott opciók közül:

  • az arp_filter biztosítja, hogy több interface-szel rendelkező gép esetén minden interface csak a saját IP-jére vonatkozó who-has kérésére válaszoljon (Linux alapértelmezés szerint a gép bármelyik IP-jére vonatkozó who-has kérésre bármelyik interface válaszol, nemcsak az, amelyikre az adott IP be van állítva).
  • ha a gép a belhálózaton DHCP-t használ, kell a dhcp direktíva; statikus IP esetén vegyük ki.
  • a norfc1918 blokkolja a nem route-olható címekről érkező forgalmat; ezt a külső interface-en érdemes aktiválni, ha a szerver külső lába előtt már nincs címfordítás (NAT-olt DMZ-ben nyilván nem).

hosts

Itt deklarálhatóak azok a zónák, amelyeket nem hálózati interface, hanem IP tartomány alapján definiálunk - ebben a leírásban ilyen a trs (trusted) zóna. A hozzárendelés felülről lefelé értékelődik ki, vagyis több zóna és átfedő tartományok esetén a sorrend fontos! Az ezen tartományokkal le nem fedett hálózat az interfaces állományban megadott zónát (net) alkotja. Ha újabb zónára lenne szükség, azt itt érdemes felvenni; kerülendő az IP-k bedrótozása a szabályokba!

-rw-r----- root root /etc/shorewall/hosts

[...]
##############################################################################
#ZONE           HOSTS                           OPTIONS
#
trs             $NET_IF:IP.IP.IP.IP/MASK,IP.IP.IP.IP/MASK

policy

Nem tévesztendő össze az iptables policy beállításokkal, amelyek nem relevánsak, mert a Shorewall minden eredeti láncot logdrop-pal zár le.

Ebben az állományban kell megadni az alapértelmezett viselkedést másutt nem kezelt csomagok esetére (eldobás és naplózás). Ebben a leírásban két naplószintet használunk: a warn logban a hatáskörünkbe tartozó (a telepítés alatti szervergép, vagy a megbízható hálózat felől kezdeményezett) szabálysértéseket gyűjtjük, az info logban pedig az egyéb (jellemzően az Internet felől kezdeményezett) szabálysértéseket. A naplóbejegyzések alapértelmezésben a kern.log-ba kerülnek, ezt alább át fogjuk irányítani.

-rw-r----- root root /etc/shorewall/policy

[...]
###############################################################################
#SOURCE         DEST            POLICY  LOGLEVEL        LIMIT   CONNLIMIT
#
fw              all             REJECT  warn            
net             fw              DROP    info            
trs             fw              REJECT  warn            
# The FOLLOWING POLICY MUST BE LAST
all             all             DROP    info            

rules

Ebben a leírásban befelé csak a ping, az SSH, SMTP, web (mindenhonnan) és az Amanda (csak a biztonságosnak gondolt trs hálózatról) engedélyezett. Kifelé engedélyezett a ping, a DNS lekérés és a traceroute, a levélküldés SMTP-vel (+SMTPs, MSA), az időszinkron NTP protokollal, PGP kulcsszerverek elérése (HKP), a web és az FTP. Opcionálisan az SSH is engedélyezett lehet.

-rw-r----- root root /etc/shorewall/rules

[...]
####################################################################################### [...>]
#ACTION         SOURCE          DEST            PROTO   DPORT   SPORT   ORIGDEST        [...>]

[...]
?SECTION NEW

# RULES HANDLING INCOMING CONNECTIONS

# Accept ping from anywhere
Ping/ACCEPT     all             fw
# Accept ping from trs; silently drop from any other source
#Ping/ACCEPT    trs             fw
#Ping/DROP      all             fw

# Public services
SSH/ACCEPT      all             fw
SMTP/ACCEPT     all             fw
Web/ACCEPT      all             fw

# Accept Amanda connections from trs
Amanda/ACCEPT   trs             fw
ACCEPT          trs             fw              udp     1:65535 amanda
ACCEPT          trs             fw              tcp     amandaidx
ACCEPT          trs             fw              tcp     amidxtape

# From net incoming auth request silently dropped (stealth);
# from trs rejected by default
DROP            net             fw              tcp     113

# Any other trials logdropped by default
# (broadcasts, invalids, not-syns, SMB, SMTP, UPn silently)

# RULES HANDLING OUTBOUND CONNECTIONS

Ping/ACCEPT     fw              all
Amanda/ACCEPT   fw              all
Auth/ACCEPT     fw              all
DNS/ACCEPT      fw              all
FTP/ACCEPT      fw              all
HKP/ACCEPT      fw              all
NTP/ACCEPT      fw              all
SMTP/ACCEPT     fw              all
SMTPS/ACCEPT    fw              all
MSA/ACCEPT      fw              all
#SSH/ACCEPT     fw              all
Trcrt/ACCEPT    fw              all
Web/ACCEPT      fw              all
#

# Any other trials logdropped by default

#LAST LINE -- ADD YOUR ENTRIES BEFORE THIS ONE -- DO NOT REMOVE

Megjegyzés: biztonságosabbnak tűnik az SSH-t kifelé tiltani, és az SCP-t mindig az adminisztrátor által használt, távoli gépről indítani - ez alól csak a szolgáltatások átköltöztetése idejére, tetemes adatforgalom esetén lenne érdemes kivételt tenni. A vonatkozó action-ök ezért kommentezve vannak.

Használatba vétel

A Shorewall engedélyezéséhez a /etc/default/shorewall állományban a startup értékét 1-re kell állítani:

-rw-r--r-- root root /etc/default/shorewall

[...]
startup=1

majd a tűzfal elindítható:

systemctl start shorewall

A generált iptables szabályok megtekinthetőek az alábbi paranccsal:

iptables -n -L | less

Bug: a jelen leírás készítésekor, a fenti beállításokkal (re)boot után a Shorewall nem indul el (de manuálisan indítható)! Lehetséges workaround:

systemctl enable shorewall  # csak egy alkalommal kell megtenni

ezután, tapasztalat szerint, a Shorewall rendben elindul. Releváns lehet még ez a régebbi hibajegy is - TODO!

Tűzfalnapló átirányítása

Érdemes elkülöníteni a terjedelmes tűzfalnaplókat a többiektől. Az alanti megoldás a Gentoo Security listáról való, és feltételezi, hogy a Shorewall csak warn és info szintű syslog bejegyzéseket készít. Az elkülönítéshez készítsünk egy napló könyvtárat a Shorewall számára:

mkdir -m 750 /var/log/shorewall

Ezután szerkesszük meg a /etc/syslog-ng/syslog-ng.conf file-t, és szúrjuk be a Destinations section végére:

-rw-r--r-- root root /etc/syslog-ng/syslog-ng.conf

[...]
# Shorewall separate logging
# originally: http://marc.theaimsgroup.com/?l=gentoo-security&m=106040714910563&w=2
destination d_shorewall_warn
    { file ("/var/log/shorewall/warn.log" owner(root) group(adm)); };
destination d_shorewall_info
    { file ("/var/log/shorewall/info.log" owner(root) group(adm)); };

Ugyanitt a Filters section végére:

-rw-r--r-- root root /etc/syslog-ng/syslog-ng.conf

[...]
# Shorewall separate logging
# originally: http://marc.theaimsgroup.com/?l=gentoo-security&m=106040714910563&w=2
filter f_shorewall_warn { level (warn) and match ("Shorewall" value ("MESSAGE")); };
filter f_shorewall_info { level (info) and match ("Shorewall" value ("MESSAGE")); };

Végül a Log paths section elejére (így a flags(final); direktíva miatt csak ezekbe a logokba kerül a kimenet):

-rw-r--r-- root root /etc/syslog-ng/syslog-ng.conf

[...]
# Shorewall separate logging
# originally: http://marc.theaimsgroup.com/?l=gentoo-security&m=106040714910563&w=2
log { source (s_src); filter (f_shorewall_warn); destination (d_shorewall_warn); flags(final); };
log { source (s_src); filter (f_shorewall_info); destination (d_shorewall_info); flags(final); };

Az új logok rotálásához egészítsük ki a /etc/logrotate.d/shorewall állományt az alábbiakkal:

-rw-r--r-- root root /etc/logrotate.d/shorewall

[...]
/var/log/shorewall/*.log {
    daily
    rotate 7
    compress
    missingok
    create 0640 root adm
}

A változtatások érvényesítésére indítsuk újra a syslog-ng-t:

systemctl restart syslog-ng

Gyorsteszt

Próbáljunk ki egy tiltott kapcsolódást és ellenőrizzük, hogy az sikertelen, valamint hogy a megfelelő Shorewall logban létrejön a bejegyzés:

telnet 1.2.3.4 111; sleep 1; tail -f /var/log/shorewall/warn.log

Tűzfal kinyitása

Ha átmenetileg(!) ki kell kapcsolni a csomagszűrést, ez pl. a következő paranccsal tehető meg:

systemctl stop shorewall

Irodalom