Comment puis-je faire la mise en forme du trafic sous Linux par IP?


15

Nous avons une configuration de proxy transparente. J'ai essayé de chercher la mise en forme du trafic sous Linux, et tout ce que j'ai pu trouver en ligne était de limiter le trafic par interface (eth0 / eth1 ...).

J'ai besoin de limiter la bande passante (sans jamais dépasser une limite spécifique) par adresse IP ou plage IP et je ne trouve pas de moyen de le faire.

Y'a-t'il un quelconque moyen d'y arriver?

Réponses:


17

La couche de mise en forme du trafic du noyau est, fondamentalement, un planificateur de paquets attaché à votre carte réseau. Ainsi, une politique de mise en forme du trafic s'applique à une carte réseau.

Ce que vous pouvez faire, dans votre cas, est de créer une liste d'IP et de bande passante attachée, puis, pour chaque IP, vous créez:

  • Une règle de mise en forme du trafic identifiée par un classid
  • Une règle de netfilter qui marquera les paquets à une valeur de marque spécifique
  • Un filtre qui liera ces marques de paquets au classid, appliquant ainsi la règle de contrôle du trafic aux paquets spécifiés.

L'exemple donné par @Zoredache fonctionne, mais je préfère personnellement utiliser la capacité Netfilter au lieu de TC pour filtrer les paquets, et HTB au lieu de CBQ pour l'algorithme de mise en forme. Vous pouvez donc essayer quelque chose comme ça (nécessite Bash 4 pour les tableaux associatifs):

#! /bin/bash
NETCARD=eth0
MAXBANDWIDTH=100000

# reinit
tc qdisc del dev $NETCARD root handle 1
tc qdisc add dev $NETCARD root handle 1: htb default 9999

# create the default class
tc class add dev $NETCARD parent 1:0 classid 1:9999 htb rate $(( $MAXBANDWIDTH ))kbit ceil $(( $MAXBANDWIDTH ))kbit burst 5k prio 9999

# control bandwidth per IP
declare -A ipctrl
# define list of IP and bandwidth (in kilo bits per seconds) below
ipctrl[192.168.1.1]="256"
ipctrl[192.168.1.2]="128"
ipctrl[192.168.1.3]="512"
ipctrl[192.168.1.4]="32"

mark=0
for ip in "${!ipctrl[@]}"
do
    mark=$(( mark + 1 ))
    bandwidth=${ipctrl[$ip]}

    # traffic shaping rule
    tc class add dev $NETCARD parent 1:0 classid 1:$mark htb rate $(( $bandwidth ))kbit ceil $(( $bandwidth ))kbit burst 5k prio $mark

    # netfilter packet marking rule
    iptables -t mangle -A INPUT -i $NETCARD -s $ip -j CONNMARK --set-mark $mark

    # filter that bind the two
    tc filter add dev $NETCARD parent 1:0 protocol ip prio $mark handle $mark fw flowid 1:$mark

    echo "IP $ip is attached to mark $mark and limited to $bandwidth kbps"
done

#propagate netfilter marks on connections
iptables -t mangle -A POSTROUTING -j CONNMARK --restore-mark

- edit: oublié la classe par défaut et propager les marques à la fin du script.


umm .. comment ajouter la limite de bande passante par défaut pour ceux qui ne figurent pas sur la liste?
Kokizzu

Vous avez utilisé $ mark comme définition prio. Ne serait-il pas préférable d'utiliser la même priorité pour tous?
motobói

si je change "iptables -t mangle -A INPUT" en "iptables -t mangle -A OUTPUT" pourrais-je contrôler le débit de mon serveur vers une IP particulière ??
Frank Barcenas

comment puis-je restaurer les paramètres après cela?
Stefan Rogin

Je ne peux pas faire cela, en écrivant des commandes manuellement sans boucle pour une seule IP.
Adones Pitogo

5

Quelque chose comme ça a fonctionné pour moi pour limiter la webcam d'un entrepreneur à une quantité limitée de bande passante. Consultez la page de manuel de tc pour plus de détails.

#!/bin/bash
set -x

DEV=eth0
export DEV

tc qdisc del dev $DEV root
tc qdisc del dev $DEV root
tc qdisc add dev $DEV root handle 1: cbq avpkt 1000 bandwidth 100mbit

# setup a class to limit to 1500 kilobits/s
tc class add dev $DEV parent 1: classid 1:1 cbq rate 1500kbit \
   allot 1500 prio 5 bounded isolated

# add traffic from 10.2.1.37 to that class
tc filter add dev $DEV parent 1: protocol ip prio 16 u32 \
   match ip src 10.2.1.37 flowid 1:1

3
CBQ est un peu abandonné ... vous trouveriez le HTB beaucoup plus facile à utiliser et obtenez le même résultat
Julien Vehent

1
Pas besoin d'exporter DEV s'il n'est utilisé que dans ce script ....
Gert van den Berg

1

Je ne suis pas sûr d'avoir bien compris votre question.

Le proxy transparent (comme dans Squid pour HTTP) est utilisé pour contrôler principalement les données entrantes. Alors que la mise en forme du trafic est utilisée pour contrôler les données sortantes.

Vous devez fournir plus de détails. Si vous avez beaucoup de postes de travail derrière un proxy HTTP et essayez de limiter leurs vitesses de téléchargement, vous feriez mieux d'opter pour quelque chose comme les pools de délais Squid +.

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.