Linux自帶的流量控制工具-TC

背景

最近故障演練需要對(duì)redis服務(wù)器進(jìn)行流量相關(guān)的控制和模擬粗合,學(xué)習(xí)了一下相關(guān)的工具和原理萍嬉,讀了幾篇文章,這里做下總結(jié)隙疚。

一壤追、原理

netem 與 tc:

netem 是 Linux 2.6 及以上內(nèi)核版本提供的一個(gè)網(wǎng)絡(luò)模擬功能模塊。該功能模塊可以用來(lái)在性能良好的局域網(wǎng)中供屉,模擬出復(fù)雜的互聯(lián)網(wǎng)傳輸性能行冰,諸如低帶寬、傳輸延遲伶丐、丟包等等情況悼做。使用 Linux 2.6 (或以上) 版本內(nèi)核的很多發(fā)行版 Linux 都開(kāi)啟了該內(nèi)核功能,比如Fedora哗魂、Ubuntu肛走、Redhat、OpenSuse录别、CentOS朽色、Debian等等。

tc 是 Linux 系統(tǒng)中的一個(gè)工具组题,全名為traffic control(流量控制)葫男。tc 可以用來(lái)控制 netem 的工作模式,也就是說(shuō)崔列,如果想使用 netem 梢褐,需要至少兩個(gè)條件,一個(gè)是內(nèi)核中的 netem 功能被包含,另一個(gè)是要有 tc

Linux操作系統(tǒng)中的流量控制器TC(Traffic Control)用于Linux內(nèi)核的流量控制利职,主要是通過(guò)在輸出端口處建立一個(gè)隊(duì)列來(lái)實(shí)現(xiàn)流量控制趣效。
接收包從輸入接口進(jìn)來(lái)后,經(jīng)過(guò)流量限制丟棄不符合規(guī)定的數(shù)據(jù)包猪贪,由輸入多路分配器進(jìn)行判斷選擇:

如果接收包的目的主機(jī)是本主機(jī)跷敬,那么將該包送給上層處理,否則需要進(jìn)行轉(zhuǎn)發(fā)热押,將接收包交到轉(zhuǎn)發(fā)塊(Forwarding Block)處理西傀。
轉(zhuǎn)發(fā)塊同時(shí)也接收本主機(jī)上層(TCP、UDP等)產(chǎn)生的包桶癣,通過(guò)查看路由表拥褂,決定所處理包的下一跳。
然后牙寞,對(duì)包進(jìn)行排列以便將它們送到輸出接口饺鹃。
一般只能限制網(wǎng)卡發(fā)送的數(shù)據(jù)包,不能限制網(wǎng)卡接收的數(shù)據(jù)包间雀,所以可以通過(guò)改變發(fā)送次序來(lái)控制傳輸速率悔详。Linux流量控制主要是在輸出接口排列時(shí)進(jìn)行處理和實(shí)現(xiàn)的。

二惹挟、規(guī)則

2.1 流量控制方式

流量控制包括以下幾種方式:

SHAPING(限制): 當(dāng)流量被限制茄螃,它的傳輸速率就被控制在某個(gè)值以下。限制值可以大大小于有效帶寬连锯,這樣可以平滑突發(fā)數(shù)據(jù)流量归苍,使網(wǎng)絡(luò)更為穩(wěn)定。shaping(限制)只適用于向外的流量运怖。
SCHEDULING(調(diào)度): 通過(guò)調(diào)度數(shù)據(jù)包的傳輸拼弃,可以在帶寬范圍內(nèi),按優(yōu)先級(jí)分配帶寬摇展。SCHEDULING(調(diào)度)也只適于向外的流量吻氧。
POLICING(策略):
SHAPING用于處理向外的流量,而POLICIING(策略)用于處理接收到的數(shù)據(jù)吗购。
DROPPING(丟棄): 如果流量超過(guò)某個(gè)設(shè)定的帶寬医男,就丟棄數(shù)據(jù)包砸狞,不管是向內(nèi)還是向外捻勉。

2.2 流量控制處理對(duì)象

流量的處理由三種對(duì)象控制,它們是:

qdisc(排隊(duì)規(guī)則)
class(類別)
filter(過(guò)濾器)

2.2.1 qdisc(排隊(duì)規(guī)則)

QDisc(排隊(duì)規(guī)則)是queueing discipline的簡(jiǎn)寫刀森,它是理解流量控制(traffic control)的基礎(chǔ)踱启。無(wú)論何時(shí),內(nèi)核如果需要通過(guò)某個(gè)網(wǎng)絡(luò)接口發(fā)送數(shù)據(jù)包,它都需要按照為這個(gè)接口配置的qdisc(排隊(duì)規(guī)則)把數(shù)據(jù)包加入隊(duì)列埠偿。然后透罢,內(nèi)核會(huì)盡可能多地從qdisc里面取出數(shù)據(jù)包,把它們交給網(wǎng)絡(luò)適配器驅(qū)動(dòng)模塊冠蒋。最簡(jiǎn)單的QDisc是pfifo它不對(duì)進(jìn)入的數(shù)據(jù)包做任何的處理羽圃,數(shù)據(jù)包采用先入先出的方式通過(guò)隊(duì)列。不過(guò)抖剿,它會(huì)保存網(wǎng)絡(luò)接口一時(shí)無(wú)法處理的數(shù)據(jù)包朽寞。
qdisc的類別如下:

CLASSLESS QDisc(不可分類QDisc)

[p|b]fifo:
使用最簡(jiǎn)單的qdisc,純粹的先進(jìn)先出斩郎。只有一個(gè)參數(shù):limit脑融,用來(lái)設(shè)置隊(duì)列的長(zhǎng)度,pfifo是以數(shù)據(jù)包的個(gè)數(shù)為單位;bfifo是以字節(jié)數(shù)為單位缩宜。
pfifo_fast:
在編譯內(nèi)核時(shí)肘迎,如果打開(kāi)了高級(jí)路由器(Advanced Router)編譯選項(xiàng),pfifo_fast就是系統(tǒng)的標(biāo)準(zhǔn)QDISC锻煌。它的隊(duì)列包括三個(gè)波段(band)妓布。在每個(gè)波段里面,使用先進(jìn)先出規(guī)則炼幔。而三個(gè)波段(band)的優(yōu)先級(jí)也不相同秋茫,band 0的優(yōu)先級(jí)最高,band 2的最低乃秀。如果band0里面有數(shù)據(jù)包肛著,系統(tǒng)就不會(huì)處理band 1里面的數(shù)據(jù)包,band 1和band 2之間也是一樣跺讯。數(shù)據(jù)包是按照服務(wù)類型(Type of Service,TOS)被分配多三個(gè)波段(band)里面的枢贿。
red:
red是Random Early Detection(隨機(jī)早期探測(cè))的簡(jiǎn)寫。如果使用這種QDISC刀脏,當(dāng)帶寬的占用接近于規(guī)定的帶寬時(shí)局荚,系統(tǒng)會(huì)隨機(jī)地丟棄一些數(shù)據(jù)包。它非常適合高帶寬應(yīng)用。
sfq:
sfq是Stochastic Fairness Queueing的簡(jiǎn)寫。它按照會(huì)話(session--對(duì)應(yīng)于每個(gè)TCP連接或者UDP流)為流量進(jìn)行排序熬尺,然后循環(huán)發(fā)送每個(gè)會(huì)話的數(shù)據(jù)包叉袍。
tbf:
tbf是Token Bucket Filter的簡(jiǎn)寫,適合于把流速降低到某個(gè)值婿着。
不可分類qdisc配置: 如果沒(méi)有可分類QDisc,不可分類QDisc只能附屬于設(shè)備的根。它們的用法如下:

tc qdisc add dev DEV root QDISC QDISC-PARAMETERS
要?jiǎng)h除一個(gè)不可分類QDisc仙逻,需要使用如下命令:

tc qdisc del dev DEV root
一個(gè)網(wǎng)絡(luò)接口上如果沒(méi)有設(shè)置QDisc驰吓,pfifo_fast就作為缺省的QDisc。

CLASSFUL QDISC(分類QDisc):
可分類的qdisc包括:
CBQ: CBQ是Class Based Queueing(基于類別排隊(duì))的縮寫系奉。它實(shí)現(xiàn)了一個(gè)豐富的連接共享類別結(jié)構(gòu)檬贰,既有限制(shaping)帶寬的能力,也具有帶寬優(yōu)先級(jí)管理的能力缺亮。帶寬限制是通過(guò)計(jì)算連接的空閑時(shí)間完成的翁涤。空閑時(shí)間的計(jì)算標(biāo)準(zhǔn)是數(shù)據(jù)包離隊(duì)事件的頻率和下層連接(數(shù)據(jù)鏈路層)的帶寬萌踱。
HTB: HTB是Hierarchy Token Bucket的縮寫迷雪。通過(guò)在實(shí)踐基礎(chǔ)上的改進(jìn),它實(shí)現(xiàn)了一個(gè)豐富的連接共享類別體系虫蝶。使用HTB可以很容易地保證每個(gè)類別的帶寬章咧,它也允許特定的類可以突破帶寬上限,占用別的類的帶寬能真。HTB可以通過(guò)TBF(Token Bucket Filter)實(shí)現(xiàn)帶寬限制赁严,也能夠劃分類別的優(yōu)先級(jí)。
PRIO: PRIO QDisc不能限制帶寬粉铐,因?yàn)閷儆诓煌悇e的數(shù)據(jù)包是順序離隊(duì)的疼约。使用PRIO QDisc可以很容易對(duì)流量進(jìn)行優(yōu)先級(jí)管理,只有屬于高優(yōu)先級(jí)類別的數(shù)據(jù)包全部發(fā)送完畢蝙泼,才會(huì)發(fā)送屬于低優(yōu)先級(jí)類別的數(shù)據(jù)包程剥。為了方便管理,需要使用iptables或者ipchains處理數(shù)據(jù)包的服務(wù)類型(Type Of Service,ToS)汤踏。

2.2.2 class(類)

某些QDisc(排隊(duì)規(guī)則)可以包含一些類別织鲸,不同的類別中可以包含更深入的QDisc(排隊(duì)規(guī)則),通過(guò)這些細(xì)分的QDisc還可以為進(jìn)入的隊(duì)列的數(shù)據(jù)包排隊(duì)溪胶。通過(guò)設(shè)置各種類別數(shù)據(jù)包的離隊(duì)次序搂擦,QDisc可以為設(shè)置網(wǎng)絡(luò)數(shù)據(jù)流量的優(yōu)先級(jí)。

2.2.3 filter(過(guò)濾器)

Filter(過(guò)濾器)用于為數(shù)據(jù)包分類哗脖,決定它們按照何種QDisc進(jìn)入隊(duì)列瀑踢。無(wú)論何時(shí)數(shù)據(jù)包進(jìn)入一個(gè)劃分子類的類別中,都需要進(jìn)行分類才避。分類的方法可以有多種橱夭,使用fileter(過(guò)濾器)就是其中之一。使用filter(過(guò)濾器)分類時(shí)桑逝,內(nèi)核會(huì)調(diào)用附屬于這個(gè)類(class)的所有過(guò)濾器棘劣,直到返回一個(gè)判決。如果沒(méi)有判決返回肢娘,就作進(jìn)一步的處理呈础,而處理方式和QDISC有關(guān)。需要注意的是橱健,filter(過(guò)濾器)是在QDisc內(nèi)部而钞,它們不能作為主體。

2.3 執(zhí)行過(guò)程
類(Class)組成一個(gè)樹(shù)拘荡,每個(gè)類都只有一個(gè)父類臼节,而一個(gè)類可以有多個(gè)子類。某些QDisc(例如:CBQ和HTB)允許在運(yùn)行時(shí)動(dòng)態(tài)添加類珊皿,而其它的QDisc(例如:PRIO)不允許動(dòng)態(tài)建立類网缝。允許動(dòng)態(tài)添加類的QDisc可以有零個(gè)或者多個(gè)子類,由它們?yōu)閿?shù)據(jù)包排隊(duì)蟋定。此外粉臊,每個(gè)類都有一個(gè)葉子QDisc,默認(rèn)情況下驶兜,這個(gè)葉子QDisc使用pfifo的方式排隊(duì)扼仲,我們也可以使用其它類型的QDisc代替這個(gè)默認(rèn)的QDisc。而且抄淑,這個(gè)葉子QDisc有可以分類屠凶,不過(guò)每個(gè)子類只能有一個(gè)葉子QDisc。 當(dāng)一個(gè)數(shù)據(jù)包進(jìn)入一個(gè)分類QDisc肆资,它會(huì)被歸入某個(gè)子類矗愧。
我們可以使用以下三種方式為數(shù)據(jù)包歸類,不過(guò)不是所有的QDisc都能夠使用這三種方式:

tc過(guò)濾器(tc filter): 如果過(guò)濾器附屬于一個(gè)類郑原,相關(guān)的指令就會(huì)對(duì)它們進(jìn)行查詢唉韭。過(guò)濾器能夠匹配數(shù)據(jù)包頭所有的域,也可以匹配由ipchains或者iptables做的標(biāo)記犯犁。
服務(wù)類型(Type of Service): 某些QDisc有基于服務(wù)類型(Type of Service,ToS)的內(nèi)置的規(guī)則為數(shù)據(jù)包分類纽哥。
skb->priority: 用戶空間的應(yīng)用程序可以使用SO_PRIORITY選項(xiàng)在skb->priority域設(shè)置一個(gè)類的ID。
樹(shù)的每個(gè)節(jié)點(diǎn)都可以有自己的過(guò)濾器栖秕,但是高層的過(guò)濾器也可以直接用于其子類春塌。
如果數(shù)據(jù)包沒(méi)有被成功歸類,就會(huì)被排到這個(gè)類的葉子QDisc的隊(duì)中簇捍。相關(guān)細(xì)節(jié)在各個(gè)QDisc的手冊(cè)頁(yè)中只壳。

2.4 命名規(guī)則

所有的QDisc、類和過(guò)濾器都有ID暑塑。ID可以手工設(shè)置吼句,也可以有內(nèi)核自動(dòng)分配。ID由一個(gè)主序列號(hào)和一個(gè)從序列號(hào)組成事格,兩個(gè)數(shù)字用一個(gè)冒號(hào)分開(kāi)惕艳。

QDISC: 一個(gè)QDisc會(huì)被分配一個(gè)主序列號(hào)搞隐,叫做句柄(handle),然后把從序列號(hào)作為類的命名空間远搪。句柄采用象10:一樣的表達(dá)方式劣纲。習(xí)慣上,需要為有子類的QDisc顯式地分配一個(gè)句柄谁鳍。
class:
在同一個(gè)QDisc里面的類分享這個(gè)QDisc的主序列號(hào)癞季,但是每個(gè)類都有自己的從序列號(hào),叫做類識(shí)別符(classid)倘潜。類識(shí)別符只與父QDisc有關(guān)绷柒,和父類無(wú)關(guān)。類的命名習(xí)慣和QDisc的相同涮因。
filter:
過(guò)濾器的ID有三部分废睦,只有在對(duì)過(guò)濾器進(jìn)行散列組織才會(huì)用到。詳情請(qǐng)參考tc-filters手冊(cè)頁(yè)养泡。

2.5 單位

帶寬或流速單位:
kbps 千字節(jié)/s
mbps 兆字節(jié)/s
kbit Kbit/s
mbit Mbit/s
bps或者一個(gè)無(wú)單位數(shù)字 字節(jié)/s
數(shù)據(jù)數(shù)量單位:
kb或者k 千字節(jié)
mb或者m 兆字節(jié)
mbit 兆bit
kbit 千bit
b或者一個(gè)無(wú)單位數(shù)字 字節(jié)數(shù)

三郊楣、模擬網(wǎng)絡(luò)延遲和丟包

3.1 模擬網(wǎng)絡(luò)延遲

  • 添加一個(gè)固定延遲到本地網(wǎng)卡 eth0
// delay: 100ms
tc qdisc add dev eth0 root netem delay 100ms
  • 給延遲加上上下 10ms 的波動(dòng)
tc qdisc change dev eth0 root netem delay 100ms 10ms
  • 加一個(gè) 25% 的相關(guān)概率

相關(guān)性,是這當(dāng)前的延遲會(huì)和上一次數(shù)據(jù)包的延遲有關(guān)瓤荔,短時(shí)間里相鄰報(bào)文的延遲應(yīng)該是近似的而不是完全隨機(jī)的净蚤。這個(gè)值是個(gè)百分比,如果為 100%输硝,就退化到固定延遲的情況今瀑;如果是 0% 則退化到隨機(jī)延遲的情況, Pn = 25% Pn-1 + 75% Random

tc qdisc change dev eth0 root netem delay 100ms 10ms 25%
  • 讓波動(dòng)變成正態(tài)分布的
tc qdisc change dev eth0 root netem delay 100ms 20ms distribution normal

3.2 模擬網(wǎng)絡(luò)丟包

  • 設(shè)置丟包率為 1%
tc qdisc change dev eth0 root netem loss 0.1%
  • 添加一個(gè)相關(guān)性參數(shù)

這個(gè)參數(shù)表示當(dāng)前丟包的概率與上一條數(shù)據(jù)包丟包概率有 25% 的相關(guān)性 Pn = 25% Pn-1 + 75% Random

tc qdisc change dev eth0 root netem loss 0.1% 25%

3.3 模擬數(shù)據(jù)包重復(fù)

  • 1% 的數(shù)據(jù)包重復(fù)
tc qdisc change dev eth0 root netem duplicate 1%

3.4 模擬包損壞

  • 2% 的包損壞
tc qdisc add dev eth0 root netem corrupt 2%
  • 模擬包亂序

網(wǎng)絡(luò)傳輸并不能保證順序点把,傳輸層 TCP 會(huì)對(duì)報(bào)文進(jìn)行重組保證順序橘荠,所以報(bào)文亂序?qū)?yīng)用的影響比上面的幾種問(wèn)題要小。

報(bào)文亂序可前面的參數(shù)不太一樣郎逃,因?yàn)樯厦娴膱?bào)文問(wèn)題都是獨(dú)立的哥童,針對(duì)單個(gè)報(bào)文做操作就行,而亂序則牽涉到多個(gè)報(bào)文的重組褒翰。模擬報(bào)亂序一定會(huì)用到延遲(因?yàn)槟M亂序的本質(zhì)就是把一些包延遲發(fā)送)贮懈,netem 有兩種方法可以做。

  • 第一種是固定的每隔一定數(shù)量的報(bào)文就亂序一次:

每 5th (10th, 15th…) 的包延遲 10ms

tc qdisc change dev eth0 root netem gap 5 delay 10ms

  • 第二種方法使用概率來(lái)選擇亂序优训,相對(duì)來(lái)說(shuō)更偏向?qū)嶋H情況一些

25 % 的立刻發(fā)送(50% 的相關(guān)性)朵你,其余的延遲 10ms

tc qdisc change dev eth0 root netem delay 10ms reorder 25% 50%
只使用 delay 也可能造成數(shù)據(jù)包的亂序
tc qdisc change dev eth0 root netem delay 100ms 75ms
比如 first one random 100ms, second random 25ms,這樣就是會(huì)造成第一個(gè)包先于第二個(gè)包發(fā)送

四揣非、流量控制

Linux流量控制主要分為建立隊(duì)列抡医、建立分類和建立過(guò)濾器三個(gè)方面。

4.1 步驟:

  • 針對(duì)網(wǎng)絡(luò)物理設(shè)備(如以太網(wǎng)卡eth0)綁定一個(gè)隊(duì)列QDisc早敬;

  • 在該隊(duì)列上建立分類class忌傻;

  • 為每一分類建立一個(gè)基于路由的過(guò)濾器filter大脉;

  • 最后與過(guò)濾器相配合,建立特定的路由表水孩。

4.2 應(yīng)用1:

git限速1:針對(duì)端口進(jìn)行限速

在使用git拉去代碼時(shí)很容易跑滿帶寬镰矿,為了控制帶寬的使用,配置如下:

#查看現(xiàn)有的隊(duì)列
tc -s qdisc ls dev eth0

#查看現(xiàn)有的分類
tc -s class ls dev eth0

#創(chuàng)建隊(duì)列
tc qdisc add dev eth0 root handle 1:0 htb default 1 
#添加一個(gè)tbf隊(duì)列荷愕,綁定到eth0上,命名為1:0 棍矛,默認(rèn)歸類為1
#handle:為隊(duì)列命名或指定某隊(duì)列

#創(chuàng)建分類
tc class add dev eth0 parent 1:0 classid 1:1 htb rate 10Mbit burst 15k
#為eth0下的root隊(duì)列1:0添加一個(gè)分類并命名為1:1安疗,類型為htb,帶寬為10M
#rate: 是一個(gè)類保證得到的帶寬值.如果有不只一個(gè)類,請(qǐng)保證所有子類總和是小于或等于父類.
#ceil: ceil是一個(gè)類最大能得到的帶寬值.

#創(chuàng)建一個(gè)子分類
tc class add dev eth0 parent 1:1 classid 1:10 htb rate 10Mbit ceil 10Mbit burst 15k
#為1:1類規(guī)則添加一個(gè)名為1:10的類够委,類型為htb荐类,帶寬為10M

#為了避免一個(gè)會(huì)話永占帶寬,添加隨即公平隊(duì)列sfq.
tc qdisc add dev eth0 parent 1:10 handle 10: sfq perturb 10
#perturb:是多少秒后重新配置一次散列算法,默認(rèn)為10秒
#sfq,他可以防止一個(gè)段內(nèi)的一個(gè)ip占用整個(gè)帶寬

#使用u32創(chuàng)建過(guò)濾器
tc filter add dev eth0 protocol ip parent 1:0 prio 1 u32 match ip sport 22 flowid 1:10

#刪除隊(duì)列
tc qdisc del dev eth0 root

配置完成后加入本地啟動(dòng)文件:  
/etc/rc.local

git限速2:針對(duì)ip進(jìn)行限速

情景:
因?yàn)閹捹Y源有限(20Mbit≈2Mbyte)茁帽,使用git拉取代碼的時(shí)候?qū)е聨捹Y源告警玉罐,所以對(duì)git進(jìn)行限速,要求:內(nèi)網(wǎng)不限速潘拨;外網(wǎng)下載速度為1M左右吊输。(注意:此處需要注意單位轉(zhuǎn)換1byte=8bit)...

<腳本>

#!/bin/bash
#針對(duì)不同的ip進(jìn)行限速

#清空原有規(guī)則
tc qdisc del dev eth0 root

#創(chuàng)建根序列
tc qdisc add dev eth0 root handle 1: htb default 1

#創(chuàng)建一個(gè)主分類綁定所有帶寬資源(20M)
tc class add dev eth0 parent 1:0 classid 1:1 htb rate 20Mbit burst 15k

#創(chuàng)建子分類
tc class add dev eth0 parent 1:1 classid 1:10 htb rate 20Mbit ceil 10Mbit burst 15k
tc class add dev eth0 parent 1:1 classid 1:20 htb rate 20Mbit ceil 20Mbit burst 15k

#避免一個(gè)ip霸占帶寬資源(git1有講到)
tc qdisc add dev eth0 parent 1:10 handle 10: sfq perturb 10
tc qdisc add dev eth0 parent 1:20 handle 20: sfq perturb 10

#創(chuàng)建過(guò)濾器
#對(duì)所有ip限速
tc filter add dev eth0 protocol ip parent 1:0 prio 2 u32 match ip dst 0.0.0.0/0 flowid 1:10
#對(duì)內(nèi)網(wǎng)ip放行
tc filter add dev eth0 protocol ip parent 1:0 prio 1 u32 match ip dst 12.0.0.0/8 flowid 1:20

該過(guò)程遇到的問(wèn)題:

  • 未配置優(yōu)先級(jí)以至于只有一條規(guī)則生效(所有的ip都被限速)
    • 解決辦法:在過(guò)濾器中加入prio,指定規(guī)則的優(yōu)先級(jí)
  • 不知道本地帶寬是多大:
    • 解決辦法:直接給你一個(gè)很大很大的帶寬(100000....)铁追,對(duì)需要限速的ip分配指定的帶寬資源季蚂,然后把剩余的帶寬全部分配給內(nèi)網(wǎng)ip。琅束。扭屁。(簡(jiǎn)單粗暴有效)

4.3 應(yīng)用2:環(huán)境模擬實(shí)例

需求:

流量控制器上的以太網(wǎng)卡(eth0) 的IP地址為192.168.1.66,在其上建立一個(gè)CBQ隊(duì)列涩禀。假設(shè)包的平均大小為1000字節(jié)料滥,包間隔發(fā)送單元的大小為8字節(jié),可接收沖突的發(fā)送最長(zhǎng)包數(shù)目為20字節(jié)艾船。
假如有三種類型的流量需要控制:

  • 是發(fā)往主機(jī)1的葵腹,其IP地址為192.168.1.24。其流量帶寬控制在8Mbit屿岂,優(yōu)先級(jí)為2礁蔗;
  • 是發(fā)往主機(jī)2的,其IP地址為192.168.1.30雁社。其流量帶寬控制在1Mbit浴井,優(yōu)先級(jí)為1;
  • 是發(fā)往子網(wǎng)1的霉撵,其子網(wǎng)號(hào)為192.168.1.0磺浙,子網(wǎng)掩碼為255.255.255.0洪囤。流量帶寬控制在1Mbit,優(yōu)先級(jí)為6撕氧。
實(shí)現(xiàn):
建立隊(duì)列:

一般情況下瘤缩,針對(duì)一個(gè)網(wǎng)卡只需建立一個(gè)隊(duì)列。
將一個(gè)cbq隊(duì)列綁定到網(wǎng)絡(luò)物理設(shè)備eth0上伦泥,其編號(hào)為1:0剥啤;網(wǎng)絡(luò)物理設(shè)備eth0的實(shí)際帶寬為10 Mbit,包的平均大小為1000字節(jié)不脯;包間隔發(fā)送單元的大小為8字節(jié)府怯,最小傳輸包大小為64字節(jié)。

tc qdisc add dev eth0 root handle 1: cbq bandwidth 10Mbit avpkt 1000 cell 8 mpu 64
#cell:包間隔發(fā)送單元的大小為8字節(jié)

建立分類:

分類建立在隊(duì)列之上防楷。
一般情況下牺丙,針對(duì)一個(gè)隊(duì)列需建立一個(gè)根分類,然后再在其上建立子分類复局。對(duì)于分類冲簿,按其分類的編號(hào)順序起作用,編號(hào)小的優(yōu)先亿昏;一旦符合某個(gè)分類匹配規(guī)則峦剔,通過(guò)該分類發(fā)送數(shù)據(jù)包,則其后的分類不再起作用角钩。

1) 創(chuàng)建根分類1:1羊异;分配帶寬為10Mbit,優(yōu)先級(jí)別為8

tc class add dev eth0 parent 1:0 classid 1:1 cbq bandwidth 10Mbit rate 10Mbit maxburst 20 allot 1514 prio 8 avpkt 1000 cell 8 weight 1Mbit
#prio:用來(lái)指示借用帶寬時(shí)的競(jìng)爭(zhēng)力,prio越小,優(yōu)先級(jí)越高,競(jìng)爭(zhēng)力越強(qiáng).

該隊(duì)列的最大可用帶寬為10Mbit彤断,實(shí)際分配的帶寬為10Mbit野舶,可接收沖突的發(fā)送最長(zhǎng)包數(shù)目為20字節(jié);最大傳輸單元加MAC頭的大小為1514字節(jié)宰衙,優(yōu)先級(jí)別為8平道,包的平均大小為1000字節(jié),包間隔發(fā)送單元的大小為8字節(jié)供炼,相應(yīng)于實(shí)際帶寬的加權(quán)速率為1Mbit一屋。
2) 創(chuàng)建分類1:2,其父分類為1:1袋哼,分配帶寬為8Mbit冀墨,優(yōu)先級(jí)別為2

tc class add dev eth0 parent 1:1 classid 1:2 cbq bandwidth 10Mbit rate 8Mbit maxburst 20 allot 1514 prio 2 avpkt 1000 cell 8 weight 800Kbit split 1:0 bounded

該隊(duì)列的最大可用帶寬為10Mbit,實(shí)際分配的帶寬為 8Mbit涛贯,可接收沖突的發(fā)送最長(zhǎng)包數(shù)目為20字節(jié)诽嘉;最大傳輸單元加MAC頭的大小為1514字節(jié),優(yōu)先級(jí)別為1,包的平均大小為1000字節(jié)虫腋,包間隔發(fā)送單元的大小為8字節(jié)骄酗,相應(yīng)于實(shí)際帶寬的加權(quán)速率為800Kbit,分類的分離點(diǎn)為1:0悦冀,且不可借用未使用帶寬趋翻。
3)創(chuàng)建分類1:3,其父分類為1:1盒蟆,分配帶寬為1Mbit踏烙,優(yōu)先級(jí)別為1。

tc class add dev eth0 parent 1:1 classid 1:3 cbq bandwidth 10Mbit rate 1Mbit maxburst 20 allot 1514 prio 1 avpkt 1000 cell 8 weight 100Kbit split 1:0

該隊(duì)列的最大可用帶寬為10Mbit历等,實(shí)際分配的帶寬為 1Mbit讨惩,可接收沖突的發(fā)送最長(zhǎng)包數(shù)目為20字節(jié);最大傳輸單元加MAC頭的大小為1514字節(jié)募闲,優(yōu)先級(jí)別為2步脓,包的平均大小為1000字節(jié)愿待,包間隔發(fā)送單元的大小為8字節(jié)浩螺,相應(yīng)于實(shí)際帶寬的加權(quán)速率為100Kbit,分類的分離點(diǎn)為1:0仍侥。
4) 創(chuàng)建分類1:4要出,其父分類為1:1,分配帶寬為1Mbit农渊,優(yōu)先級(jí)別為6患蹂。

tc class add dev eth0 parent 1:1 classid 1:4 cbq bandwidth 10Mbit rate 1Mbit maxburst 20 allot 1514 prio 6 avpkt 1000 cell 8 weight 100Kbit split 1:0

建立過(guò)濾器

過(guò)濾器主要服務(wù)于分類。
一般只需針對(duì)根分類提供一個(gè)過(guò)濾器砸紊,然后為每個(gè)子分類提供路由映射传于。
1)應(yīng)用路由分類器到cbq隊(duì)列的根,父分類編號(hào)為1:0醉顽;過(guò)濾協(xié)議為ip沼溜,優(yōu)先級(jí)別為100,過(guò)濾器為基于路由表游添。

tc filter add dev eth0 parent 1:0 protocol ip prio 100 route

2)建立路由映射分類1:2, 1:3, 1:4

tc filter add dev eth0 parent 1:0 protocol ip prio 100 route to 2 flowid 1:2

tc filter add dev eth0 parent 1:0 protocol ip prio 100 route to 3 flowid 1:3

tc filter add dev eth0 parent 1:0 protocol ip prio 100 route to 4 flowid 1:4

建立路由

該路由是與前面所建立的路由映射一一對(duì)應(yīng)系草。
1)發(fā)往主機(jī)192.168.1.24的數(shù)據(jù)包通過(guò)分類2轉(zhuǎn)發(fā)(分類2的速率8Mbit)

ip route add 192.168.1.24 dev eth0 via 192.168.1.66 realm 2

2)發(fā)往主機(jī)192.168.1.30的數(shù)據(jù)包通過(guò)分類3轉(zhuǎn)發(fā)(分類3的速率1Mbit)

ip route add 192.168.1.30 dev eth0 via 192.168.1.66 realm 3

3)發(fā)往子網(wǎng)192.168.1.0/24的數(shù)據(jù)包通過(guò)分類4轉(zhuǎn)發(fā)(分類4的速率1Mbit)

ip route add 192.168.1.0/24 dev eth0 via 192.168.1.66 realm 4

注:一般對(duì)于流量控制器所直接連接的網(wǎng)段建議使用IP主機(jī)地址流量控制限制,不要使用子網(wǎng)流量控制限制唆涝。如一定需要對(duì)直連子網(wǎng)使用子網(wǎng)流量控制限制找都,則在建立該子網(wǎng)的路由映射前,需將原先由系統(tǒng)建立的路由刪除廊酣,才可完成相應(yīng)步驟能耻。

4.4 應(yīng)用3:MySQL數(shù)據(jù)庫(kù)同步數(shù)據(jù)限速方案

mysql1: 10.9.57.162 
may1:   10.12.1.45 
# mysql1上實(shí)施(限制到may1的流量: 8mbit)
tc qdisc add dev eth0 root handle 1: htb r2q 1
tc class add dev eth0 parent 1: classid 1:1 htb rate 8mbit ceil 8mbit
tc qdisc add dev eth0 parent 1:1 handle 10: sfq perturb 10
tc filter add dev eth0 parent 1: protocol ip prio 16 u32 match ip dst 10.12.1.45 flowid 1:1 # may1(限制到mysql1的流量: 8mbit)
tc qdisc del dev em1 root [ ] 
tc qdisc add dev  em1 root handle 2: htb r2q 1
tc class  add dev  em1 parent 2: classid 2:1 htb rate 8mbit ceil 8mbit
tc qdisc add dev  em1 parent 2:1 handle 11: sfq perturb 10
tc filter add dev  em1 parent 2: protocol ip prio 16 u32 match ip dst 10.9.57.162 flowid 2:1

監(jiān)視

主要包括對(duì)現(xiàn)有隊(duì)列、分類、過(guò)濾器和路由的狀況進(jìn)行監(jiān)視嚎京。
1)顯示隊(duì)列的狀況
簡(jiǎn)單顯示指定設(shè)備(這里為eth0)的隊(duì)列狀況

# tc qdisc ls dev eth0
qdisc cbq 1: rate 10Mbit (bounded,isolated) prio no-transmit

詳細(xì)顯示指定設(shè)備(這里為eth0)的隊(duì)列狀況

tc -s qdisc ls dev eth0

這里主要顯示了通過(guò)該隊(duì)列發(fā)送了13232個(gè)數(shù)據(jù)包嗡贺,數(shù)據(jù)流量為7646731個(gè)字節(jié),丟棄的包數(shù)目為0鞍帝,超過(guò)速率限制的包數(shù)目為0诫睬。
2)顯示分類的狀況
簡(jiǎn)單顯示指定設(shè)備(這里為eth0)的分類狀況

tc class ls dev eth0

詳細(xì)顯示指定設(shè)備(這里為eth0)的分類狀況

tc -s class ls dev eth0

這里主要顯示了通過(guò)不同分類發(fā)送的數(shù)據(jù)包,數(shù)據(jù)流量帕涌,丟棄的包數(shù)目摄凡,超過(guò)速率限制的包數(shù)目等等。其中根分類(class cbq 1:0)的狀況應(yīng)與隊(duì)列的狀況類似蚓曼。
例如亲澡,分類class cbq 1:4發(fā)送了8076個(gè)數(shù)據(jù)包,數(shù)據(jù)流量為5552879個(gè)字節(jié)纫版,丟棄的包數(shù)目為0床绪,超過(guò)速率限制的包數(shù)目為0。
顯示過(guò)濾器的狀況

tc -s filter ls dev eth0

這里flowid 1:2代表分類class cbq 1:2其弊,to 2代表通過(guò)路由2發(fā)送癞己。
顯示現(xiàn)有路由的狀況

ip route

如上所示,結(jié)尾包含有realm的顯示行是起作用的路由過(guò)濾器梭伐。

實(shí)例腳本

  • 限速
# 痹雅!/bin/sh
touch  /var/lock/subsys/local

echo  1  > /proc/sys/net/ipv4/ip_forward (激活轉(zhuǎn)發(fā))

route add default  gw  10.0.0.0  (這是加入電信網(wǎng)關(guān),如果你已設(shè)了不用這條)

DOWNLOAD=640Kbit (640/8 =80K ,我這里限制下載最高速度只能80K)
UPLOAD=640Kbit (640/8 =80K,上傳速度也限制在80K)
INET=192.168.0. (設(shè)置網(wǎng)段糊识,根據(jù)你的情況填)
IPS=1 (這個(gè)意思是從192.168.0.1開(kāi)始)
IPE=200 (我這設(shè)置是從IP為192.168.0.1-200這個(gè)網(wǎng)段限速绩社,根據(jù)自已的需要改)
ServerIP=253 (網(wǎng)關(guān)IP)
IDEV=eth0
ODEV=eth1

/sbin/tc  qdisc  del  dev  $IDEV root handle 10:
/sbin/tc  qdisc  del  dev  $ODEV  root handle  20:
/sbin/tc  qdisc  add  dev $IDEV  root  handle  10: cbq  bandwidth  100Mbit avpkt  1000
/sbin/tc  qdisc  add  dev  $ODEV  root  handle  20: cbq bandwidth  1Mbit  avpkt  1000
/sbin/tc  class  add  dev $IDEV  parent 10:0  classid  10:1  cbq  bandwidth  100Mbit  rate 100Mbit  allot 1514  weight  1Mbit  prio  8  maxburst  20  avpkt 1000
/sbin/tc  class  add  dev  $ODEV  parent  20:0  classid  20:1 cbq  bandwidth  1Mbit  rate  1Mbit  allot  1514  weitht  10Kbit  prio  8  maxburst  20  avpkt 1000

COUNTER=$IPS
while  [  $COUNTER  -le  $IPE  ] do
/sbin/tc  class  add  dev  $IDEV  parent  10:1  classid  10:1$COUNTER  cbq  banwidth  100Mbit  rate  
$DOWNLOAD  allot  1514  weight  20Kbit  prio  5  maxburst  20  avpkt  1000  bounded
/sbin/tc  qdisc  add  dev  $IDEV  parent  10:1$COUNTER  sfq  quantum  1514b  perturb15

/sbin/tc  filter  add  dev  $IDEV  parent  10:0  protocol  ip  prio  100  u32  match  ipdst  $INET$COUNTER  flowid  10:1$COUNTER COUNTER=` expr  $COUNTER  +  1  `
done

iptables  -t  nat  -A  POSTROUTING  -o  eth1  -s  192.168.0.0/24  -J  MASQUERADE

  • 模型
#!/bin/sh
tc qdisc del dev eth7 root &> /dev/null
tc qdisc del dev eth8 root &> /dev/null

#Add qdisc
tc qdisc add dev eth7 root handle 10: htb default 9998
tc qdisc add dev eth8 root handle 10: htb default 9998

#Add htb root node
tc class add dev eth7 parent 10: classid 10:9999 htb rate 1000000kbit ceil 1000000kbit
tc class add dev eth8 parent 10: classid 10:9999 htb rate 1000000kbit ceil 1000000kbit

#Add htb fake default node here
tc class add dev eth7 parent 10:9999 classid 10:9998 htb rate 1000000kbit ceil 1000000kbit
tc class add dev eth8 parent 10:9999 classid 10:9998 htb rate 1000000kbit ceil 1000000kbit

#Add rule node
tc class add dev eth7 parent 10:9999 classid 10:3 htb rate 1kbit ceil 50kbit
tc filter add dev eth7 parent 10: protocol ip handle 3 fw classid 10:3
tc class add dev eth8 parent 10:9999 classid 10:3 htb rate 1kbit ceil 50kbit
tc filter add dev eth8 parent 10: protocol ip handle 3 fw classid 10:3

#Add htb real default node here
tc class change dev eth7 classid 10:9998 htb rate 1kbit ceil 1000000kbit
tc class change dev eth8 classid 10:9998 htb rate 1kbit ceil 1000000kbit

tc

#創(chuàng)建一個(gè)主隊(duì)列
 tc qdisc add dev eth0 root handle 1: htb  default 1
#tc 隊(duì)列   添加 設(shè)置接口  root為最上層 句柄(做標(biāo)記用): 標(biāo)記類型 默認(rèn)使用1的class
#命令解釋:將一個(gè)htb隊(duì)列綁定在eth0上,編號(hào)為1:0,默認(rèn)歸類是1

 tc class add dev eth0 parent 1:0 classid1:30 htb rate 10mbit
#為eth0 下的root隊(duì)列1:0 添加分類并命名為 1:30 類型為htb 速度為10M

 tc class add dev eth0 parent 1:30 classid 1:31 htb rate 10mbit

tc qdisc add dev eth0 root tbf  match ip sport 22 0xffff rate 10mbit 

網(wǎng)絡(luò)速度測(cè)試的方法

測(cè)試本機(jī)網(wǎng)絡(luò)狀態(tài)

centos7系統(tǒng)

# yum install -y speedtest-cli
# speedtest-cli

測(cè)試來(lái)自某ip的下載

scp root@ip:/dir/filename  /dir/

wondershaper

了解完tc工具后再來(lái)看一個(gè)簡(jiǎn)單實(shí)用的限速工具——wondershaper赂苗。這個(gè)單詞看似很復(fù)雜愉耙,但是當(dāng)你看過(guò)源碼之后會(huì)發(fā)現(xiàn),這只不過(guò)是將tc一些簡(jiǎn)單的功能封裝成了一個(gè)shell腳本而已拌滋,安裝和使用方法如下:

  • 安裝
$ yum install epel-release -y # 依賴第三方庫(kù)
$ yum install wondershaper -y

  • 查看使用說(shuō)明:
$ wondershaper
Wonder Shaper 1.2.1

Usage: /usr/sbin/wondershaper [device] clean|[upload speed in Kb/s] [download speed in Kb/s]
Example: /usr/sbin/wondershaper eth0 20 500

https://bugzilla.redhat.com/enter_bug.cgi?product=Fedora&component=wondershaper

  • 示例:
# 將上行帶寬限制為1M朴沿,下行帶寬限制為10M
$ wondershaper eth0 1024 10240

# 清除原有規(guī)則 (兩個(gè)參數(shù)可以是任何字符)
$ wondershaper clean clean

# 查看已有規(guī)則 (查看eth0的規(guī)則)
$ wondershaper eth0

Note: 一般為3個(gè)參數(shù),第一個(gè)參數(shù)為網(wǎng)卡名鸠真,第二個(gè)上行速度(出)限制悯仙,第三個(gè)參數(shù)為下行速度(入)限制。

參考文章:
https://www.huaweicloud.com/articles/9d6581c20b6c10f60984eabc45e860bd.html
https://int64.me/2018/TC%20-%20Linux%20%e6%b5%81%e9%87%8f%e6%8e%a7%e5%88%b6%e5%b7%a5%e5%85%b7.html
https://cloud.tencent.com/developer/article/1721030

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
禁止轉(zhuǎn)載吠卷,如需轉(zhuǎn)載請(qǐng)通過(guò)簡(jiǎn)信或評(píng)論聯(lián)系作者锡垄。
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市祭隔,隨后出現(xiàn)的幾起案子货岭,更是在濱河造成了極大的恐慌路操,老刑警劉巖,帶你破解...
    沈念sama閱讀 206,968評(píng)論 6 482
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件千贯,死亡現(xiàn)場(chǎng)離奇詭異屯仗,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)搔谴,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,601評(píng)論 2 382
  • 文/潘曉璐 我一進(jìn)店門魁袜,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人敦第,你說(shuō)我怎么就攤上這事峰弹。” “怎么了芜果?”我有些...
    開(kāi)封第一講書(shū)人閱讀 153,220評(píng)論 0 344
  • 文/不壞的土叔 我叫張陵鞠呈,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我右钾,道長(zhǎng)蚁吝,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 55,416評(píng)論 1 279
  • 正文 為了忘掉前任舀射,我火速辦了婚禮窘茁,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘后控。我一直安慰自己庙曙,他們只是感情好空镜,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,425評(píng)論 5 374
  • 文/花漫 我一把揭開(kāi)白布浩淘。 她就那樣靜靜地躺著,像睡著了一般吴攒。 火紅的嫁衣襯著肌膚如雪张抄。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書(shū)人閱讀 49,144評(píng)論 1 285
  • 那天褒纲,我揣著相機(jī)與錄音裸扶,去河邊找鬼烫沙。 笑死,一個(gè)胖子當(dāng)著我的面吹牛极谊,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播安岂,決...
    沈念sama閱讀 38,432評(píng)論 3 401
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼轻猖,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了域那?” 一聲冷哼從身側(cè)響起咙边,我...
    開(kāi)封第一講書(shū)人閱讀 37,088評(píng)論 0 261
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后败许,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體王带,經(jīng)...
    沈念sama閱讀 43,586評(píng)論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,028評(píng)論 2 325
  • 正文 我和宋清朗相戀三年市殷,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了愕撰。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,137評(píng)論 1 334
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡醋寝,死狀恐怖盟戏,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情甥桂,我是刑警寧澤柿究,帶...
    沈念sama閱讀 33,783評(píng)論 4 324
  • 正文 年R本政府宣布,位于F島的核電站黄选,受9級(jí)特大地震影響蝇摸,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜办陷,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,343評(píng)論 3 307
  • 文/蒙蒙 一貌夕、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧民镜,春花似錦啡专、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,333評(píng)論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至鲸鹦,卻和暖如春慧库,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背馋嗜。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 31,559評(píng)論 1 262
  • 我被黑心中介騙來(lái)泰國(guó)打工齐板, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人葛菇。 一個(gè)月前我還...
    沈念sama閱讀 45,595評(píng)論 2 355
  • 正文 我出身青樓甘磨,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親眯停。 傳聞我的和親對(duì)象是個(gè)殘疾皇子济舆,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,901評(píng)論 2 345

推薦閱讀更多精彩內(nèi)容