网络:云中网络

从物理机到虚拟机

数据中心里面堆着一大片一大片的机器,用网络连接起来,机器数目一旦非常多,人们就发现,维护这么一大片机器还挺麻烦的,有好多不灵活的地方。

  • 采购不灵活:如果客户需要一台电脑,那就需要自己采购、上架、插网线、安装操作系统,周期非常长。一旦采购了一用就N年,不能退货,哪怕业务不做了,机器还在数据中心里留着。
  • 运维不灵活:一旦需要扩容CPU、内存、硬盘,都需要去机房手动弄,非常麻烦。
  • 规格不灵活:采购的机器往往动不动几百G的内存,而每个应用往往可能只需要4核8G,所以很多应用混合部署在上面,端口各种冲突,容易相互影响。
  • 复用不灵活:一台机器,一旦一个用户不用了,给另外一个用户,那就需要重装操作系统。因为原来的操作系统可能遗留很多数据,非常麻烦。

为了解决这些问题,人民发明了一种叫做虚拟机的东西,并给予它产生了云计算技术。

  • 虚拟机可以扔你灵活的指定CPU的数目、内存大小、硬盘大小,网卡个数,然后在一台电脑里创建多台电脑,不用的时候,一点就删除没有了
  • 在数据中心里面,也有一种类似的开源技术qemu-kvm,能让你在一台巨大的物理机里面,隔出一台台小的机器。这套软件就能解决上面的问题:一点就能创建,一点就能销毁。你想要多大就能多大,每次创建的系统还是新的。

为什么能做到这样呢?

  • 关键在于用软件模拟硬件
  • 数据中心里面用的qemu-kvm,emu就是emulator(模拟器)的意思,主要会模拟CPU、内存、网络、硬盘,使得虚拟机感觉自己在使用独立的设备,但是真正使用的时候,当然还是使用物理的设备
  • 比如,多个虚拟机轮流使用物理CPU,内存也是使用虚拟内存映射的方式,最终映射到物理内存上。硬盘在一个大的文件系统上创建一个N个G的文件,作为虚拟机的硬盘
  • 简单来讲,虚拟化软件就像一个“骗子”,向上“骗”虚拟机里面的应用,让他们感觉在独享资源,其实自己傻也没有,全部向下从物理机里面弄

网络网卡的原理

那网络时如何“骗”应用的呢?如何将虚拟机的网络与物理机的网络连接起来?

  • 首先,虚拟机要有一张网卡。对于 qemu-kvm 来说,这是通过 Linux 上的一种 TUN/TAP 技术来实现的
  • 虚拟机是物理机上跑着的一个软件,这个软件可以像其他应用打开文件一样,打开一个称为TUN/TAP的char dev(字符设备文件)。打开了这个字符设备文件之后,在物理机上就能看到一张虚拟TAP网卡
  • 虚拟化软件作为“骗子”,会将打开的这个文件,在虚拟机里面虚拟出一张网卡,让虚拟机里面的应用觉得他们真的有一张网卡。于是,所有的网络包都往这里发
  • 当然,网络包会到虚拟机化软件这里。它会将网络流转换成文件流,写入字符设备,就像写一个文件一样。内核中TUN/TAP字符设备驱动会收到这个写入的文件流,交给TUN/TAP的虚拟网卡驱动。这个驱动将文件流再次转成网络包,交给TCP/IP协议栈,最终从虚拟TAP网卡发出来,成为标准的网络包
    在这里插入图片描述
    就这样,几经转手,数据终于从虚拟机里面,发到了虚拟机外面。

虚拟网卡连接到云中

我们就这样有了虚拟TAP网卡。接下来就要看,这个卡怎么接入庞大的数据中心网络中。

在接入之前,我们先来看,云计算中的网络都需要注意到哪些点:

  • 共享:尽管每个虚拟机都会有一个或者多个虚拟网卡,但是物理机器上可能只有有限的网卡。那这么多的虚拟网卡如何共享同一个出口
  • 隔离:分两个方面,一个是安全隔离,两个虚拟机可能属于两个用户,那怎么保证一个用户的数据不被另一个用户窃听?一个是流量隔离,两个虚拟机,如果有一个疯狂下片,会不会导致另外一个上不了网
  • 互通:分两个方面,一个是如果同一个机器上的两个虚拟机,属于同一个用户的话,这两个如何相互通信?另一个是如果不同物理机上的两条虚拟机,属于同一个用户的话,这两个如何相互通信。
  • 灵活:虚拟机和物理不同,会经常创建、删除,从一个机器漂移到另一台机器,有的互通,有的不通等等,灵活性比物理网络要好很多,需要能够灵活配置。

共享和互通问题

首先,一台物理机上有多个虚拟机,有多个虚拟网卡,这些虚拟网卡如何连在一起,进行相互访问。

还记得我们在大学宿舍里做的事情吗?你可以想象你的物理机就是你们宿舍,虚拟机就是你的个人电脑,这些电脑应该怎么连接起来呢?当然应该买一个交换机。

在虚拟机上,应该有一个虚拟的交换机,在Linux上有一个命令叫做brctl,可以创建虚拟的网桥brctl addbr br0。创建出来之后,将两个虚拟机的虚拟网卡,都连接到虚拟网桥brctl addif br0 tap0上,这样将两个虚拟机配置相同的子网字段,两台虚拟机就能够相互通信了。

在这里插入图片描述

那这些虚拟机如何连外网呢?在桌面虚拟化软件上,我们能看懂下面选项。

在这里插入图片描述
这里面,host-only的网络对应的,其实就是上面两个虚拟机连到一个br0虚拟网桥上,而且不考虑访问外部的场景,只要虚拟机之间能够相互访问就可以了。

如果要访问外部,往往有两种方式。

一种方法叫做桥接

如果在桌面虚拟化软件上选择桥接网络,则在你的笔记本电脑上,就会形成下面的结构

  • 每个虚拟机都会有虚拟网卡,在你的笔记本电脑上,会发现多了几个网卡,其实是虚拟交换机。这个虚拟交换机将虚拟机连接在一起。
  • 在桥接模式下,物理网卡也连接到这个虚拟交互及上,物理机在物理 网卡在桌面虚拟化软件上,在“界面名称”那里选定。
    在这里插入图片描述
  • 如果使用桥接网络,当你登录虚拟机里看IP地址的时候会发现,你的虚拟机的地址和你的笔记本电脑的,以及你旁边的同事的电脑的网段是一个网段。这是为什么呢?这其实相当于将物理机和虚 拟机放在同一个网桥上,相当于这个网桥上有三台机器,是一个网段的。具体如下如图所示:
    在这里插入图片描述
  • 在数据中心里面,采用的也是类似的技术,只不过都是Linux,在每台机器上都创建网桥br0,虚拟机的网卡都连到br0上,物理网卡也连到br0上,所有的br0都通过物理网卡出来连接到物理交换机上

在这里插入图片描述

  • 换一个角度看待这个拓扑图。同样是将网络打平,虚拟机会和你的物理网络具有相同的网段。
    在这里插入图片描述
  • 在这种方式下,不仅解决了同一台机器的互通问题,也解决了跨物理机的互通问题,因为都在一个二层网络里面,彼此用相同的网段访问就可以了。但是当规模很大的时候,会存在问题
    • 在一个二层网络中,最大的问题是广播。一个数据中心的物理机已经很多了,广播已经非常严重,需要通过VLAN进行划分。
    • 如果使用了虚拟机,假设一台物理机里面创建了10台虚拟机,全部在一个二层网络里面,那么广播会很严重,所以除非你是桌面虚拟机或者数据中心规模比较小,才可以使用这种相对比较简单的方式

另一种方式称为NAT

  • 如果在桌面虚拟化软件中使用NAT模式,则网络结构如下:
    在这里插入图片描述
  • 在这种方式下,虚拟机的网络是虚拟机的,物理机的网络时物理机的,两个不相同。虚拟机要想访问物理机的时候,需要将地址NAT转化称为物理机的地址。
  • 除此之外,它会在笔记本电脑里面内置一个DHCP服务器,为笔记本电脑上的虚拟机动态分配IP地址。因为虚拟机的网络自成体系,需要进行IP管理。为什么桥接方式不需要呢?因为桥接将网络打通了,虚拟机的IP地址应该由物理网络的DHCP服务器分配
  • 在数据中心里面,也是使用类似的方式。虚拟机是你的电脑,路由器和DHCP Server相当于家用路由器,物理网卡相当于外网接口,用于访问互联网,使用电脑都通过内网网卡连接到一个网桥br0上,虚拟机要想访问互联网,需要通过br0连到路由器上,然后通过路由器将请求NAT成为物理网络的地址,转发到物理网络

在这里插入图片描述

  • 如果是你自己登录到物理机上做个简单配置,你可以简化一下。例如将虚拟机所在网络的网关的地址直接配置到br0上,不用DHCP Server,手动配置每台虚拟机的IP地址,通过命令iptables -t nat -A POSTROUTING -o ethX -j MASQUERADE,直接在物理网卡ethX上进行NAT,所有从这个网卡出去的包都NAT成这个网卡的地址。通过设置net.ipv4.ip_forward = 1,开启物理机的转发功能,直接做路由器,而不用单独的路由器,这样虚拟机就能直接上网了
    在这里插入图片描述

隔离问题

如果一台机器上的两个虚拟机不属于同一个用户,怎么办呢?

还在brctl创建的网桥也是支持VLAN功能的,可以设置两个虚拟机的tag,这样在这个虚拟网桥上,两个虚拟机是不互通的。

但是如何跨物理机互通,并且实现VLAN的隔离呢?由于brctl创建的网桥上面的tag是没有办法在网桥范围之外起作用的,所以我们需要找其他的方式。

有一个命令vconfig,可以基于物理网卡eth0创建待VLAN的虚拟网卡,所有从这个虚拟网卡出去的包,都带这个VLAN,这样,跨物理机的互通和隔离就可以通过这个网卡实现

在这里插入图片描述

首先为每个用户分配不同的VLAN。比如有一个用户VLAN10,一个用户VLAN20,在一台物理机上,基于物理网卡,为每个用户用vconfig创建一个带VLAN的网卡。不同的用户使用不同的虚拟网桥,带VLAN的虚拟网卡也连接到虚拟网桥上。

这样是否能够保证两个用户的隔离性呢?不同的用户由于网桥不通,不能相互通信,一旦出了网桥,由于VLAN不同,也不会将包转发到另一个网桥上。另外,出了物理机,也是带着VLAN ID的。只要物理机也是支持VLAN的,到达另一台物理机的时候,VLAN ID依然存在,它只会将包转发给相同VLAN的网卡和网桥,所以跨物理机,不同的VLAN也不会相互通信。

使用brctl创建出来的网桥功能是简单的,基于VLAN的虚拟网卡也能实现简单的隔离。但是这都不是大规模平台能够满足的,一个是VLAN的隔离,数目太少,VLAN ID只有4096个。另一个原因是配置不灵活,谁和谁通,谁和谁不通,流量的隔离也没有实现,还有大量改进的空间

网络安全

对于公有云上的虚拟机,建议仅仅开放需要的端口,而将其他的端口一概关闭。这个时候,你只要通过安全措施守护号这个唯一的入口就可以了。采用的方式常常是ACL(Access Control List,访问控制列表)来控制IP和端口。设置好规则之后,只有指定的IP段能够访问指定的开放接口。这些规则的集合常称为安全组。那安全组是怎么实现的呢?

我们来复习一下,当一个网络包进入一台机器的时候,都会做什么事情?

  • 首先拿下MAC头看看,是不是我的(在路由判断之前,这个节点我们称为PREROUTING)。如果是,则拿下IP头来。
  • 得到目标IP后,就开始进行路由判断。
    • 如果发现IP是我的,包就应该是我的,就发给上面的传输层,这个节点叫做INPUT
    • 如果发现IP不是我的,就需要将包转发出去,这个节点叫做FORWARD
  • 如果是我的,上层处理完毕之后,一般会返回一个处理结果,这个处理结果会发出去,这个节点叫做OUTPUT
  • 无论是FORWARD还是OUTPUT,都是路由判断之后发生的,最后一个节点是POSTROUTING
    在这里插入图片描述

整个包的处理过程还是原来的过程,只不过为什么要格外关注这五个节点呢?

  • 是因为在Linux内核中,有一个框架叫做Netfilter。它可以在这些节点插入hook函数。

  • 这些函数可以截获数据包,对数据包进行干预。比如做一定的修改,然后决策是否接着交给TCP/IP协议栈处理;或者可以交回给协议栈,那就是ACCEPT;或者过滤掉,不再传输,就是DROP;还有就是QUEUE,发送给某个用户态进程处理

  • 这个比较难理解,经常用在内部负载均衡,就是过来的数据一会儿传给目标地址1,一会儿传给目标地址2,而且目标地址的个数和权重都可能变。协议栈往往处理不了这么复杂的逻辑,需要写一个函数接管这个数据,实现自己的逻辑

  • 有了Netfilter之后,就可以在IP转发的过程中,随时干预这个过程,只要你能够实现这些hook函数

  • 一个著名的实现,就是内核ip_tables。它在这五个节点上埋下函数,从而可以根据规则进行包的处理。按照功能可以分为五大类:连接跟踪(conntrack)、数据报的过滤(filter)、网络地址转换(nat)和数据报的修改(mangle)。其中连接功能是基础功能,被其他功能所依赖。其他三个可以实现包的过滤、修改和网络地址转换

  • 在用户态,还有一个客户端程序iptables,用命令行来干预内核的规则。内核的功能对应iptables的命令行来讲,就是表和链的概念
    在这里插入图片描述

  • iptables的表分为四种:raw->mangle->nat->filter。这四个优先级依次降低,raw不常用,所以主要功能都在其他三种表中实现。每个表可以设置多个链。

  • filter表处理过滤功能,主要包含三个链:

    • INPUT链:过滤所有目标地址是本机的数据包
    • FORWARD链:过滤所有路过本机的数据包
    • OUTPUT链:过滤所有有本机产生的数据包
  • nat表主要是处理网络地址转换,可以进行Snat(改变数据包的源地址)、Dnat(改变数据包的目标地址),包括三个链:

    • PREROUTING链:可以在数据包到达防火墙时改变目标地址
    • OUTPUT链:可以改变本地产生的数据报的目标地址
    • POSTROUTING链:在数据包离开防火墙时改变数据包的源地址
  • mangle表主要是修改数据包,包含:

    • PREROUTING 链;
    • INPUT 链;
    • FORWARD 链;
    • OUTPUT 链;
    • POSTROUTING 链。

将iptables的表和链加入到上面的过程图中,就形成了下面的图和过程。
在这里插入图片描述

  • 数据包进入的时候,先进mangle表的PREROUTING链。在这里可以根据需要,改变数据包头内容之后,进入nat表的PREROUTING链,在这里可以根据需要做Dnat,也就是目标地址转换。
  • 进入路由判断,要判断是进入本地的还是转发的。
  • 如果是进入本地的,就进入INPUT链,之后按条件过滤限制进入。
  • 之后进入本机,再进入OUTPUT链,按条件过滤限制出去,离开本地。
  • 如果是转发就进入FORWARD链,根据条件过滤限制转发。
  • 之后进入POSTROUTING链,这里可以做Snat,离开网络接口。
    有了iptables命令,我们就可以在云中实现一定的安全策略。例如我们可以处理前面的偷窥事件。首先我们将所有的门都关闭。
iptables -t filter -A INPUT -s 0.0.0.0/0.0.0.0 -d X.X.X.X -j DROP

-s 表示源IP地址段 , -d表示目标地址段,DROP表示丢弃,也即无论从哪里来的,要想访问我这台机器,全部拒绝,谁也黑不进来。

但是你发现坏了,ssh也进不来了,都不能远程运维了,可以打开一下。

iptables -I INPUT -s 0.0.0.0/0.0.0.0 -d X.X.X.X -p tcp --dport 22 -j ACCEPT

如果这台机器是提供的是web服务,80端口也应该打开,当然一旦打开,这个80端口就需要很好的防护,但是从规则角度还是要打开。

iptables -A INPUT -s 0.0.0.0/0.0.0.0 -d X.X.X.X -p tcp --dport 80 -j ACCEPT

这样就搞定了,其他的账户都封死,就一个防盗门可以进出,只要防盗门是五星级的,就比较安全了。

这些规则都可以在虚拟机里,自己安装iptables自己配置。但是如果虚拟机数目非常多,都要配置,对于用户来讲就太麻烦了,能不能让云平台把这部分工作做掉呢?

当然可以了。在云平台上,一般允许一个或者多个虚拟机属于某个安全组,而属于不同安全组的虚拟机之间的访问以及外网访问虚拟机,都需要通过安全组进行过滤。 
在这里插入图片描述
例如图中,我们会创建一系列的网站,都是前端在Tomcat里面,对外开放8080端口。数据库使用MySQL,开放3306端口。

为了方便运维,我们创建两个安全组,将Tomcat所在的虚拟机放在安全组携面。在安全组携面,允许任意IP地址0.0.0.0/0访问8080端口,但是对于ssh的22端口,仅仅允许管理员网段203.0.113.0/24访问。

我们将MySQL所在的虚拟机在安全组B里面。在安全组B里面,仅仅允许来自安全组A的机器访问3306端口,但是对于ssh的22端口,同样允许管理员网段203.0.113.0/24访问。

这些安全组规则都可以自动下发到每个在安全组里面的虚拟机上,从而控制一大批虚拟机的安全策略

总结

  • 云计算的关键技术是虚拟化。
  • 虚拟网卡通过打开TUN/TAP字符设备的方式,将虚拟机内外连接起来
  • 云中的网络重点关注四个方面,共享、隔离、互通、灵活。其中共享和互通有两种常用方式:桥接和NAT,隔离可以通过VLAN的方式
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值