LinuxTC(TrafficControl)框架原理解析


近日的工作多多少少和Linux的流控有点关系,自打几年前知道有TC这么一个玩意儿并且多多少少理解了它的原理之后,我就没有再动过它,因为我不喜欢TC命令行,实在是太繁琐了,iptables命令行也比较繁琐,但是比TC命令行直观,而TC命令行则太过于技术化。也许是我对TC框架没有对Netfilter框架理解深刻吧,也许是的。iptables/Netfilter对应的就是tc/TC。

\


不光是控制逻辑的组织,就连Linux在实现UNIX进程模型时,也采用了这种树形的递归控制逻辑,每一个层次都是一个两层的树,下图展示了这个模型:

\


可以看出,递归控制是分形的,如果能用立体的图展示会更好些,对于上图而言,除了叶子节点之外的每一个节点都是一颗独立的小树,不管是大树还是小树,对于控制逻辑或者组织逻辑而言,其性质是完全一样的。
1.将整个带宽按照2:3的比例分给TCP和UDP;


\


但是事情远非想象的那个单纯,虽然上面的图已经让你看出了TC框架的端倪,然而对于实现它却没有一点帮助。几个典型的问题摆在那里,你怎么甄别数据包到不同的队列,图中的非叶子节点要呈现成什么数据结构,既然不是真正的队列却又要有队列的行为,那么如何表达它们?...
1.对于叶子节点,真正排入一个真实的队列或者从真正的队列拉出一个数据包;

vcD48cD48aW1nIHNyYz0="http://www.2cto.com/uploadfile/Collfiles/20141027/20141027091624109.jpg" alt="\" />


可以看到,我并没有用那个经典的“队列规程,类别,过滤器”三元组来定义TC框架,而是用一种递归控制的意义来解释。如果用经典三元组来套在这幅图上,就会是下面这个样子,注意,我删去了不必要的文字,这样图不至于太过混乱,需要文字的请参考上图:

\


可见,万变不离其衷或者说英雄所见略同。
1.实现一个新的Qdisc,其内置一个简单的FIFO队列,enqueue操作进行从Netfilter移植过来的matches/target,所有ACCEPT的数据包排入FIFO;


\


对于第2点,比较简单,其本质就是在那个菱形中做文章,放大后的菱形如下图所示:

\


这样就用TC框架实现了防火墙的功能以及NAT的功能,这是我一直以来的愿望。其实我早就知道这件事,只是我不太喜欢TC的命令,因为它配置起来太技术化了,维护起来极其困难,甚至比iptables规则维护起来都困难,而维护是超级重要的,它甚至比你想到如何书写这个规则更重要,因为如何书写是一瞬间的事,如果你有足够的积累,那么一瞬间你就能搞定,如果你碰到了难题,敢说灵感的显现也是一瞬间的,比如酒后,但是维护却是长久的事,且维护的人不一定是你自己,你必须要为别人考虑,因为技术社会是利他的社会。


看我的文章,你可能很难得到那种复制了之后直接粘贴上就能用的东西,代码省略了,命令省略了,就算是我自己,在看到自己多年前写的东西时,十分想快速运行点什么,但是没有这样的东西。可是我觉得,思想大于实现,如果你理解了实现背后或者现实背后的本质,那么你就会得心应手,游刃有余。

相关内容