QOS, klasifikace síťového provozu

Marek Posolda, 60575@mail.muni.cz


Obsah


1. Úvod

Přenos dat mezi počítači (případně mezi počítačovými sítěmi) je vcelku obtížná záležitost. Ve většině případů si přejeme. aby data došla pokud možno co nejrychleji, nejbezpečněji, s minimálním zpožděním a rozptylem zpoždění atd. Právě toto nám zabezpečuje kvalita služby (QOS - quality of services).

QOS je určena následujícími parametry:

Při zajišťování QOS je třeba mít co největší šířku pásma a co nejmenší zpoždění, rozptyl a ztrátovost. Zpravidla pro nás některá data přenášená po síti mají větší cenu než jiná. Proto chceme mít možnost ovlivňovat QOS pro přijatá a odeslaná data podle různých kritérií, jako je cílový či zdrojový port, cílová či zdrojová IP adresa, velikost paketu atd.

Hodnota QOS závisí na všech vrstvách a komponentách síťového provozu (cílový počítač, zdrojový počítač, routery, huby, jednotlivé linky po kterých data putují) Některé z těchto komponent zpravidla nemůžeme ovlivnit, ale u některých to možné je. Naštěstí tedy máme možnost QOS poměrně jednoduše v Linuxu konfigurovat.


2. Modely QOS


3. Provozy


4. Fronty paketů (qdiscs)

4.1 Classless qdiscs

Jsou navázané na určité síťové rozhraní a není na ně možné navázat další fronty. Pakety jsou na rozhraní zařazována do front a tvarována různými způsoby podle následujících algoritmů

4.2 Classfull qdiscs

Pakety příchozí na síťové zařízení jsou rozdělovány do tříd. Řazení paketů do tříd probíhá na záklaedě uživatelem definovaných filtrů. Na třídu pak mohou být navazovány další qdiscy (classless nebo classfull)
                     1:   root qdisc
                      |
                     1:1    child class
                   /  |  \
                  /   |   \
                 /    |    \
                /     |     \
              1:10  1:11  1:12   child classes
               |      |     | 
               |      |     |    
               |      |     | 
              10:    11:   12:   qdisc

Čísla - Př. u třídy 1:10 je 1 majoritní číslo a 10 minoritní číslo.
Třída - má stejně majoritní číslo jako rodič.
Qdisc - Jeho minoritní číslo je rovno 0. Přitom se často nezapisuje, tzn. 10:0 a 10: jsou 2 možnosti zápisu stejného qdiscu.

Při příchodu na síťový interface je paket podle filtru pklasifikován např. takto:
1: -> 1:1 -> 1:11 -> 11:

Na konečné qdiscy je navázána implicitně pfifo_fast. Pokud to chceme změnit, je třeba provést změnu na jiný classless qdisc.

Druhy classfull qdisců:


5) Konfigurace v Linuxu

5.1) Podmínky konfigurace

5.2) Příklad konfigurace shapingu pomocí HTB

# SMAZANI PUVODNIHO QDISCU NA ROZHRANI eth1

tc qdisc del dev eth1 root

# VYTVORENI htb KORENOVEHO QDISCU NA ROZHRANI eth1
# DEFAULT 10 ZNAMENA, ZE PAKETY KTERE NEVYHOVI ZADNEMU FILTRU DAVAME DO KONCOVEHO QDISCU 10:0

tc qdisc add dev eth1 root handle 1:0 htb default 10

# VYTVORENI TRID NA NEHO NAVAZANYCH
# RATE - OMEYENI POCTU PRENESENYCH DAT ZA 1 SEKUNDU
# CEIL - PRI POUZITI TOHOTO PARAMETRU SE KANAL MUZE "DELIT" SE SVYMI SOUROZENCI
#        TZN. POKUD KANALEM 10 NEPROTEKAJI DATA, TAK KANALEM 11 MUZE PROTEKAT AZ 256kbit.
#        CEIL BY MEL BYT VZDY VETSI NEZ RATE A MENSI NEZ RATE PREDKA.

tc class add dev eth1 parent 1:0 classid 1:1 htb rate 256kbit

tc class add dev eth1 parent 1:1 classid 1:10 htb rate 128kbit ceil 256kbit
tc class add dev eth1 parent 1:1 classid 1:11 htb rate 128kbit ceil 256kbit

# VYTVORENI QDISKŮ TYPU SFQ NAVAZANYCH NA TŘÍDY 1:10 A 1:11. HANDLE 10: IDENTIFIKACE PRO FILTRY.
# PERTURB 10 - POUZITO U SFQ. HASHOVACI FUNKCE ROZRAZUJICI DO PAKETY DO FRONT JE ZMENENA PO 10 
#              SEKUNDACH. 10 SEKUND JE IDEALNI HODNOTA PRO PERTURB.
              
tc qdisc add dev eth1 parent 1:10 handle 10:0 sfq perturb 10
tc qdisc add dev eth1 parent 1:11 handle 11:0 sfq perturb 10


# PRIKLAD DEFINICE FILTRU BEZ POUZITI IPTABLES. ROZRAZENI PODLE CILOVE IP ADRESY

tc filter add dev eth1 parent 1:1 protocol ip u32 match ip dst 10.0.0.10 flowid 1:10
tc filter add dev eth1 parent 1:1 protocol ip u32 match ip dst 10.0.0.11 flowid 1:11

# PRIKLAD DEF. FILTRU S POUZITIM IPTABLES A JEJICH TABULKY MANGLE. ROZRAZENI PODLE CILOVEHO PORTU.

iptables -t mangle -I FORWARD -d 10.0.0.10 -p tcp -i eth1 --dport 80 -j MARK --set-mark 10
iptables -t mangle -I FORWARD -d 10.0.0.10 -p tcp -i eth1 --dport 21 -j MARK --set-mark 11

tc filter add dev eth1 parent 1:1 protocol ip handle 10 fw flowid 1:10
tc filter add dev eth1 parent 1:1 protocol ip handle 11 fw flowid 1:11
Jak vidíme, konfigurace shapingu pomocí htb je poměrně jednoduchá a dává dobré výsledky z hlediska přesnosti rate.

5.3) Příklad konfigurace policingu

# NA eth0 NAVAZUJEME HANDLE ffff: PRO INGRESS. NASLEDNE VYTVARIME FILTR, KTERY 
# SE SNAZI OMEZIT PRICHOZI PROVOZ NA 256kbit POMOCI ZAHAZOVANI PAKETU.

tc qdisc add dev eth0 handle ffff: ingress
tc filter add dev eth0 parent ffff: protocol ip prio 50 u32 match ip src 0.0.0.0/0 police rate 256kbit burst 10k drop flowid :1
Konfigurace policingu touto metodou ve srovnání s htb příliš přesná není (velikost přicházejících dat se tímto omezila asi na 440kbit.) Je však možno ovlivnit přesnost zmenšením kbelíku (parametr burst)

5.4) Příklad konfigurace policingu pomocí IMQ

Pro použití IMQ se většinou nevyhneme některým krokům jako je patch a rekompilace jádra, případně navíc i patch programu iptables.
modprobe IMQ

# Musíme přesměrovat příchozí provoz na naše virtuální IMQ zařízení ješte
# před jeho jakýmkoliv zpracováním.

iptables -t mangle -A PREROUTING -j IMQ

# Nyní můžeme vytvořit strom stejně jako v předchozím případě.

tc qdisc del dev imq0 root
tc class add ...

6) Rozdělení zátěže přes více rozhraní

Dosáhneme toho pomocí metody zv. bonding, neboli sloučení více fyzických rozhraní do jednoho logického. Musíme mít podporu v jádře [Device drivers/Network device support/Bonding driver support]. Příklad zprovoznění:
[/root ]# modprobe bonding
[/root ]# ip addr add 10.0.0.1/24 brd + dev bond0
[/root ]# ip link set dev bond0 up
[/root ]# ifenslave  bond0 eth2 eth3
master has no hw address assigned; getting one from slave!
The interface eth2 is up, shutting it down it to enslave it.
The interface eth3 is up, shutting it down it to enslave it.
[/root ]# ifenslave  bond0 eth2 eth3
[/root ]# cat /proc/net/bond0/info
Bonding Mode: load balancing (round-robin)
MII Status: up
MII Polling Interval (ms): 0
Up Delay (ms): 0
Down Delay (ms): 0

Slave Interface: eth2
MII Status: up
Link Failure Count: 0

Slave Interface: eth3
MII Status: up
Link Failure Count: 0
Vyčerpávající dokumentaci k této technice najdete v dokumentaci kernelu ($kernel_src/Documentation/networking/bonding.txt).

7) Měření síťového provozu

Doporučuji použít program iptraf (http://cebu.mozcom.com/riker/iptraf/) ze stejnojmenného balíčku. Velmi intuitivní ovládání, možnost měřit síťový provoz podle rozhraní, velikosti paketu, portu atd.

8) Zdroje

1) Archív referátů P90
2) Seriál na rootu o htb
3) Semestrální projekt studentů cs.vsb.cz do předmětu Technologie počítačových sítí
4) man tc