我想模拟下面的情况:考虑到我有4个Ubuntu的服务器机器A,B,C和D.我想在机器A和机器C之间减less20%的networking带宽,在A和B之间减less10%使用networking模拟/节stream工具来做到这一点?
要做到这一点,你可以单独使用tc u32filter或结合使用iptables标记 (如果你不想学习复杂的filter语法可能更直接)。 我会在以下的post里详细介绍以前的解决scheme。
举个例子,让我们考虑运行10Mbit / s虚拟接口的A,B,C和D。
你基本上想要:
为了模拟这个,我将创build4个networking命名空间和插入网桥的虚拟以太网接口。
当然,在你的情况下,你将使用真正的网卡,网桥将成为你的网关或交换机,这取决于你的基础设施。
所以在我的模拟中,我们将在10.0.0.0/24networking中进行以下设置:
10.0.0.254 +-------+ | | | br0 | | | +---+---+ | | veth{A..D}.peer | +------------+------+-----+------------+ | | | | vethA | vethB | vethC | vethD | +---+---+ +---+---+ +---+---+ +---+---+ | | | | | | | | | A | | B | | C | | D | | | | | | | | | +-------+ +-------+ +-------+ +-------+ 10.0.0.1 10.0.0.2 10.0.0.3 10.0.0.4
首先,设置阶段,所以你可以理解它是由什么组成的,如果你不熟悉它就跳过它,没什么大不了的。 但是你必须知道的是,命令ip netns exec <namespace> <command>允许在networking命名空间(即在前一个绘图的一个框中)执行一个命令。 这也将在下一节中使用。
# Create the bridge ip link add br0 type bridge # Create network namespaces and veth interfaces and plug them into the bridge for host in {A..D} ; do ip link netns add ${host} ip link add veth${host} type veth peer name veth${host}.peer ip link set dev veth${host}.peer master br0 ip link set dev veth${host} netns ${host} ip netns exec ${host} ip link set veth${host} up done # Assign IPs ip addr add 10.0.0.254/24 dev br0 ip netns exec A ip addr add 10.0.0.1/24 dev vethA ip netns exec B ip addr add 10.0.0.2/24 dev vethB ip netns exec C ip addr add 10.0.0.3/24 dev vethC ip netns exec D ip addr add 10.0.0.4/24 dev vethD
所以在这一点上,我们有前面描述的设置。
现在是时候进入交通pipe制,以得到你想要的。 tc工具允许您添加排队规则:
它有3个概念: qdisc , 类和filter 。 这些概念可以用来设置复杂的数据包stream量pipe理,并根据您想要的任何标准/条件优先处理stream量。
简而言之 :
所有这些通常作为一棵树叶子是qdiscs和类是节点。 树或子树的根将被声明为<id>:并且子节点将被声明为<parent_id>:<children_id> 。 记住这个语法。
对于你的情况,让我们拿A并渲染你想用tc设置的树:
1: | | | 1:1 / | \ / | \ / | \ 1:10 1:20 1:30 | | | | | | :10 :20 :30
说明:
1:是连接到设备vethA的root qdisc,它将明确地作为htb令牌桶的htb (根据OS,设备的默认htb是pfifo或pfifo_fast )。 它特别适合于带宽pipe理。 没有在这个级别定义的filter匹配的包将去1:30级。 1:1将是一个htb类,将设备的整个stream量限制为10 Mbit / s。 1:10将是一个htb级别,将输出stream量限制为9 Mbit / s(10 Mbit / s的90%)。 1:20将是一个htb级,将输出stream量限制为8 Mbit / s(80%的10 Mbit / s)。 1:30将是一个htb级别的stream量限制到10 Mbit / s(后备)。 :10, :20, :30是随机公平队列的sfq 。 换句话说,这些qdiscs将确保公平传输调度基于stream量。 整个事情由以下命令设置:
ip netns exec A tc qdisc add dev vethA root handle 1: htb default 30 ip netns exec A tc class add dev vethA parent 1: classid 1:1 htb rate 10mbit burst 15k ip netns exec A tc class add dev vethA parent 1:1 classid 1:10 htb rate 9mbit burst 15k ip netns exec A tc class add dev vethA parent 1:1 classid 1:20 htb rate 8mbit burst 15k ip netns exec A tc class add dev vethA parent 1:1 classid 1:30 htb rate 10mbit burst 15k ip netns exec A tc qdsic add dev vethA parent 1:10 handle 10: sfq perturb 10 ip netns exec A tc qdisc add dev vethA parent 1:20 handle 20: sfq perturb 10 ip netns exec A tc qdisc add dev vethA parent 1:30 handle 30: sfq perturb 10
最后我们需要添加filter,目标IP等于B的IP数据包将进入1:10级,目标IP等于C的IP数据包将进入1:20级:
ip netns exec A tc filter add dev vethA parent 1: protocol ip prio 1 u32 match ip dst 10.0.0.2/32 flowid 1:10 ip netns exec A tc filter add dev vethA parent 1: protocol ip prio 2 u32 match ip dst 10.0.0.3/32 flowid 1:20
现在你明白了,你需要在B和C上添加类似的tc规则,这样从这些钻机上向A的传输也被整形。
现在我们来testing一下。 为此,我习惯于使用iperf来玩游戏,它只包含一个可以作为客户端或服务器运行的二进制文件,并且会在两台主机之间自动发送尽可能多的stream量。
在A和B之间:
$ ip netns exec B iperf -s -p 8001 ... $ ip netns exec A iperf -c 10.0.0.2 -p 8001 -t 10 -i 2 ------------------------------------------------------------ Client connecting to 10.0.0.2, TCP port 8001 TCP window size: 21.0 KByte (default) ------------------------------------------------------------ [ 5] local 10.0.0.1 port 58191 connected with 10.0.0.2 port 8001 [ ID] Interval Transfer Bandwidth [ 5] 0.0- 2.0 sec 2.38 MBytes 9.96 Mbits/sec [ 5] 2.0- 4.0 sec 2.12 MBytes 8.91 Mbits/sec [ 5] 4.0- 6.0 sec 2.00 MBytes 8.39 Mbits/sec [ 5] 6.0- 8.0 sec 2.12 MBytes 8.91 Mbits/sec [ 5] 8.0-10.0 sec 2.00 MBytes 8.39 Mbits/sec [ 5] 0.0-10.1 sec 10.8 MBytes 8.91 Mbits/sec
我们获得了9 Mbit / s的带宽限制。
在A和C之间:
$ ip netns exec C iperf -s -p 8001 ... $ ip netns exec A iperf -c 10.0.0.3 -p 8001 -t 10 -i 2 ------------------------------------------------------------ Client connecting to 10.0.0.3, TCP port 8001 TCP window size: 21.0 KByte (default) ------------------------------------------------------------ [ 5] local 10.0.0.1 port 58522 connected with 10.0.0.3 port 8001 [ ID] Interval Transfer Bandwidth [ 5] 0.0- 2.0 sec 2.25 MBytes 9.44 Mbits/sec [ 5] 2.0- 4.0 sec 1.75 MBytes 7.34 Mbits/sec [ 5] 4.0- 6.0 sec 1.88 MBytes 7.86 Mbits/sec [ 5] 6.0- 8.0 sec 1.88 MBytes 7.86 Mbits/sec [ 5] 8.0-10.0 sec 1.75 MBytes 7.34 Mbits/sec [ 5] 0.0-10.1 sec 9.62 MBytes 7.98 Mbits/sec
我们获得了8 Mbit / s的带宽限制。
在A和D之间:
$ ip netns exec D iperf -s -p 8001 ... $ ip netns exec A iperf -c 10.0.0.4 -p 8001 -t 10 -i 2 ------------------------------------------------------------ Client connecting to 10.0.0.4, TCP port 8001 TCP window size: 21.0 KByte (default) ------------------------------------------------------------ [ 5] local 10.0.0.1 port 40614 connected with 10.0.0.4 port 8001 [ ID] Interval Transfer Bandwidth [ 5] 0.0- 2.0 sec 2.62 MBytes 11.0 Mbits/sec [ 5] 2.0- 4.0 sec 2.25 MBytes 9.44 Mbits/sec [ 5] 4.0- 6.0 sec 2.38 MBytes 9.96 Mbits/sec [ 5] 6.0- 8.0 sec 2.25 MBytes 9.44 Mbits/sec [ 5] 8.0-10.0 sec 2.38 MBytes 9.96 Mbits/sec [ 5] 0.0-10.2 sec 12.0 MBytes 9.89 Mbits/sec
这里我们已经达到了10Mbit / s的虚拟接口全速。
请注意,通过调整适当的参数,可以在htb类中更好地处理每个运行的第一个度量的爆发。
去除 :
1:上的优先级1的筛选器: tc filter del dev vethA parent 1: prio 1 u32 。 1:上的所有filter: tc filter del dev vethA parent 1: 1:20及其子女: tc class del dev vethA parent 1:1 classid 1:20 。 tc qdisc del dev vethA 。 清理模拟集:
# Remove veth pairs and network namespaces for host in {A..D} ; do ip link del dev veth${host}.peer ip netns del ${host} done # Remove the bridge ip link del dev br0
Ubuntu有从FreeBSD移植的IPFW,IPFW有DUMMYNET,可以pipe理各种networking参数 – 带宽,延迟,丢包率等。
最好是使用现在集成的(至less在Ubuntu服务器上)netem模块的tc工具。 你可以在这篇文章中find更多的信息从Stackoverflow 。
涓stream运作良好。
这个讨论显示了一些限制: https : //unix.stackexchange.com/questions/109973/how-to-change-speed-limit-of-running-trickle-instance