基于Linux Network Namespace的Mininet架构分析

Mininet作为一个轻量级的SDN仿真工具,在其系统实现架构中充分利用了Linux命名空间内核技术,其中Linux Network Namespace机制更是Mininet软件架构的基石,对网络资源的模拟发挥着重要作用。其实Linux Network Namespace在OpenStack和Docker等开源项目中也广泛应用。

什么是Linux Network Namespace? 从Linux 2.6.24版的内核开始,Linux 逐渐支持6种不同类型的命名空间。这其中包括进程间通信(IPC)的命名空间、进程命名空间、网络命名空间、挂载命名空间、UTS 命名空间、 用户命名空间。通过命名空间技术使得用户创建的进程能够与系统分离得更加彻底,从而不需要使用更多的底层虚拟化技术。Linux Namespaces机制提供一种资源隔离方案,使得PID、Network、IPC等系统资源不再具有全局性,而是属于某个特定的Namespace。每个Namespace下的资源对于其他Namespace下的资源都是透明,不可见的。因此在操作系统层面上看,就会出现多个相同pid的进程。而在用户层面上只能看到属于用户自己Namespace下的资源,例如使用ps命令只能列出自己Namespace下的进程。这样每个Namespace看上去就像一个单独的Linux系统。Linux的命名空间技术架构如下图所示:

Network namespace主要提供了网络资源的隔离能力,包括网络设备、IPv4和IPv6协议栈、IP路由表、防火墙、/proc/net目录、/sys/class/net目录、端口(socket)等等。从网络命名空间的角度看,它代表着分配给一个或多个进程的私有网络资源集合。其主要特性集中在虚拟化和隔离。每个Linux container拥有其自己的网络设备(虚拟的)和用于绑定自己网络端口号的应用程序。主机上合适的路由规则可以将网络数据包和特定container相关的网络设备关联。网络命名空间的主要应用场景包括:1、多个网络命名空间可以拥有eth0和lo等网络设备;2、多个Apache服务器进程可以在不同网络命名空间的80端口上进行监听;3、一个进程不能嗅探其他网络命名空间的流量;4、一个进程不能关闭其他网络命名空间的接口。

后台进程可以运行在不同网络命名空间内的相同端口上,用户还可以自己虚拟出网卡。一个物理的网络设备最多存在于一个Network namespace中,你可以通过创建veth pair(虚拟网络设备对)在不同的Network namespace间创建通道进行通信。veth pair是用于不同Network namespace间进行通信的方式,veth pair将一个Network namespace数据发往另一个Network namespace的veth。

简单veth pair通信机制

多Network namespace借助bridge进行通信

Mininet如何使用网络命名空间技术? Mininet使用Linux Network Namespaces来创建虚拟节点,默认情况下,在仿真网络中Mininet会为每一个host创建一个新的网络命名空间,同时在root Namespace(根进程命名空间)运行交换机和控制器的进程,因此这两个进程就共享同一个网络命名空间。由于每个主机都有各自独立的网络命名空间,我们就可以进行个性化的网络配置和网络程序部署。由于命名空间的虚拟技术没有提供类似于虚拟机的持久化能力,所以在Mininet关闭时不能保存所有的配置。

Mininet使用网络命名空间来让不同的Host进程拥有独立的网络上下文。在如下的示例中,两个虚拟主机H1和H2连接到交换机S1,通过Bash来模拟H1和H2,交换机S1运行在Linux内核运行的root namespace。H1和H2就拥有自己的网络命名空间以及私有网络接口h1-eth0和h2-eth0。交换机S1有两个端口s1-eth0和s1-eth1,通过veth pair与对应的主机接口相连,这样H1和H2就可以通过S1进行通信。s1-eth0和s1-eth1间的数据包转发通过软件交换机完成,它运行在root namespace并使用物理接口eth0,等待控制器的指令。

其实基于Linux Network Namespace就可以原生支持操作系统层级的虚拟化,就可以被用来进行网络仿真。而Mininet工具使用Python语言对网络仿真过程所涉及的节点、拓扑、链路等进行了封装抽象,便于科研人员迅速开展仿真工作。Mininet创建的Network namespace是nameless的,所以通过ip netns list命令是查看不到的,而通过ip netns add命令创建的namespace是带name的,这是两者最明显的区别之处。这其中ip命令是iproute2软件包里面的一个强大的网络配置工具,它能够替代一些传统的网络管理工具,例如ifconfig、route等,使用权限为超级用户。几乎所有的Linux发行版本都支持该命令。

下面就看看两个具体的示例,一个是通过ip命令创建网络命名空间进行实验,另一个是通过Mininet的命令进行实验。两者相比,Mininet就凸显出优势,实验用户可以不再关心底层系统实现,而聚焦在上层实验逻辑上。

示例一:

# Create host namespaces
ip netns add h1
ip netns add h2
# Create switch
ovs-vsctl add-br s1
# Create links
ip link add h1-eth0 type veth peer name s1-eth1
ip link add h2-eth0 type veth peer name s1-eth2
ip link show
# Move host ports into namespaces
ip link set h1-eth0 netns h1
ip link set h2-eth0 netns h2
ip netns exec h1 ip link show
ip netns exec h2 ip link show
# Connect switch ports to OVS
ovs-vsctl add-port s1 s1-eth1
ovs-vsctl add-port s1 s1-eth2
ovs-vsctl show
# Set up OpenFlow controller
ovs-vsctl set-controller s1 tcp:127.0.0.1
ovs-controller ptcp: &
ovs-vsctl show
# Configure network
ip netns exec h1 ifconfig h1-eth0 10.1
ip netns exec h1 ifconfig lo up
ip netns exec h2 ifconfig h2-eth0 10.2
ip netns exec h1 ifconfig lo up
ifconfig s1-eth1 up
ifconfig s1-eth2 up
# Test network
ip netns exec h1 ping -c1 10.2

示例二:

sudo mn --topo=single,2

然后使用pingall命令进行类似的实验

其实从Mininet的util.py中makeIntfPair、moveIntfNoRetry、moveIntf等函数实现,以及link.py文件中对makeIntfPair函数的调用可以看出一些端倪。在makeIntfPair函数中实现了接口管理,包括创建一对veth接口、关联node接口、建立连接映射等。Mininet通过对IP命令的封装实现了基于Linux Network namespace的网络构建。

参考资料: 1、介绍 Linux 的命名空间。https://linux.cn/article-5019-1.html 2、Docker背后的内核知识:命名空间资源隔离。http://linux.cn/article-5057-6.html 3、 Linux内核的namespace机制分析。http://blog.chinaunix.net/uid-20788636-id-4479145.html 4、Docker实践(4)—network namespace与veth pair。http://www.cnblogs.com/hustcat/p/3928261.html 5、mininet与namespace。http://vinllen.com/mininetyu-namespace/ 6、Mininet Walkthrough。http://mininet.org/walkthrough 7、Mininet运作原理。http://hwchiu.logdown.com/posts/221370-mininet-parsing 8、Testing SDN behavior with Mininet。http://www.linux-magazine.com/Issues/2014/162/Mininet 9、Mininet network simulator review。

http://www.brianlinkletter.com/mininet-test-drive/

10、Mininet中虚拟机构成的分析。http://richardzhao.me/?p=369 11、linux IP 命令使用举例。http://blog.csdn.net/radkitty/article/details/3022181

原文发布于微信公众号 - SDNLAB(SDNLAB)

原文发表时间:2015-07-28

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏deed博客

改变Android手机软件安装位置方法

1797
来自专栏腾讯移动品质中心TMQ的专栏

像 google 一样测试系列之五:流程与覆盖率篇

有了用例,还需持续跑起来,并能有覆盖率。如何让 Local Unit Tests和Instrumented Tests 都支持脚本执行?

2301
来自专栏美团技术团队

【美团技术博客】Docker系列之二:基于容器的自动构建

自动构建系统是从美团的自动部署系统发展出来的一个新功能。每当开发人员提交代码到仓库后,系统会自动根据开发人员定制的构建配置,启动新的Docker容器,在其中对源...

40010
来自专栏CSDN技术头条

运用Kubernetes进行分布式负载测试

本文为CSDN原创编译文章,禁止转载。 负载测试是开发后台基础架构的重要一环,它不但能够演示系统在真实需求面前的性能表现,还可以通过模拟用户与设备行为,在应用程...

2146
来自专栏Coding+

使用 youtube-dl 下载网络视频

youtube-dl 是一个命令行程序,用于从 YouTube.com 和其他几个网站下载视频。它需要 Python 解释器,版本2.6,2.7或3.2+,它是...

1.7K2
来自专栏容器云生态

Mesos+Marathon+Docker构建docker集群化管理

由Docker引领的容器技术最近一年在生产环境叫嚣的比较厉害,由于Docker本身拥有的一些特性,使得越来越多的人愿意并且想尝试在生产环境构建Docker,有关...

2815
来自专栏Jerry的SAP技术分享

C4C Product Price List的模型中和有效期相关的两个字段

SAP C4C的price list实例可以在工作中心Products,视图Price Lists里看到。

1567
来自专栏PHP技术大全

使用PHP结合Ffmpeg快速搭建流媒体服务实践

笔者想将自己收藏的一些电影放到网站上可以用来随时播放,不过遇到了一个问题,便是如果直接将MP4文件放放到网站目录当中,手机端必须下载整个视频才可以播放,而如果跨...

4764
来自专栏编程坑太多

『中级篇』overlay网络和etcd实现多机的容器通信(31)

PS:本次通过第三方工具etcd分布式的方式完成2台机器,2个容器组件网络,实现相互的访问,这里只是通过ping的方式,如果按照上次说的 flask-redis...

922
来自专栏程序人生 阅读快乐

自建DNS服务器

不晓得为撒,用网上的一些公共DNS服务的时候,总是莫名其妙的有些网站无法解析,有时候114能解析,阿里DNS不行或者腾讯DNS不行,导致总是来回切换DNS,很是...

1K2

扫码关注云+社区

领取腾讯云代金券