Linux 2.4 Packet Filtering HOWTO
Rusty Russell, liste d'email netfilter@lists.samba.org
Traduit par Emmanuel Rogerflynux@freegates.be
v1.0.1 Lundi 1er Mai 18:09:31 CST 2000, traduction du 04
septembre 2000
Ce document décrit comment utiliser iptables pour filtrer les mauvais
paquets pour le Noyau Linux 2.4.
______________________________________________________________________
Table des matières
1. Introduction
2. Où se trouvent les site web officiels et la liste de mail ?
3. Donc Qu'est ce Qu'un Filtre à Paquets?
3.1 Pourquoi Voudrais-je Filtrer des Paquets?
3.2 Comment est-ce que je Filtre les Paquets Sous Linux?
3.2.1 iptables
3.2.2 Faire des Règles Permanentes
4. Bon Dieu qui est tu, et pourquoi est ce que tu joues avec mon noyau ?
5. Le Guide Rapide de Rusty sur le Filtrage de Paquets
6. Comment les Paquets Traversent les Filtres
7. Utiliser iptables
7.1 Ce que tu Verras quand ton Ordinateur Démarrera
7.2 Operations sur une Seule Chaine
7.3 Spécifications de filtrage
7.3.1 Specifier les adresses IP source et destination
7.3.2 Spécifier une inversion
7.3.3 Specifier le protocole
7.3.4 Specifier une interface
7.3.5 Specifier des Fragments
7.3.6 Extensions à iptables : Nouvelles Correspondances
7.3.6.1 Extensions TCP
7.3.6.1.1 Une Explication des Drapeaux TCP
7.3.6.2 Extensions UDP
7.3.6.3 Extensions ICMP
7.3.6.4 Autres Extensions de Concordance
7.3.6.5 La Concordance d'Etat
7.4 Specifications de Cibles
7.4.1 Les chaines créées par l'utilisateur
7.4.2 Extensions à iptables : Nouvelles Cibles
7.4.3 Cibles Speciales compilées
7.5 Operations sur une Chaine Entière
7.5.1 Créer une Nouvelle Chaine
7.5.2 Supprimer une Chaine
7.5.3 Vider une Chaine
7.5.4 Lister une Chaine
7.5.5 Resetter (Zeroer) les Compteurs
7.5.6 Configurer la Police
8. Utiliser ipchains et ipfwadm
9. Mixer le NAT et le Filtrage de Paquets
10. Différences entre iptables et ipchains
11. Mise en Garde sur le Filtre de Paquets
______________________________________________________________________
[1m1. Introduction[0m
Bienvenue, gentil lecteur.
Il est supposé que tu sais ce que sont une adresse IP, une adresse
réseau, le routage et le DNS. Sinon, je te recommende de lire le HOWTO
sur les concepts réseaux.
Ce HOWTO voyage entre une gentille introduction (qui vas te laisser
chaud et bien pour l'instant, mais non protégé dans le monde réel) et
des discussions brutales (qui vont laisser tout le monde confu, parano
et en recherche d'armes lourdes, sauf les plus hardis).
Ton réseau n'est pas [1msécurisé[22m. Le problème de permettre des
communications convenables, en les limitant aux bonnes communications,
tandis qu'interdire les mauvaises intentions est semblable à d'autres
problèmes tels que permettre de parler dans un théatre bourré, tandis
qu'on prohibe de crier ``Au Feu!''. Ce type de problème ne sera pas
résolu par ce HOWTO.
Donc toi seul peut décider où le compromis se trouvera. J'essayerai de
t'expliquer l'utilisation de quelques outils disponibles et les
quelques trous de sécurité auxquels il faut faire attention, dans
l'espoir que tu les utiliseras pour le bien, et non à de mauvaises
intentions. Un autre problème du même genre.
(C) 2000 Paul `Rusty' Russell. Sous license GNU GPL.
[1m2. Où se trouvent les site web officiels et la liste de mail ?[0m
Voici les trois sites officiels:
· Merci à Filewatcher .
· Merci à l'équipe de samba et SGI .
· Merci à Harald Welte .
Pour la liste email officielle de netfilter: Liste de netfilter
.
[1m3. Donc Qu'est ce Qu'un Filtre à Paquets?[0m
Un filtre à paquets est un programme qui regarde l'[4men-tète[24m des paquets
qui passent, et décide du sort du paquet entier. Il peut décider de
[1mDROP[22mer le paquet (p.e., faire comme si il n'avait jamais été reçu),
[1mACCEPT [22mle paquet (p.e. le laisser passer), ou quelque chose de plus
compliqué.
Sous Linux, le filtrage de paquets est dans le noyau (comme un module,
ou directement dedans), et il y a un tas de trucs qu'on peut faire
avec les paquets, mais le principe de base qui est de regarder les en-
tètes et de décider du sort du paquet est toujours la.
[1m3.1. Pourquoi Voudrais-je Filtrer des Paquets?[0m
Controle. Securité. Prévention.
[1mControle:[0m
quand tu utilises une machine linux pour connecter ton réseau
interne à un autre réseau (on va dire Internet), tu as la
possibilité de permettre certains types de traffic et de
prohiber d'autres. Par exemple, l'en-tète du paquet contient
l'adresse de destination du paquet, donc tu peux empecher les
paquets d'aller vers une certaine partie du réseau externe.
Comme autre exemple, j'utilise netscape pour accèder à l'archive
de Dilbert. Il y a des pubs de doubleclick.net sur la page, et
netscape perds mon temps à les télécharger. Dire au filtre de
paquets de ne pas permettre de paquets de et vers
doubleclick.net résout ce problème (il y a de meilleures façons
de faire ça : voir Junkbuster).
[1mSecurité:[0m
quand ta machine Linux est la seule chose entre le chaos
d'internet et ton beau réseau bien ordonné, c'est intéressant de
savoir que tu peux limiter ce qui frappe à ta porte. Par
exemple, tu peux permettre à tout de sortir de ton réseau, mais
tu peux être embèté par le bien connu `Ping of Death' venant
d'étrangers malicieux. Comme autre exemple tu ne voudrais pas
qu'un étranger telenette dans ta machine Linux, même si tout tes
comptes ont un mot de passe. Peut être que tu veux (comme la
pluspart des gens) être un observateur sur internet et pas un
serveur (voulu ou pas). Simplement ne laisses personne se
connecter, en utilisant le filtrage de paquets pour rejeter les
paquets entrants qui utilisés pour établir des connections.
[1mPrévention:[0m
Parfois une machine mal configurée sur le reseau local décidera
d'envoyer des paquets au monde extérieur. C'est intéressant de
dire au filtrage de paquets de te dire si quelque chose
d'anormal se produit; peut être veux tu y faire quelque chose ou
peut être est tu curieux par nature.
[1m3.2. Comment est-ce que je Filtre les Paquets Sous Linux?[0m
Les Noyaux Linux ont le filtrage de paquet depuis la série des 1.1.
La première génération, basée sur ipfw de BSD, a été portée par Alan
Cox fin 1994. Ca a été amélioré par Jos Vos et d'autres pour Linux
2.0; le logiciel `ipfwadm' controllait les régles de filtrage du
noyau. A la mi-1998, pour Linux 2.2, j'ai méchamment retravaillé le
noyau, avec l'aide de Michael Neuling, et ai introduit un logiciel
appelé `ipchains'. Finallement, le logiciel de 4ème génération,
`iptables', et une autre réécriture du kernel sont arrivés a la
mi-1999 pour Linux 2.4. C'est cet iptables sur lequel se concentre ce
HOWTO.
Tu as besoin d'un noyau qui a l'infrastructure netfilter en lui :
netfilter est une infrastructure générale dans le noyau sur laquelle
d'autres choses (comme le module iptables) viennent se greffer. ça
veut dire que tu as besoin de Linux 2.3.15 ou plus, et de répondre `Y'
à CONFIG_NETFILTER dans la configuration du noyau.
L'outil iptables parle au noyau et lui dit quels paquets filtrer. A
moins que tu ne sois programmeur ou bien vachement curieux c'est comme
ça que tu vas controller les paquets.
[1m3.2.1. iptables[0m
L'outil iptables insère et retire des règles de la table de filtrage
des paquets du noyau. Ca veut dire que quoi que tu configures, ca sera
perdu au reboot; vois ``Faire des Règles Permanentes'' pour comment
être sûr que tes règles seront restaurées au prochain démarrage.
iptables est un remplacement ipfwadm et ipchains : voir ``Utiliser
ipchains et ipfwadm'' pour comment éviter de peiner sur iptables si tu
utilises un des ces 2 derniers.
[1m3.2.2. Faire des Règles Permanentes[0m
Ta config de firewall courante est stockée dans le noyau, et donc sera
perdue au redémarrage. Ecrire iptables-save et iptables-restore est
dans ma liste de choses à faire. Quand ils existeront ils seront
cools, je le promets.
En attendant, mets les commandes de configuration nécessaires dans un
script d'initialisation. Sois sûr de faire quelque chose d'intelligent
si une des commandes venait à foirer (habituellement `exec
/sbin/sulogin').
[1m4. Bon Dieu qui est tu, et pourquoi est ce que tu joues avec mon[0m
[1mnoyau ?[0m
Je suis Rusty; le mainteneur du Firewall IP pour Linux et juste un
autre codeur qui se trouvait à la bonne place au bon moment. J'ai
écrit ipchains (voir ``Comment est-ce que je Filtre les Paquets Sous
Linux?'' au dessus pour les crédits dus aux gens qui ont fait le
travail actuel), et ai appris assez pour faire le filtrage de paquets
convenablement cette fois. J'espère.
WatchGuard , une entreprise de firewalls
excellente qui vends le Firebox, m'a offert de ne rien faire, comme ça
je peux passer mon temps à écrire ce truc, et maintenir mes trucs
précédents. J'avais prédit 6 mois, et ça en a pris 12, mais je pense
que cette fois ça a été bien fait. Beaucoup de réécritures, un crash-
disque, un portable volé, quelques systèmes de fichiers corrompus, et
un écran cassé plus tard, voila ce que ça donne.
Tant que je suis ici, je voudrais mettre au clair quelques points : je
ne suis pas un gourou du noyau. Je le sais, parce que mon travail sur
le noyau m'a mis en contact avec quelques uns : David S. Miller,
Alexey Kuznetsov, Andi Kleen, Alan Cox. De toutes façons ils sont tous
occupés à faire de la magie en profondeur, me laissant ici plus haut,
là où c'est sécurisé.
[1m5. Le Guide Rapide de Rusty sur le Filtrage de Paquets[0m
La pluspart des gens ont juste une simple connection PPP à internet,
et ne veulent pas que quelqu'un rentre dans leur réseau, ou leur
firewall:
## Insèrer les modules de suivi de connection (pas nécessaire si compilé dans le noyau).
# insmod ip_conntrack
# insmod ip_conntrack_ftp
## Créer une chaine qui bloque les nouvelles connections à part celles qui viennent de l'intérieur.
# iptables -N block
# iptables -A block -m state --state ESTABLISHED,RELATED -j ACCEPT
# iptables -A block -m state --state NEW -i ! ppp0 -j ACCEPT
# iptables -A block -j DROP
## Sauter sur cette chaine à partir des chaines INPUT et FORWARD.
# iptables -A INPUT -j block
# iptables -A FORWARD -j block
[1m6. Comment les Paquets Traversent les Filtres[0m
Le noyeau contient à la base trois listes de règles dans la table
`filter'; ces listes sont appelées [1mchaines de firewall [22mou juste
[1mchaines[22m. Les trois chaines sont appelées [1mINPUT[22m, [1mOUTPUT [22met [1mFORWARD[22m.
[1mC'est vraiment différent de comment les noyeaux 2.0 et 2.2[0m
[1mfonctionnaient![0m
Pour les fans de l'art ASCII, les chaines sont arrangées comme suit:
_____
Entrée / \ Sortie
-->[Décision]--->|FORWARD|------->
[de routage] \_____/ ^
| |
v ____
___ / \
/ \ |OUTPUT|
|INPUT| \____/
\___/ ^
| |
---->Processus local ----
Les trois cercles représentent les trois chaines mentionnées ci-
dessus. Quand un paquet arrives au cercle dans le diagramme, cette
chaine est examinée pour decider du sort du paquet. Si la chaine dit
de DROP le paquet il est tué ici, mais si la chaine dit ACCEPT le
paquet, il continue sa traversée du diagramme.
Une chaine est un checklist de [1mrègles[22m. Chaque règle dit `si l'en-tète
du paquet est comme ca, voila quoi faire avec le paquet'. Si la règle
ne convient pas au paquet, alors la règle suivante est examinée.
Finallement si il ne reste plus de chaines à examiner, le noyau
regarde [1mla règle par défaut [22mde la chaine pour décider quoi faire. Dans
un système conscienscieux de la sécurité, cette règle par défaut dit
de DROPer le paquet.
1. Quand un paquet arrives (on va dire par la carte Ethernet) le noyau
regarde en premier la destination de ce paquet : c'est appelé le
`routage'.
2. Si c'est destiné à cette machine, le paquet passe vers le bas dans
le diagramme, vers la chaine INPUT. Si il la passe, les processus
qui attendent le paquet le recevront.
3. Autrement, si le noyau n'a pas le forwarding autorisé, ou qu'il ne
sait pas comment forwarder le paquet, le paquet est tué. Si le
forwarding est autorisé, et que le paquet est destiné à une autre
interface réseau (si tu en as une autre), le paquet va directement
à la chaine FORWARD dans le diagramme. Si il est ACCEPTé, il sera
envoyé.
4. Finallement, un programme qui tourne sur la machine peut envoyer
des paquets. Ces paquets passeront par la chaine OUTPUT
immédiatement : si elle dit ACCEPT, alors le paquet continue vers
l'interface à laquelle il est destiné.
[1m7. Utiliser iptables[0m
iptables a une page de manuel bien détaillée (man iptables), si tu
veux des détails en particulier. Si tu es familier avec ipchains tu
devrais simplement regarder ``Différences entre iptables et
ipchains''; ils sont vraiment similaires.
Il y a plusieurs choses que tu peux faire avec iptables. Tu commences
avec trois chaines de départ INPUT, OUTPUT et FORWARD que tu ne peux
pas effacer. Regardons les opérations pour administrer les chaines :
1. Créer une nouvelle chaine (-N).
2. Effacer une chaine vide (-X).
3. Changer la règle par défaut pour une chaine de départ (-P).
4. Lister les règles dans une chaine (-L).
5. Retirer les règles d'une chaine (-F).
6. Mettre à zero les compteurs de bits et de paquets d'une chaine
(-Z).
Il y a plusieurs manières de manipuler une règles dans une chaine :
1. Ajouter une nouvelle règle à la chaine (-A).
2. Insérer une nouvelle règle à une position dans la chaine (-I).
3. Remplacer une règle à une position dans la chaine (-R).
4. Supprimer une règle à une position dans la chaine (-D).
5. Supprimer la première règle qui convient dans une chaine (-D).
[1m7.1. Ce que tu Verras quand ton Ordinateur Démarrera[0m
iptables peut être un module, appelé (`iptable_filter.o'), qui devrait
être automatiquement chargé quand tu lances iptables. Il peut aussi
être compilé dans le noyau.
Avant qu'aucune commande n'ait été effectuée, (attention : certaines
distributions lanceront iptables dans leurs scripts d'initialisation),
il n'y a pas de règles dans aucune des chaines par défaut (`INPUT',
`FORWARD' et `OUTPUT'), toutes les chaines ont une règle par défaut de
ACCEPT. Tu peux changer la règle par defaut de la chaine FORWARD en
specifiant l'option `forward=0' au module iptable_filter.
[1m7.2. Operations sur une Seule Chaine[0m
C'est le pain et le beurre du filtrage de paquets; manipuler des
règles. plus communément, tu utiliseras probablement les commandes
d'ajout (-A) et d'effacement (-D). Les autres (-I pour insérer et -R
pour remplacer) sont de simples extensions de ces concepts.
Chaque règle spécifie des conditions que le paquet doit remplir, et
que faire si le paquet les remplis (une `cible'). Par exemple, tu
voudrais laisser tomber tous les paquets ICMP qui viennent de
l'adresse IP 127.0.0.1. Donc dans ce cas les conditions sont que le
protocole soit icmp et que l'adresse source soit 127.0.0.1. Notre
cible est `DROP'.
127.0.0.1 est l'interface `loopback', que tu auras même si tu n'as pas
de connection réseau réelle. Tu peux utiliser la commande `ping' pour
generer de tels paquets (elle envoie simplement un ICMP de type 8
(echo request) auquel tout les hôtes devraient répondre avec un icmp
de type 0 (echo reply)). Cela est utile pour tester.
# ping -c 1 127.0.0.1
PING 127.0.0.1 (127.0.0.1): 56 data bytes
64 bytes from 127.0.0.1: icmp_seq=0 ttl=64 time=0.2 ms
--- 127.0.0.1 ping statistics ---
1 packets transmitted, 1 packets received, 0% packet loss
round-trip min/avg/max = 0.2/0.2/0.2 ms
# iptables -A INPUT -s 127.0.0.1 -p icmp -j DROP
# ping -c 1 127.0.0.1
PING 127.0.0.1 (127.0.0.1): 56 data bytes
--- 127.0.0.1 ping statistics ---
1 packets transmitted, 0 packets received, 100% packet loss
#
Tu peux voir que le 1er ping a fonctionné (le `-c 1' dit à ping de
n'envoyer qu'un seul paquet).
Ensuite nous ajoutons (-A) à la chaine `INPUT', une règle spécifiant
que pour les paquets venant de 127.0.0.1 (`-s 127.0.0.1') avec le
protocole ICMP (`-p icmp') nous devons sauter vers la cible DROP (`-j
DROP').
Ensuite nous testons notre règle, en utilisant le second ping. Il y
aura une pause avant que le programme ne stoppe parce qu'il attendra
une réponse qui ne viendra jamais.
Nous pouvons effacer une règle de deux façons. Premièrement, comme
nous savons que c'est la seule règle dans la chaine INPUT, on peut
utiliser un effacement avec le nombre, comme:
# iptables -D INPUT 1
#
Pour effacer la règle numéro 1 dans la chaine INPUT.
La seconde façon est un miroir de la commande -A, remplacer -A par -D.
C'est utile quand tu as une chaine complexe et que tu ne veux pas les
compter pour trouver que c'est la règle 37 que tu veux effacer. Dans
ce cas , on utiliserait:
# iptables -D INPUT -s 127.0.0.1 -p icmp -j DROP
#
La syntaxe de la commande -D doit avoir exactement les mêmes options
que celles de -A (ou -I ou -R). Si il y a plusieurs règles identiques
dans la même chaine, la première seulement sera effacée.
[1m7.3. Spécifications de filtrage[0m
Nous avons vu l'utilisation de `-p' pour specifier le protocole, et de
`-s' pour specifier la source, mais il y a d'autres options que tu
peux utiliser pour specifier les caractéristiques d'un paquet. Ce qui
suit est une liste exhaustive.
[1m7.3.1. Specifier les adresses IP source et destination[0m
Les adresses IP source (`-s', `--source' ou `--src') et destination
(`-d',`--destination' ou `--dst') peuvent être specifiées de 4 façons.
La façon la plus commune est d'utiliser le nom complet, comme
`localhost' ou `www.linuxhq.com'. La seconde façon est de specifier
l'adresse IP comme `127.0.0.1'.
Les troisièmes et quatrièmes façons permettent de specifier un groupe
d'IPs, comme `199.95.207.0/24' ou `199.95.207.0/255.255.255.0'. Elles
specifient toutes deux les adresses de 199.95.207.0 à 199.95.207.255
inclus; les nombres après le `/' disent quelle partie des adresses IP
a de la signification. `/32' ou `/255.255.255.255' est le défaut
(correspond à toutes les adresses IP). Pour specifier toutes les
adresses IP `/0' peut être utilisé, comme dans :
[ NOTE: `-s 0/0' is redundant here. ]
# iptables -A INPUT -s 0/0 -j DROP
#
C'est rarement utilisé, comme l'effet ci dessus est le même que de ne
pas specifier l'option `-s' du tout.
[1m7.3.2. Spécifier une inversion[0m
Beaucoup d'options comme `-s' (ou `--source' ) et `-d'
(`--destination') peuvent avoir leurs arguments précédés de `!'
(pronnoncé `NOT') pour correspondre aux adresses PAS égales à celles
données. Par exemple `-s ! localhost' correspond à tout paquet qui ne
vient [1mpas [22mde localhost.
[1m7.3.3. Specifier le protocole[0m
Le protocole peut être spécifié avec `-p' ( ou `--protocol'). Le
protocole peut être un nombre (si tu connais les valeurs numériques de
protocole IP) ou un nom pour les cas spéciaux `TCP', `UDP' ou `ICMP'.
La casse n'a pas d'importance, `tcp' marche aussi bien que `TCP'.
Le nom du protocole peut être préfixé d'un `!', pour l'inverser, comme
`-p ! TCP' pour specifier les paquets qui ne sont [1mpas [22mTCP.
[1m7.3.4. Specifier une interface[0m
Les options `-i' (ou `--in-interface') et `-o' (ou `--out-interface')
spécifient le nom d'une [1minterface [22mà laquelle le paquet doit
correspondre. Une interface est l'appareil physique par lequel le
paquet arrive (`-i') ou sort (`-o'). Tu peux utiliser ifconfig pour
voir les interfaces qui sont `up' (p.e., qui fonctionnent pour le
moment).
Les paquets qui traversent la chaine INPUT n'ont pas encore
d'interface de sortie donc, une règle utilisant `-o' dans cette chaine
ne conviendra pas; les paquets traversant la chaine OUTPUT n'ont pas
d'interface d'entrée, donc toute règle utilisant `-i' dans cette
chaine ne correspondra jamais.
Seuls les paquets traversant la chaine FORWARD on une interface
d'entrée et de sortie.
Il est parfaitement légal de specifier une interface qui n'existe pas;
la règle ne conviendra pas jusqu'à ce que l'interface soit `up'.
C'est vraiment utile pour les lignes PPP (habituellement l'interface
ppp0) et ses semblables.
Un cas special est un nom d'interface se terminant par `+' qui
conviendra a toutes les interfaces (qui existent déja ou pas) qui
commencent par ces lettres. Par exemple, pour specifier une règle qui
convient à toutes les interfaces PPP, on utilisera l'ioption -i ppp+.
Le nom de l'interface peut être précédé par un `!' pour convenir à un
paquet qui n'appartient [1mpas [22mà l'interface spécifiée.
[1m7.3.5. Specifier des Fragments[0m
Parfois un paquet est trop large pour rentrer dans la ligne de
transmission (NdT: oui, je sais les traductions sont parfois
foireuses). Quand ça arrive, le paquet est divisé en [1mfragments[22m, et
envoyé comme de multiples paquets. Le récepteur réassemble ces
fragments pour reconstruire le paquet entier.
Le problème avec les fragments c'est que le fragment initial a son en-
tète complète (IP + TCP, UDP et ICMP) à examiner mais que les paquets
suivants ont seulement quelques morceaux de l'en-tète (IP sans les
champs de protocole). Donc regarder à l'intérieur des fragments
suivants à la recherche d'en-tètes de protocoles (comme c'est fait
pour les extensions TCP, UDP et ICMP) n'est pas possible.
Si tu utilises le suivi de connection ou le NAT, alors tout les
fragments seront recollés avant qu'ils n'arrivent au code de filtrage
de paquets, donc tu n'auras pas à t'occuper des fragments.
Autrement il est important de comprendre comment les fragments sont
traités par les règles de filtrage. Toute règle de filtrage qui
demande des infomations qu'on a pas ne conviendra [4mpas[24m. Ca veut dire
que le premier fragment est traité comme tout autre paquet, mais que
le second et suivants ne le seront pas. Donc une règle -p TCP --sport
www (qui specifie le port source `www') ne conviendra jamais à un
fragment (autre que le premier fragment). L'opposé est aussi valable
-p TCP --sport ! www.
Sinon, tu peux specifier une règle pour les seconds fragments et
suivants, en utilisant l'option `-f' (ou `--fragment'). Il est aussi
légal de spécifier une règle qui ne s'applique [4mpas[24m aux secondes
fragments et suivants, en précédant `-f' avec `!'.
Habituellement il est sécurisant de laisser passer les seconds
fragments et suivants, comme le filtrage sera fait sur le premier, et
empèchera le réassemblement sur la machine cible; mais des bugs ont
été trouvés qui permettent de crasher la machine simplement en lui
envoyant des fragments.
Note: les paquets malformés (TCP, UDP et ICMP qui sont trop courts
pour que le code de firewalling lise les ports ou le code ICMP et le
type) sont DROPer quand de telles combinaisons sont tentées, comme les
fragments TCP qui commencent à la position 8.
Comme exemple, la règle suivante va laisser tomber tout les fragments
qui vont vers 192.168.1.1 :
# iptables -A OUTPUT -f -d 192.168.1.1 -j DROP
#
[1m7.3.6. Extensions à iptables : Nouvelles Correspondances[0m
iptables est [1mextensible[22m, ce qui veut dire que le noyau et le programme
iptables peuvent être étendus pour avoir de nouvelles capacités.
Quelques unes de ces extensions sont standard, et d'autres sont plus
exotiques. Elles peuvent être créées par d'autres personnes et
distribuées séparément aux utilisateurs.
Les extensions au noyau sont normalement situées dans le répretoire
des modules du kernel comme /lib/modules/2.3.15/net. Elles sont
chargées a la demande si ton kernel a été compilé avec CONFIG_KMOD,
donc tu n'as pas besion de les insérer à la main.
Les extensions au programme iptables sont des librairies partagées
qui sont generallement situées dans /usr/local/lib/iptables/, bien
qu'une distribution puisse les mettre dans /lib/iptables ou
/usr/lib/iptables.
Les extensions sont de deux types : nouvelles correspondances et
nouvelles cibles (nous parlerons des nouvelles cibles plus tard).
Quelques protocoles offrent aussi de nouveaux tests : pour le moment
TCP, UDP et ICMP.
Pour ceux-ci tu pourras specifier les nouveaux tests sur la ligne de
commande après l'option `-p', qui va charger l'extension. Pour
specifier de nouveaux tests, utilises l'option `-m' pour charger
l'extension, après quoi l'extension est disponible.
Pour obtenir de l'aide sur une extension, utilises l'option pour la
charger (`-p', `-j' ou `-m') suivi de `-h' ou `--help', p.e.:
# iptables -p tcp --help
#
[1m7.3.6.1. Extensions TCP[0m
Les extensions TCP sont automatiquement chagées si `-p tcp' est
spécifié. Elles permettent les options suivantes (aucune d'entre
elles ne convient aux fragments).
[1m--tcp-flags[0m
Suivi d'un `!' optionnel, ensuite 2 chaines de caractères de
drapeaux, te permet de filtrer des drapeaux TCP spécifiques. La
première chaine de drapeaux est le masque : une liste de
drapeaux que tu veux examiner. La deuxième chaine de drapeaux
dit lequel doit être présent. Par exemple:
# iptables -A INPUT --protocol tcp --tcp-flags ALL SYN,ACK -j DENY
Ceci indique que tous les drapeaux doivent être examinés (`ALL' est
ynonyme de `SYN,ACK,FIN,RST,URG,PSH'), mais seulement SYN et ACK
doivent être présents. Il y a aussi l'argument `NONE' qui veut dire
pas de drapeaux.
[1m--syn[0m
Précédé optionnelement d'un `!', c'est une raccourci pour
`--tcp-flags SYN,RST,ACK SYN'.
[1m--source-port[0m
suivi d'un `!' optionnel, ensuite soit un port TCP seul, ou un
bloc de ports. Les ports peuvent être des noms de ports, listés
dans `/etc/services', ou des nombres. Les blocs sont soit 2 noms
de ports séparés par `:', ou (pour specifier plus grand que ou
égal a) un port avec un `:' ajouté, ou (pour specifier plus
petit que ou égal a) un port précédé de `:'.
[1m--sport[0m
est synonime de `--source-port'.
[1m--destination-port[0m
et
[1m--dport[0m
sont les mêmes qu'au dessus, ils spécifient juste la destination
plutôt que la source qui convient.
[1m--tcp-option[0m
suivi d'un `!' optionnel ou d'un nombre, convient à un paquet
qui a une option TCP qui équivaut à ce nombre. Un paquet qui
n'a pas une en-tète TCP complète est laissé tombé
automatiquement si un essai est fait pour examiner ses options
TCP.
[1m7.3.6.1.1. Une Explication des Drapeaux TCP[0m
Il est parfois utile d'autoriser les connections TCP dans un sens mais
pas dans l'autre. Par exemple, tu pourrais vouloir autoriser les
connections vers un serveur WWW externe, mais pas les connections à
partir de ce serveur.
L'approche naive serait de bloquer les paquets TCP venant du serveur.
Malheureusement, les connections TCP on besion d'avoir des paquets qui
vont dans les deux sens pour fonctionner.
La solution est de bloquer seulement les paquets qui sont utilisés
pour demander une connection. Ces paquets sont appelés des paquets [1mSYN[0m
(ok, techniquement ce sont des paquets avec le drapeux SYN et pas de
drapeaux FIN et ACK, mais nous les appelons paquets SYN pour faire
plus court). En déniant seulement ces paquets, nous pouvons stopper
les tentatives de connections.
Le drappeau `--syn' est utilisé pour cela : il est seulement valide
pour les règles qui spécifient TCP comme protocole. Par exemple, pour
specifier un essai de connection de la part de 192.168.1.1 :
-p TCP -s 192.168.1.1 --syn
Ce drapeau peut être spécifié en le précédant de `!', qui veut dire
tout les paquets sauf ceux d'initiation de connection.
[1m7.3.6.2. Extensions UDP[0m
Ces extensions sont automatiquements chargées si `-p udp' est
spécifié. Elles donnent les options `--source-port', `--sport',
`--destination-port' et `--dport' comme détaillé pour le tcp ci-
dessus.
[1m7.3.6.3. Extensions ICMP[0m
Ces extensions sont automatiquements chargées si `-p icmp' est
spécifié. Elles donnent seulement une seule nouvelle option :
[1m--icmp-type[0m
suivi d'un `!' optionnel, et ensuite un nom de type icmp (pe.
`host-unreachable'), ou un type numérique (p.e. `3'), ou un type
et un code numérique séparés par un `/' (p.e. `3/3'). Une liste
de types icmp disponibles est donnée en utilisant `-p icmp
--help'.
[1m7.3.6.4. Autres Extensions de Concordance[0m
Les autres extensions dans le package netfilter sont des extensions de
démonstration, qui (si installées) peuvent être invoquées avec
l'option `-m'.
[1mmac[0m
Ce module doit être spécifié explicitement avec `-m mac' ou
`--match mac'. Il est utilisé pour concorder à des adresses
Ethernet (MAC) de paquets qui arrivent, et est seulement utile
pour convenir avec des paquets traversant les chaines INPUT et
PREROUTING. Il donne une seule option:
[1m--mac-source[0m
suivi d'un `!' optionnel, ensuite une adresse ethernet en
notation hexa séparée par `:', pe `--mac-source
00:60:08:91:CC:B7'.
[1mlimit[0m
Ce module doit être spécifié explicitement avec `-m limit' ou
`--match limit'. Il est utilisé pour limiter la vitesse de
concordance, comme pour specifier des messages de log. Il
conviendra seulement à un certain nombre de fois pas seconde (
par défaut 3 concordances par heure, avec une réserve de 5). Il
prends deux arguments optionnels:
[1m--limit[0m
suivi d'un nombre; spécifie le nombre maximum de concordances
allouées par seconde. Le nombre peut specifier les unités
explicitement, en utilisant `/second', `/minute', `/hour' ou
`/day', ou une partie (donc `5/second' est le même que
`5/s').
[1m--limit-burst[0m
suivi d'un nombre, inndique la réserve maximale avant
d'atteindre la limite ci-dessus.
Cette concordance peut souvent être utilisée avec la cible LOG
pour effectuer du logging limité en débit. Pour comprendre
comment cela fonctionne on va regarder à la règle suivante, qui
logue les paquets avec les paramètres de limite par défaut:
# iptables -A FORWARD -m limit -j LOG
La première fois que cette règle est atteinte, le paquet sera
logué; en fait comme la réserve est de 5, les 5 premiers paquets
seront logués. Après cela, 20 minutes passeront avant qu'un paquet
ne soit logué par cette règle, sans tenir compte du nombre de
paquets qui l'atteignent. Aussi, chaque 20 minutes qui passent
sans concorder avec un paquet, un paquet de la réserve sera
regagné; si aucun paquet n'atteint la règle pendant 100 minutes, la
réserve sera complètement rechargée; on est revenu au point de
départ.
Note : tu ne peux pas créer de règle avec un temps de recharge de
plus de 59 heures, donc si tu configures un débit moyen de 1 par
jour, alors le débit de réserve doit être inférieur à 3.
Tu peux aussi utiliser ce module pour eviter les déniement de
service (DoS) avec un débit supérieur pour augmenter la vitesse de
réaction.
Protection syn-flood:
# iptables -A FORWARD -p tcp --syn -m limit --limit 1/s -j ACCEPT
Test de ports furtif:
# iptables -A FORWARD -p tcp --tcp-flags SYN,ACK,FIN,RST RST -m limit --limit 1/s -j ACCEPT
Ping de la mort:
# iptables -A FORWARD -p icmp --icmp-type echo-request -m limit --limit 1/s -j ACCEPT
Ce module fonctionne comme "une porte à hystérésis", comme montré
dans le graphe qui suit.
débit (pkt/s)
^ .---.
| / DoS \
| / \
limite de DoS -|.....:.........\.......................
= (limit * | /: \
limit-reserve) | / : \ .-.
| / : \ / \
| / : \ / \
Fin de DoS -|/....:..............:.../.......\..../.
= limite | : :`-' `--'
-------------+-----+--------------+------------------> temps (s)
LOGIQUE =>concord.| pas concord. | concord.
On dit un paquet par seconde avec une réserve de 5 paquets mais,
les paquets commences à arriver à 4/s pendant 3 secondes puis
recommencent après 3 autres secondes
<--Flood 1--> <---Flood 2--->
Total ^ Ligne __-- YNNN
Paquets| Débit __-- YNNN
| mum __-- YNNN
10 | Maxi __-- Y
| __-- Y
| __-- Y
| __-- YNNN
|- YNNN
5 | Y
| Y Key: Y -> Règle concorde
| Y N -> Règle concorde pas
| Y
|Y
0 +--------------------------------------------------> Temps (secondes)
0 1 2 3 4 5 6 7 8 9 10 11 12
Tu peux voir que les 5 premiers paquets sont autorisés à depasser
la limite de un paquet par seconde, ensuite la limite entre en jeu.
Si il y a une pause, un autre bloc est autorisé, mais pas au dessus
de la limite maximum configurée par la règle (1 paquet par seconde
après que la première réserve soit usée).
[1mowner[0m
Ce module essaye de concorder les caractéristiques variées du
créateur du paquet, pour les paquets générés locallement. Il est
seulement valide pour la chaine OUTPUT, et même comme cela,
certains paquets (comme les réponses de ping ICMP) n'auront pas
de possesseur, et donc ne concorderont jamais.
[1m--uid-owner userid[0m
Concorde si le paquet a été créé par un processus qui a le
user id effectif (numérique) donné.
[1m--uid-owner groupid[0m
Concorde si le paquet a été créé par un processus qui a le
group id effectif (numérique) donné.
[1m--pid-owner processid[0m
Concorde si le paquet a été créé par un processus qui a le
process donné.
[1m--sid-owner sessionid[0m
Concorde si le paquet a été créé par un processus qui a le
groupe de session donné.
[1munclean[0m
Ce module expérimental doit être spécifié explicitement avec `-m
unclean ou `--match unclean'. Il effectue des vérifications
sanitaires aléatoires et variées sur les paquets. Ce module n'a
pas été testé, et ne devrait pas être utilisé comme une fonction
de sécurité (il rend peut-ètre les choses plus mauvaises si il a
des bugs lui-mème). Il n'a pas d'options.
[1m7.3.6.5. La Concordance d'Etat[0m
Le critère le plus utile est fourni par l'extension `state' qui
interprète l'analyse de suivi de connection du module `ip_conntrack'.
Il est fortement recommendé.
Specifier `-m state' permet une option additionelle `--state', qui est
une liste séparée par des virgules d'états qui conviennent ( les `!'
indiquent les états qui ne conviennent [1mpas[22m. Ces états sont:
[1mNEW[0m
Un paquet qui engendre une nouvelle connection.
[1mESTABLISHED[0m
Un paquet qui appartient à une connection existante (p.e., une
qui a eu des paquets de réponse).
[1mRELATED[0m
Un paquet qui est relaté a, mais pas partie de, une connection
existante, comme une erreur ICMP, ou ( avec le module ftp
chargé), un paquet qui etablit une connection de données ftp.
[1mINVALID[0m
Un paquet qui ne peut pas être identifié pour n'importe quelle
raison : ceci inclus le manque de mémoire et les erreurs icmp
qui ne correspondent à aucune connection connue. Générallement,
ces paquets doivent être laissé tombés.
[1m7.4. Specifications de Cibles[0m
Maintenant nous connaissons les examens que nous pouvons faire sur un
paquet, nous avons besoin de trouver une façon de dire quoi faire de
ces paquets qui correspondent à nos tests. Ceci est appelé la [1mcible[0m
d'une règle.
Il y a deux cibles simples compilées : DROP et ACCEPT. Nous les avons
déja rencontrées. Si une règle correspond à un paquet et que la cible
est une de celles ci, les règles suivantes ne sont pas consultées : le
sort du paquet a été décidé.
Il y a deux autres types de cibles que celles qui sont compilées : les
extensions et les chaines créées par l'utilisateur.
[1m7.4.1. Les chaines créées par l'utilisateur[0m
Une propriété puissante que iptables hérite de ipchains est la
possibilité pour l'utilisateur de créer de nouvelles chaines, en
addition a celles qui existent déja (INPUT, FORWARD et OUTPUT). Par
convention les chaines utilisateur sont en minuscule pour les
distinguer, nous décrirons comment créer des chaines utilisateur dans
``Opérations sur une Chaine Entière'' ci-dessous).
Quand un paquet concorde à une règle dont la cible est une chaine
utilisateur, le paquet commence à traverser les règles dans la chaine
utilisateur. Si cette chaine ne décide pas du sort du paquet, alors
une fois que la traversée de cette chaine est terminée, la traversée
reprend sur la règle suivante de la chaine courante.
Il est temps pour un peu plus d'art ASCII. Considérons deux chaines:
INPUT (la chaine par defaut) et test (une chaine utilisateur).
`INPUT' `test'
---------------------------- ----------------------------
| Règle1: -p ICMP -j DROP | | Règle1: -s 192.168.1.1 |
|--------------------------| |--------------------------|
| Règle2: -p TCP -j test | | Règle2: -d 192.168.1.1 |
|--------------------------| ----------------------------
| Règle3: -p UDP -j DROP |
----------------------------
Considérons un paquet TCP venant de 192.168.1.1, allant à 1.2.3.4. Il
entre dans la chaine INPUT, et est testé par la règle1 - pas de
concordance. La règle2 concorde et sa cible est test, donc la règle
suivante examinée est le debut de la chaine test. La règle1 de test
concorde mais ne spécifie pas de cible, donc la règle suivante est
examinée, la règle2. Ca ne concorde pas, nous avons atteint la fin de
la chaine test. Nous retournons à la chaine INPUT ou nous venons
d'examiner la règle2, donc nous examinons la règle3, qui ne concorde
pas d'avantage.
Donc la traversée du paquet est:
v __________________________
`INPUT' | / `test' v
------------------------|--/ -----------------------|----
| Règle1 | /| | Règle1 | |
|-----------------------|/-| |----------------------|---|
| Règle2 / | | Règle2 | |
|--------------------------| -----------------------v----
| Règle3 /--+___________________________/
------------------------|---
v
Les chaines utilisateurs peuvent sauter dans d'autres chaines
utilisateur (mais ne fais pas de boucles : tes paquets seront laissés
tomber si ils sont dans une boucle).
[1m7.4.2. Extensions à iptables : Nouvelles Cibles[0m
L'autre type de cible est une extension. Une extension de cible
consiste en un module du noyau, et une extension optionnele à iptables
pour permettre de nouvelles options sur la ligne de commande. Il y a
plusieurs extensions dans la distribution netfilter :
[1mLOG[0m
Ce module permet de logger les paquets qui concordent. Il donne
plusieurs options additionelles:
[1m--log-level[0m
Suivi d'un nombre de niveau ou d'un nom. Les noms valides
sont (non sensible à la casse) `debug', `info', `notice',
`warning', `err', `crit', `alert' and `emerg', correspondent
aux nombres 7 à 0. Voir la page de manuel de syslog.conf
pour une explication de ces niveaux.
[1m--log-prefix[0m
Suivi d'une chaine de 29 caractères maximum, ce message est
envoyé au début du message de log, pour lui permettre d'être
identifié uniquement.
Ce module est le plus utile après une concordance limit, pour ne
pas saturer les logs.
[1mREJECT[0m
Ce module a les mèmes effets que `DROP', excepté que l'envoyeur
reçoit un message d'erreur ICMP `port unreachable'. Notes que
le message d'erreur ICMP n'est pas envoyé si (voir RFC 1122):
· Le paquet filtré etait un message d'erreur ICMP, ou un type
ICMP inconnu.
· Le paquet filtré est un fragment sans en-tète.
· Nous avons envoyé trop de messages d'erreur ICMP à cette
destination récemment.
REJECT peut aussi prendre une option `--reject-with' qui altère
le type du paquet de réponse utilisé : voir la page de manuel.
[1m7.4.3. Cibles Speciales compilées[0m
Il y a 2 cibles speciales compilées: RETURN et QUEUE.
RETURN a le même effet que de tomber à la fin d'une chaine : pour une
règle dans une chaine compilée, la police de la chaine est exécutée.
Pour une règle dans une chaine utilisateur, la traversée continue dans
la chaine précédente, juste après la règle qui a sauté sur cette
chaine.
QUEUE est une cible spéciale, met les paquets en queue pour les
traiter en espace utilisateur. Pour que ça soit utile, deux composants
supplémentaires sont requis:
· un "arbitre de queue", qui utilise les mécanismes du noyau pour
passer les paquets entre le noyau et l'espace utilisateur; et
· une application utilisateur pour recevoir, peut être manipuler, et
donner un verdict sur les paquets.
L'arbitre de queue standard IPV4 pour iptables est le module
ip_queue, qui est distribué avec le noyau et marqué comme
expérimental.
Ce qui suit est un exemple rapide de comment utiliser iptables pour
mettre des paquets en queue pour les traiter en espace utilisateur:
# modprobe iptable_filter
# modprobe ip_queue
# iptables -A OUTPUT -p icmp -j QUEUE
Avec cette règle, les paquets ICMP sortants générés locallement (comme
créés par exemple avec ping) sont passés au module ip_queue, qui
ensuite essaye de délivrer les paquets à une application utilisateur.
Si aucune application n'est là pour prendre les paquets, ils sont
laissés tomber.
Pour écrire une application utilisateur, utilises l'API libipq. Elle
est distribuée avec iptables. du code d'exemple peut être trouvé avec
les outils de la suite de tests (p.e. redirect.c) en CVS.
Le status de ip_queue peut être vérifié via :
/proc/net/ip_queue
La longueur maximale de la queue (le nombre de paquets délivrés à
l'espace utilisateur sans verdict retourné) peut être controllé via :
/proc/sys/net/ipv4/ip_queue_maxlen
La valeur par défaut de la longueur maximum de la queue est 1024. Une
fois que cette limite est atteinte, les nouveaux paquets seront
laissés tomber jusqu'a ce que la longueur de la queue tombe en dessous
de la limite. Les protocoles bien faits comme le TCP interprètent les
paquets laissés tombés comme une congestion, et réagiront positivement
lorsque la queue se remplit. De toutes façons, des expériences
doivent être faites pour determiner la longueur de queue maximale pour
une situation donnée si la valeur par défaut est trop petite.
[1m7.5. Operations sur une Chaine Entière[0m
Une propriété utile de iptables est la possibilité de groupper des
règles dans des chaines. Tu peux appeler les chaines comme tu veux,
mais je recommende les minuscules pour éviter la confusion avec les
chaines compilées et les cibles. les noms de chaines peuvent être de
31 caractères maximum.
[1m7.5.1. Créer une Nouvelle Chaine[0m
Créons une nouvelle chaine. Parce que je suis imaginatif je
l'appelerai test. Nous utilisons l'option `-N' ou `--new-chain':
# iptables -N test
#
C'est aussi simple que ça. Maintenant tu peux mettre des règles dedans
comme détaillé au dessus.
[1m7.5.2. Supprimer une Chaine[0m
Effacer une chaine est simple aussi, en utilisant l'option `-X' ou
`--delete-chain'. Pourquoi `-X'? Ben, toutes les bonnes règles
étaient prises.
# iptables -X test
#
Il y a quelques restrictions pour effacer une chaine : elles doit être
vide (voir ``Vider une Chaine'' dessous) et elle ne doit pas être la
cible d'une table. Tu ne peux pas effacer une des chaines compilées.
Si tu ne spécifie pas de chaine, [4mtoutes[24m les chaines utilisateur seront
effacées, si possible.
[1m7.5.3. Vider une Chaine[0m
Il y a une façon simple d'effacer toutes les règles d'une chaine, en
utilisant la commande `-F' (or `--flush').
# iptables -F FORWARD
#
Si tu ne spécifie pas de chaine, alors [4mtoutes[24m les chaines seront
vidées.
[1m7.5.4. Lister une Chaine[0m
Tu peux lister toutes les règles d'une chaine en utilisant la commande
`-L' (or `--list').
Le `refcnt' listé pour chaque chaine utilisateur est le nombre de
règles qui ont cette chaine pour cible. Il doit être à zero (et la
chaine doit être vide) avant que cette chaine soit effacée.
Si le nom de la chaine est omis, toutes les chaines sont listées, mème
les chaines vides.
Il y a trois options qui peuvent accompagner `-L'. Le `-n' (numérique)
qui est vraiment utile car il évite à iptables d'essayer de résoudre
les adresses IP, qui (si tu utilises des DNS comme la pluspart des
gens) causera de larges délais si ton DNS n'est pas configuré
convenablement, ou tu as filtré les requètes DNS. Il cause aussi les
ports TCP et UDP au lieu d'être affiché par leur nom seront affiché
par le numero.
L'option `-v' te montre tous les détails des règles, comme les
compteurs de paquets et d'octets, les comparaisons TOS, et les
interfaces. Sinon ces valeurs sont omises.
Notes que les compteurs de paquets et d'octets sont écris en utilisant
les suffixes `K', `M' ou `G' pour 1000, 1,000,000 et 1,000,000,000
respectivement. Utiliser `-x' (expansion des nombres) écrit les
nombres complets sans importance avec leur grandeur.
[1m7.5.5. Resetter (Zeroer) les Compteurs[0m
Ilk est utile de pouvoir remettre les compteurs à zéro. Ca peut être
fait avec l'option `-Z' (ou `--zero').
Considères ceci:
# iptables -L FORWARD
# iptables -Z FORWARD
#
Dans l'exemple du dessus, quelques paquets pourraient passer entre les
commandes `-L' et `-Z'. Pour cette raison, tu peux utiliser `-L' et
`-Z' [4mensembles[24m, pour remettre les compteurs à zero en les lisant.
[1m7.5.6. Configurer la Police[0m
Nous avons parlé de ce qui arrive quand un paquet arrive à la fin
d'une chaine compilée quand nous avons discuté comment un paquet
traversait les chaines plus tôt. Dans ce cas, la [1mpolice [22mde la chaine
détermine le sort du paquet. Seules les chaines compilées (INPUT,
OUTPUT et FORWARD) ont des polices, à cause du fait que si un paquet
tombe à la fin d'une chaine utilisateur, la traversée reprend à la
chaine précédente.
La police peut être soit ACCEPT ou DROP par exemple :
# iptables -P FORWARD DROP
#
[1m8. Utiliser ipchains et ipfwadm[0m
Il y a des modules ipchains.o et ipfwadm.o dans la distribution
netfilter. Insères un de ceux-ci dans ton noyau (NOTE : ils sont
incompatibles avec iptables.o, ip_conntrack.o et ip_nat.o!). Ensuite
tu peux utiliser ipchains et ipfwadm comme avant.
ça sera supporté pendant encore quelque temps. Je penses qu'une
formule raisonnable est 2 * [notification de remplacement - sortie
initiale stable ], avant la date d'une sortie stable d'un
remplacement.
Ca veut dire que pour ipfwadm, la fin du support sera:
2 * [Octobre 1997 (sortie du 2.1.102) - Mars 1995 (ipfwadm 1.0)]
+ Janvier 1999 (sortie du 2.2.0)
= Mars 2004.
Ca veut dire que pour ipfwadm, la fin du support sera:
2 * [Aout 1999 (sortie du 2.3.15) - Octobre 1997 (sortie du 2.2.0)]
+ Juillet 2000 (sortie du 2.4.0)
= Mars 2004.
Tu n'as pas à t'inquietter avant 2004.
[1m9. Mixer le NAT et le Filtrage de Paquets[0m
Il est commun de vouloir faire de la Translation d'Adresses Réseaux
(voir le NAT HOWTO) et le filtrage de paquets. La bonne nouvelle est
qu'ils se mixent extrèmement bien.
Tu configures complètement ton filtrage de paquets en ignorant tout le
NAT que tu feras. Les sources et destinations vues par le filtre de
paquets seront les sources et destination `réelles'. Par exemple, si
tu effectues du DNAT pour envoyer toutes les connections du port 80 de
1.2.3.4 à travers le port 8080 de 10.1.1.1, le filtre de paquets verra
les paquets allant au port 8080 de 10.1.1.1 (la destination réelle),
pas le port 80 de 1.2.3.4. Similairement tu peux ignorer le
masquerading : les paquets sembleront venir de leurs adresses ip
internes réelles (disons 10.1.1.1), et les réponses sembleront
retourner là-bas.
Tu peux utiliser la concordance `state' sans faire faire du travail
supplémentaire au filtre de paquets, puisque le NAT requiert le suivi
de connections de toutes façons. Pour étendre le simple exemple de
masquerading dans le NAT HOWTO qui rejète toutes les nouvelles
connection venant de l'interface ppp0, tu ferais ceci :
# Masquerader ppp0
iptables -t nat -A POSTROUTING -o ppp0 -j MASQUERADE
# Rejeter les paquets NEW et INVALID venant ou forwardés de ppp0.
iptables -A INPUT -i ppp0 -m state --state NEW,INVALID -j DROP
iptables -A FORWARD -i ppp0 0 -m state --state NEW,INVALID -j DROP
# Activer le forwarding IP
echo 1 > /proc/sys/net/ipv4/ip_forward
[1m10. Différences entre iptables et ipchains[0m
· Premièrement, les noms des chaines compilées sont passés de
minuscule en MAJUSCULE, parce que les chaines INPUT et OUTPUT
configurent juste les paquet destinés locallement et générés
locallement. Elles voyaient tous les paquets entrants et sortants
respectivement.
· Le drapeau `-i' signifie maintenant l'interface d'entrée, et
fonctionne seulement dans les chaines INPUT et FORWARD. Les règles
dans les chaines FORWARD ou OUTPUT qui utilisaient `-i' doivent
être changées en `-o'.
· Les ports TCP et UDP doivent maintenant être épelés avec les
options --source-port ou --sport (ou --destination-port/--dport),
et doivent être placés après les options `-p tcp' ou `-p udp',
comme cela charge les extensions TCP ou UDP respectivement.
· Le drapeau TCP `-y' est maintenant `--syn', et doit être placé
après `-p tcp'.
· La cible `DENY' est maintenant `DROP', finallement.
· Remettre une chaine à zero en la listant fonctionne.
· Remettre les chaines compilées à zéro remets les compteurs de
police à zéro aussi.
· Lister les chaines te donnes les compteurs comme atomiques.
· REJECT et LOG sont maintenant des cibles étendues, ce qui veut dire
qu'ils sont des modules du noyau.
· Les noms de chaines peuvent aller jusqu'a 31 caractères.
· MASQ est maintenant MASQUERADE et utilise une syntaxe différente.
REDIRECT tout en gardant le même nom, a aussi subi un changement de
syntaxe. Voir le NAT-HOWTO pour plus d'information pour configurer
ceci.
· L'option `-o' n'est plus utilisée pour diriger les paquets dans
l'espace utilisateur (voir `-i' ci-dessus). Les paquets sont
envoyés en espace utilisateur via la cible QUEUE.
· Probablement des tonnes d'autres trucs que j'ai oublié.
[1m11. Mise en Garde sur le Filtre de Paquets[0m
La façon généralle de procéder dans la sécurité informatique est de
tout bloquer puis d'ouvrir des trous quand c'est nécessaire. C'est
habituellement paraphrasé par `tout ce qui n'est pas spécifiquement
autorisé est défendu'. Je recommendes cette approche si la sécurité
est un primeur.
Ne fais pas tourner de service dont tu n'as pas besoin, même si tu
penses avoir bloqué l'accès vers ceux-ci.
Si tu crées un firewall dédié, commences par ne rien faire tourner et
tout bloquer et ajoutes les services et laisses passer les paquets
quand c'est nécessaire.
Je recommendes la sécurité en profondeur : combines les tcp-wrappers
(pour les connections au filtre de paquets lui-mème), la verification
de route et le filtrage de paquets. La verification de route c'est
quand un paquet qui vient d'une interface non attendue est laissé
tomber : par exemple, si un réseau interne a des adresses
10.1.1.0/24, et qu'un paquet avec cette adresse source vient sur ton
interface externe, il sera laissé tomber. Ceci peut être activé pour
une interface (ppp0) par:
# echo 1 > /proc/sys/net/ipv4/conf/ppp0/rp_filter
#
Ou pour toutes les interfaces existantes ou futures :
# for f in /proc/sys/net/ipv4/conf/*/rp_filter; do
# echo 1 > $f
# done
#
Debian fait cela par défaut quand c'est possible. Si tu utilises du
routage assymétrique (p.e. tu attends des paquets qui viennent de
direction étranges), tu voudras désactiver cela sur ces interfaces.
Le logging est utile quand tu réalises un firewall si quelquechose ne
fonctionne pas, mais sur un firewall de production, combines le avec
la concordance `limit', pour eviter que quelqu'un ne satures tes logs.
Je recommendes fortement le suivi de connections sur les systèmes
sécurisés: il introduit un peu plus de charge, comme toutes les
connections sont suivies, mais est très utile pour controller l'accès
à tes réseaux. Tu devras charger le module `ip_conntrack.o' si ton
noyau ne charges pas les modules automatiquement, et qu'il n'est pas
compilé dans le noyau. Si tu veux suivre convenablement des protocoles
complexes, tu devra charger le module de suivi aproprié (pe.
`ip_conntrack_ftp.o').
# iptables -N no-conns-from-ppp0
# iptables -A no-conns-from-ppp0 -m state --state ESTABLISHED,RELATED -j ACCEPT
# iptables -A no-conns-from-ppp0 -m state --state NEW -i ! ppp0 -j ACCEPT
# iptables -A no-conns-from-ppp0 -i ppp0 -m limit -j LOG --log-prefix "Bad packet from ppp0:"
# iptables -A no-conns-from-ppp0 -i ! ppp0 -m limit -j LOG --log-prefix "Bad packet not from ppp0:"
# iptables -A no-conns-from-ppp0 -j DROP
# iptables -A INPUT -j no-conns-from-ppp0
# iptables -A FORWARD -j no-conns-from-ppp0
Construire un bon firewall est hors du sujet de ce HOWTO, mais mon
conseil est de `toujours être minimaliste'. Voir le Security HOWTO
pour plus d'informations sur comment tester ta machine.