Linux.tc

Aus OrgaMon Wiki
Zur Navigation springen Zur Suche springen

Einführung

wir verwenden "iptables" und "tc", 2 der coolsten Linux Projekte.

Jeder ordentliche Router, oder allgemein, alle Systeme mit einem Flaschenhals auf dem Weg von Quelle zu Ziel sollten eine trickreiche Bandbreiten Kontrolle durchführen. Das Ziel ist, dass grosse Datenbewegungen mit von vorne herein bekannter langer Laufzeit, nicht die kleinen schnellen Datenbewegungen blockieren. Bei DSL Modems leidet der Gesamtdurchsatz, wenn insbesondere der Upstream am Limit betrieben wird. Der Grund: Das TCP Protokoll erfordert hin und wieder Bestätigungspakete, die z.B. einen Download ermöglichen. Ist der Upstream überlastet gehen diese Pakete nicht zeitnah raus, der Download wird langsamer.
Das Script beschränkt erst mal grundsätzlich den gesamten Upstream auf 90% seiner netto Leistungskraft. Dadurch kommt es nicht zum Paket Stau im Modem. iptables beurteilt nun alle Pakete, die als Ziel das dsl0 device haben. Es markiert die Pakete nun mit einer Prioritäts - Ziffer (1=hoch ... 4=gering). Mit tc werden 4 korospondierende Klassen erzeugt, denen dann die entsprechenden Pakete zugeteilt werden. Ausgehend werden nun Pakete mit höherer Priorität vorgezogen. Enstehen mehr Pakete als der Upstream verkraftet werden diese in einer eigenen Queue des tc gesammelt (glaube ich).
Ist im Moment die volle ungeteilte Bandbreite verfügbar, so erfolgt keine Beschränkung.

Der Downstream kann meines Wissens nicht sinnvoll beschränkt werden. Ich hab mal was über "PAUSE" Pakete gelesen, also die Bitte des Empfängers die Sendungen etwas auszusetzten, dies würde ja für einen konkurierenden Sender für mehr Luft sorgen und diesen schneller machen.

Das Script

 #
 # Konfigurationsscript eines Bandbreitenmanagment mit Hilfe von TC
 #
 #
 # Gestartet wird diese Datei mit Hilfe der /etc/rc.d/init.d/tcshape
 #
 # Description:   Script zum  Konfigurieren eines Bandbreitenmanagment
 # Autor:         Sven Neukirchner <sven@konabi.de>
 #                mit Hilfe von Newsgroups und Beispielen aus dem Internet
 #				 http://www.naxan.de/Linux/MiniQoS.html  Dank an Frank Nodes
 #				 http://www.robert-peter.de/yats/        Dank an Robert Peter
 #
 # Date           26.05.2005
 # Version:       1.0 ohne L7 Filter  (http://l7-filter.sourceforge.net)
 # Lizenz:        GPL
 # benoetigt:     iptable, tc/iproute2
 #
 # Loeschen der Warteschlangen und Klssen geschieht im Script /etc/init.d/tcshape
 #
 # mit "tc -s -d class show dev ppp0" kann man sich die einezelnen Klassen anschauen
 # oder man verwendet ein schoens Perlscipt /usr/local/bin/tcshape.pl
 # das Script sammelt die Daten und erzeugt eine HTML Datei
 # Autor des Scriptes ist mir unbekannt Download unter www.konabi.de/download/download.php
 #
 #

 echo "    Erstelle Markierungsrichtlinien..."


 # zu ueberwachendes Geraet
 DEV=dsl0


 # Uplink Speed (90% von Fullspeed, damit der Modembuffer nicht ueberlaeuft)
 UPLINK=460

 #### Prioritaetsmarke fuer ausgehende Packete setzen ########################################

 iptables -A PREROUTING -t mangle -s 192.168.115.191 -j MARK --set-mark 4

 ### - Prioritaet 1 - Packete die hoechste Prio bekommen sollen werden mit 1 markiert (--set-mark 1) ###
 #SSH, SIP, RTP, TOS=Minimize Delay
 iptables -t mangle -o $DEV -A POSTROUTING -p ICMP -j MARK --set-mark 1
 iptables -t mangle -o $DEV -A POSTROUTING -p TCP --dport 22 -j MARK --set-mark 1
 iptables -t mangle -o $DEV -A POSTROUTING -p UDP --dport 5060 -j MARK --set-mark 1
 iptables -t mangle -o $DEV -A POSTROUTING -p UDP --sport 10000:10010 -j MARK --set-mark 1


 ###  Prioritaet 2  Packete die zweithoechste Prio bekommen sollen werden mit 2 markiert  ###
 # TCP ACKs, TOS= Max Throughput
 iptables -t mangle -o $DEV -A POSTROUTING -p TCP -m length --length :64 -j MARK --set-mark 2
 iptables -t mangle -o $DEV -A POSTROUTING -p TCP -m tos --tos Maximize-Throughput -j MARK --set-mark 2


 ###  Prioritaet 3 - Standard ###


 ## Prioritaet 4 - Packete die geringste Prio bekommen sollen werden mit 4 markiert ###
 #  EMULE, TOS=Min Throughput
 iptables -t mangle -o $DEV -A POSTROUTING -p TCP --dport 4661 -j MARK --set-mark 4
 iptables -t mangle -o $DEV -A POSTROUTING -p TCP --dport 4662 -j MARK --set-mark 4
 iptables -t mangle -o $DEV -A POSTROUTING -p UDP --dport 4672 -j MARK --set-mark 4
 iptables -t mangle -o $DEV -A POSTROUTING -p TCP -m tos --tos Minimize-Cost -j MARK --set-mark 4

 #################################################################################

 tc qdisc del dev $DEV root

 echo "    Erstelle Klassen ..."

 # Installation einer HTB Warteschlange, (Hierarchy  Token  Bucket)
 # alle Packete gehen in diese Warteschlange
 # die HTP Warteschlange besitzt die Moeglichkeit garanierte Bandbreite
 # verschiedenen Klassen zuzuordnen
 # Packete die nicht markiert worden sind gehen in die Klasse 30 (default 30)
 tc qdisc add dev $DEV root handle 1: htb default 30

 # Erstellen einer Hauptklasse in der alle Packete gelangen
 tc class add dev $DEV parent 1: classid 1:1 htb rate ${UPLINK}kbit

 # Erstellen von Unterklassen und Zuordnung von garanierten min Bandbreiten bis max Bandbreite
 #    $[50*UPLINK/100]  miniumum garantierter Durchsatz 50% vom Uplink
 #    ${UPLINK}         maximaler Durchsatz entspricht Interface
 #    classid           ist name der Klasse
 #    parent 1:1        Unterklasse (classid) ist an uebergeordnete Klasse parent 1:1 angeschlossen
 #    prio              ist dafür zustaendig in welcher Reihenfolge freie Bandbreite
 #                      an die einzelnen Klassen vergeben wird
 #					   (die hoehere Klasse bekommt zuerst Bandbreite wenn Bandbreite verfuegbar ist)

 tc class add dev $DEV parent 1:1 classid 1:10 htb rate $[50*UPLINK/100]kbit ceil ${UPLINK}kbit prio 1
 tc class add dev $DEV parent 1:1 classid 1:20 htb rate $[30*UPLINK/100]kbit ceil ${UPLINK}kbit prio 2
 tc class add dev $DEV parent 1:1 classid 1:30 htb rate $[20*UPLINK/100]kbit ceil ${UPLINK}kbit prio 3
 tc class add dev $DEV parent 1:1 classid 1:40 htb rate $[10*UPLINK/100]kbit ceil ${UPLINK}kbit prio 4


 # Packete die von Firewall mit 1 markiert worden sind (handle 1) werden an Klasse 1:10 weitergeleitet usw...

 tc filter add dev $DEV protocol ip parent 1:0 prio 1 handle 1 fw flowid 1:10
 tc filter add dev $DEV protocol ip parent 1:0 prio 2 handle 2 fw flowid 1:20
 tc filter add dev $DEV protocol ip parent 1:0 prio 3 handle 3 fw flowid 1:30
 tc filter add dev $DEV protocol ip parent 1:0 prio 4 handle 4 fw flowid 1:40

 # alle Hosts einer Klasse werden gleich behandelt (SFQ  Stochastic FAIRNESS QUEUE)
 #      kommt zum Einsatz wenn z.B. meherer Rechner im Netz Bandbreite einer Klasse benutzen
 #      und ein Rechner auf Grund seiner Hardware schneller Packete empfanggen und senden kann
 #      hierdurch wird verhindert dass dieser Rechner den anderen rechnern die Bandbreite enzieht

 tc qdisc add dev $DEV parent 1:10 handle 10: sfq perturb 10
 tc qdisc add dev $DEV parent 1:20 handle 20: sfq perturb 10
 tc qdisc add dev $DEV parent 1:30 handle 30: sfq perturb 10
 tc qdisc add dev $DEV parent 1:40 handle 40: sfq perturb 10

Statistik ausgeben, an welchen Stellen die Filter greifen

tc -s class ls dev dsl0