Portál AbcLinuxu, 27. dubna 2024 07:15

IPSec v kernelu 2.6 - II

2. 7. 2004 | Marek Červenka
Články - IPSec v kernelu 2.6 - II  

Další díl seriálu o principech šifrované komunikace na bázi IPSec.

Dnes si ukážeme konfiguraci pro road warrior scénář. Autentizace bude probíhat sdíleným klíčem a výměna klíču bude realizována pomocí IKE démona racoon. Vzhledem k tomu, že bohužel zatím nejčastějším případem, kdy je někomu umožněn přístup do interní sítě zvenčí, je nějaký pán z vedení, ukážeme si, jak využít integrovaného L2TP/IPSec klienta, který je standardně ve Windows 2000/XP. A když už ten přístup bude hotový, ukážeme si, jak se tam dostane sysadmin z Linuxu.

Přehledné porovnání kladů a záporů L2TP/IPSec lze nalézt na http://www.jacco2.dds.nl/networking/freeswan-l2tp.html#ProsCons.

K realizaci našeho scénáře potřebujeme nějakou implementaci protokolu L2TP.

L2TP

Protokol L2TP (Layer Two Tunneling Protocol) je popsán v RFC 2661. L2TP je v podstatě rozšířením protokolu PPP, který umožňuje spojení pouze mezi přístupovým zařízením (NAS) a klientem. L2TP tento problém odbourává a umožňuje, aby koncová zařízení byla kdekoliv v IP síti. V Linuxu je prakticky L2TP používáno tak, že L2TP vrstva se domluví na specifických parametrech protokolu a vlastní spojení už opět realizuje pppd démon.

Implementace použitá pro naše testování se nachází na http://www.l2tpd.org. Tamtéž lze nalézt odkazy na další implementace. Implementace l2tpd je kompletně v user-space. Několik pokusů o implementaci v kernelu zůstává na mrtvém bodě. Projekt jako takový také není zrovna příliš ve středu zájmu. Poslední verze 0.69 vyšla někdy v roce 2002. Od té doby se nashromáždilo několik patchů, které jsou třeba pro správnou funkčnost.

Patchovaný balíček udržuje Jacco de Leeuw na adrese: http://www.jacco2.dds.nl/networking/freeswan-l2tp.html#L2TPoverview

Pro Debian se udržuje balíček na této stránce: http://packages.qa.debian.org/l/l2tpd.html. Tamtéž by měl být zapracovaný patch na poslední bezpečnostní problém ( http://www.securityfocus.com/archive/1/365211).

Při použití s kernelem 2.6 je třeba mít povolené CONFIG_LEGACY_PTYS=y.

Alternativní implementace: http://www.mail-archive.com/l2tpd-devel@l2tpd.org/msg00153.html.

Mimochodem, taková poznámka k patentům: http://www.jacco2.dds.nl/networking/freeswan-l2tp.html#Patent

Racoon

Racoon je implementace IKEv1 protokolu sloužícího pro automatickou výměnu klíčů. Podporuje autentizaci pomocí certifikátů, sdíleného klíče, kerberosu a rozpracována je podpora plain RSA klíčů. Ta je důležitá pro interoperabilitu se *Swan implementacemi. V některém z dalších dílů třeba také na nějakou ukázku dojde ;).

Při testování byla použita distribuce Fedora Core 2, ale stejné chování lze očekávat i u SuSE apod. Balíček, ve kterém se racoon nachází, se jmenuje ipsec-tools.

Podpora pro IPSec je již i v balíku initscripts, takže lze standardně používat konfigurační soubory typu ifcfg-ipsec0, keys-ipsec0. Parametry lze najít v /etc/sysconfig/network-scripts/ifup-ipsec nebo v dokumentaci k distribuci. Průvodce nastavením IPSecu můžeme spustit příkazem system-config-network. Konfigurace se nevztahuje na L2TP.

V našem případě ovšem zůstaneme u ruční konfigurace.

Konfigurace serveru - IPSec

Konfigurační soubor pro racoon je /etc/racoon/racoon.conf a obsahuje:

Dále si uvedeme parametry, které jsou podstatné pro náš příklad. Ostatní parametry lze nalézt v manuálových stránkách - man racoon.conf. Konfiguraci bereme z pohledu, že racoon je příjemce spojení. Parametry tedy znamenají, jaké hodnoty jsou akceptovatelné. Pokud bude racoon iniciátor (klient), budou hodnoty znamenat, jaké parametry požaduje od druhé strany. Mezi komunikujícími musí nastat vzájemná shoda v požadovaných a akceptovatelných parametrech.

globální nastavení

log <level>; #level - notify, debug, debug2
Nastavuje úroveň logování.
path pre_shared_key "/etc/racoon/psk.txt";
Cesta k souboru, ve kterém jsou uloženy sdílené klíče.

sekce listen, padding, timer

Obsahují direktivy, které umožňují přesněji specifikovat, na jakém portu má racoon poslouchat. Dále obsahují nastavení kolem časovačů a nastavení formátu vyplňování paketů - padding.

sekce remote

remote anonymous {
Klíčové slovo "anonymous" nám říká, že tato sekce se použije pro všechna spojení, pro které neexistuje jiná remote sekce se specifikovanou IP adresou.
  exchange_mode main;
Specifikuje, jaký mód komunikace je akceptovatelný ve fázi 1 (phase1), rozdíly mezi módy jsou v rychlosti/náročnosti/bezpečnosti.
  generate_policy on;
Racoon bude automaticky generovat politiky, pokud nebudou existovat (pro klienty s dynamickými ip adresami).
  proposal {
   encryption_algorithm 3des;
Šifrovací algoritmus pro fázi 1.
   hash_algorithm md5;
Hash algoritmus pro fázi 1.
   authentication_method pre_shared_key;
Metoda autentizace (v našem případě sdílený klíč).
   dh_group modp1024;
Skupina pro Diffie-Hellman (DH) algoritmus výměny klíčů.
   }
}

sekce sainfo

sainfo anonymous {
  encryption_algorithm 3des;
Specifikuje šifrovací algoritmus pro fázi 2.
  authentication_algorithm hmac_md5;
Algoritmus pro autentizaci paketů v rámci ESP.
  compression_algorithm deflate;
Kompresní algoritmus.
}

Konfigurační soubor tedy bude ve finále vypadat takto:

path pre_shared_key "/etc/racoon/psk.txt";
log debug;
remote anonymous {
    exchange_mode main;
    generate_policy on;
    proposal {
        encryption_algorithm 3des;
        hash_algorithm md5;
        authentication_method pre_shared_key;
        dh_group modp1024;
        }
}

sainfo anonymous {
    encryption_algorithm 3des;
    authentication_algorithm hmac_md5;
    compression_algorithm deflate;
}

Identifikace klienta

Jak už někoho určitě napadlo (minimálně ty, co se tím živí), abychom klienta mohli ověřit, musíme ho nějak identifikovat. V případě, že identifikaci nijak zvlášť nespecifikujeme, bere racoon jako bernou minci IP adresu klienta. To ovšem znamená, že tuto adresu potřebujeme vždy vědět předem.

Soubor se sdílenými hesly by potom vypadal nějak takto.

# psk.txt
192.168.0.150  hladjemujnepritel

Toto řešení se nám ovšem nelíbí, protože je velmi pravděpodobné, že někdo bude mít adresu dynamickou. Dle kapitoly 4.6.2.1 v RFC 2407 máme tyto možnosti identifikace klienta:

ID Type Value
RESERVED 0
ID_IPV4_ADDR 1
ID_FQDN 2
ID_USER_FQDN 3
ID_IPV4_ADDR_SUBNET 4
ID_IPV6_ADDR 5
ID_IPV6_ADDR_SUBNET 6
ID_IPV4_ADDR_RANGE 7
ID_IPV6_ADDR_RANGE 8
ID_DER_ASN1_DN 9
ID_DER_ASN1_GN 10
ID_KEY_ID 11

V situaci, kdy nám stačí jedno sdílené heslo pro všechny klienty (např. máme 5 manažerů) a používáme autentifikaci pomocí L2TP, bychom potřebovali ID_IPV4_ADDR_SUBNET 4. Tato možnost bohužel zatím není v racoonu implementována (hledá se nový majitel tohoto kousku kódu ;)).

Soubor se sdílenými hesly by potom mohl vypadat nějak takto.

# psk.txt
0.0.0.0/0  hladjemujnepritel

Vyhnout se tomuto problému je možné při použití jiné metody identifikace. Například lze použít ID_FQDN 2. V konfiguraci racoona (klient) potom použijeme v sekci remote direktivu peers_identifier fqdn "fakt.jsem.to.ja.ver.mne.cz";.

V konfiguraci racoona (server) použijeme v sekci remote direktivu peers_identifier fqdn;. Soubor se sdílenými hesly by potom vypadal takto.

# psk.txt
fakt.jsem.to.ja.ver.mne.cz hladjemujnepritel

Po tom, co se přátelsky poplácáme po rameni, zase raději vychladneme, protože nastavit způsob identifikace ve windows pravděpodobně nepůjde.

Další věc je, že takto peers_identifier fqdn "fakt.jsem.to.ja.ver.mne.cz"; si identifikaci může nastavit kdokoliv.

Politika

V okamžiku, kdy máme hotovou konfiguraci racoona, musíme zajistit pravidla, podle kterých se spojení bude šifrovat. Níže uvedený skript zařídí, že paket jdoucí na port 1701 (l2tp) musí být šifrovaný. V okamžiku, kdy se klient pokusí spojit pomocí L2TP/IPSec, se spustí proces, ve kterém se ustanoví IPSec tunel. Na straně serveru racoon se díky direktivě generate_policy on; vygenerují pravidla pro komunikaci s klientem. Tímto šifrovaným tunelem již potom dále probíhá L2TP komunikace.

#!/bin/sh
/sbin/setkey -FP
/sbin/setkey -F
/sbin/setkey -c << EOF
spdadd moje.vpngateway.cz[1701] 0.0.0.0/0 any -P out ipsec esp/transport//require ;
EOF

Politika se nastavuje pomocí nástroje setkey - více man setkey. Pro testování doporučuju pouštět racoon na popředí a mít v konfiguraci zapnutý debug: bash# racoon -F.

l2tpd

Konfigurace serveru

Hlavní konfigurační soubor pro l2tpd je /etc/l2tpd/l2tpd.conf a obsahuje:

sekce lns

LNS je zkratka pro L2TP Network Server. Konfigurace v této sekci se tedy vztahují k nastavení serveru.

[lns default]
ip range = 10.10.10.10-10.10.10.100
Rozsah adres, které se budou přidělovat klientům.
local ip = 10.10.10.1
Lokální IP adresa na serveru.
require chap = yes
Požadujeme ověření hesla metodou CHAP.
refuse pap = yes
Odmítáme ověření hesla metodou PAP.
require authentication = yes
Požadujeme ověřování.
name = LinuxVPNserver
Jméno (pro vazbu v chap-secrets).
ppp debug = yes
Debug spojení.
pppoptfile = /etc/ppp/options.l2tpd
Soubor se specifickými parametry pro pppd.

sekce lac

LAC je zkratka pro L2TP Access Concentrator. Konfigurace v této sekci se tedy vztahují k nastavení klienta. Jelikož konfigurujeme server, zůstane tato sekce prázdná. Konfigurační soubor tedy bude ve finále vypadat takto:

# l2tpd.conf

[global]

[lns default]
ip range = 10.128.253.10-10.128.253.100
local ip = 10.128.253.1
require chap = yes
refuse pap = yes
require authentication = yes
name = LinuxVPNserver
ppp debug = yes
pppoptfile = /etc/ppp/options.l2tpd
length bit = yes

V souboru /etc/ppp/options.l2tpd jsou již klasické parametry pro PPP démona.

ipcp-accept-local
ipcp-accept-remote
ms-dns  10.10.10.1
auth
crtscts
idle 1800
mtu 1400
mru 1400
nodefaultroute
debug
lock
deflate 9
proxyarp
connect-delay 5000

V souboru /etc/ppp/chap-secrets uvedeme jména a hesla uživatelů, kterým chceme umožnit připojení.

# Secrets for authentication using CHAP
# client     server  secret          IP addresses
pepa         *       zdepa             *

Pro testování doporučuju pouštět l2tpd na popředí: bash# l2tpd -D.

Konfigurace klienta - Windows 2000/XP

Možností jak nastavit OS Windows bude zřejmě více, já uvedu ten, který znám.

Vytvoření připojení

Start - Nastavení - Ovládací panely - Síťová připojení. Vlevo nahoře je odkaz na Vytvořit nové připojení. Dále postupujeme takto: Připojit k firemní síti - Připojení k VPN - zadáme libovolný název připojení - zadáme ip/fqdn adresu našeho VPN serveru - dokončíme.

Dále je potřeba nastavit sdílené heslo (PSK - Pre Shared Key). V konfiguraci serveru jsme si zvolili PSK "hladjemujnepritel". Spustíme vlastnosti připojení a heslo zadáme do nastavení protokolu IPSec - viz obrázek.

Vlastnosti připojení

Uložíme vlastnosti a zkusíme vytočit připojení. Tam ještě zadáme uživatelské jméno a heslo, které musí odpovídat chap-secrets na VPN serveru.

Konfigurace klienta - linux + racoon + l2tpd

Konfigurace klienta je v podstatě stejná jako konfigurace serveru. V sekci remote uvedeme místo "anonymous" IP adresu našeho VPN serveru. Konfigurační soubor bude vypadat takto:

# racoon.conf
path pre_shared_key "/etc/racoon/psk.txt";
log   debug;

remote ip.vpn.serveru {
    exchange_mode main;
    generate_policy on;
    proposal {
         encryption_algorithm 3des;
         hash_algorithm md5;
         authentication_method pre_shared_key;
         dh_group modp1024;
    }
}

sainfo anonymous {
    encryption_algorithm 3des;
    authentication_algorithm hmac_md5;
    compression_algorithm deflate;
}

Politika

Pravidla, podle kterých se kernel rozhoduje, zda pakety šifrovat, či ne, opět zavedeme pomocí nástroje setkey.

#!/bin/sh
/sbin/setkey -FP
/sbin/setkey -F
/sbin/setkey -c << EOF
spdadd 0.0.0.0/0 ip.vpn.serveru [1701] any -P out ipsec esp/transport//require ;
spdadd ip.vpn.serveru [1701] 0.0.0.0/0 any -P in ipsec esp/transport//require ;
EOF

Konfigurace serveru - l2tpd

V konfiguračním souboru /etc/l2tpd/l2tpd.conf nyní potřebujeme sekci lac. Parametrem lns říkáme, na jaké adrese sedí náš přístupový VPN server.

[global]

[lac vpn]
lns = ip.vpn.serveru
require chap = yes
refuse pap = yes
require authentication = no
name = LinuxVPNserver
ppp debug = yes
pppoptfile = /etc/ppp/options.l2tpd
length bit = yes

V souboru /etc/ppp/options.l2tpd je změn více. Důležité je uvést name, protože tímto říkáme lns, jakým uživatelským jménem se budeme autentizovat.

noauth
name cervajs
crtscts
mtu 1400
mru 1400
defaultroute
debug
noipdefault
local
lock
proxyarp
usepeerdns

Záznam pro toto jméno musíme tedy mít v chap-secrets.

# chap-secrets
# Secrets for authentication using CHAP
# client     server  secret          IP addresses
pepa         *       zdepa             *

Pokud máme konfigurace připraveny, můžeme připojení spustit.

bash# echo "c vpn" > /var/run/l2tp-control

Parametr "c vpn" znamená, že l2tpd má iniciovat spojení (c jako connect) podle sekce lac s názvem "vpn".

L2tpd se pokusí připojit na port 1701 na přístupovém VPN serveru. Protože VPN server má v politice nastaveno, že vše, co jde na port 1701, musí být šifrované, spustí se proces ustanovení šifrovaného IPSec tunelu. Jakmile se podaří tunel sestavit, proběhne již zabezpečeným kanálem autentizace na úrovni l2tp. Klient je připojen, je mu přidělena ip adresa a může vesele firemní poštou posílat hanbaté obrázky a provádět jiné podobné běžné pracovní úkony.

NAT

Jedním z velkých problémů, který ještě není uspokojivě vyřešen, je průchod NATem. Podpora NAT traversal pro transport mód v racoonu zatím není implementována.

Závěrem

Dnes ukázaný scénář je vhodný spíše pro malé sítě a firmy, kde změna sdíleného hesla není problémem. Lepší správu v případě velkého množství klientů nám zabezpečí použití certifikátů. Jakým způsobem nahradit sdílený klíč pomocí certifikátů si ukážeme příště.

Související články

IPSec v kernelu 2.6 - I

Odkazy a zdroje

www.ipsec-howto.org
www.kame.net
Layer 2 Tunnelling Protocol Daemon
Klady a zápory při použití L2TP

Další články z této rubriky

Úvod do Dockeru (1)
Paralelizace běžných činností v konzoli pomocí GNU Parallel
Unixové nástroje – 26 (triky pro práci v Bashi)
Unixové nástroje – 25 ((s,c)fdisk, gdisk, parted a findmnt)
Linux: systémové volání splice()

ISSN 1214-1267, (c) 1999-2007 Stickfish s.r.o.