11

iptables在Openstack安全组中的应用分析

 3 years ago
source link: https://www.sdnlab.com/23277.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

作者简介:Mr Huang,SDN/NFV研发工程师,技术擅长:SDN、NFV、Openstack

本文是基于Openstack Queens版本,且采用Linuxbridge充当虚拟交换机,描述iptables在Openstack安全组中的应用分析。涉及的实验都以Ubuntu16.04环境为准。

06iptable668.jpg

1 什么是Iptables

本文不会对iptables相关知识做过多的描述,对于不了解iptables的读者,推荐阅读网上的一份连载文章,里面详细描述了iptables的基础知识及使用。链接请参见:http://www.zsythink.net/archives/tag/iptables/

2 Openstack安全组

2.1 什么是安全组

在Openstack中,安全组是作用在neutron port上的一组策略,这些策略我们其实可以理解为一些防火墙规则的集合。可用于过滤进出neutron port的数据报文。

2.2 安全组规则

一个安全组中可以包含多个安全组规则,其中一条规则中包含的重要字段有如下:

  • Direction
    安全组是区分ingress和egress两个方向的。因此定义规则的时候需要明确指定应用的方向。
  • Ethertype
    以太网类型,主要有:IPv4和IPv6两种。
  • Protocol
    IP协议。可以用字符串来表达,也可以用整数值来表达。用整数值来表达时,范围为0~255。对于协议字符串及其整数值可以通过链接:http://www.iana.org/assignments/protocol-numbers/protocol-numbers.xhtml查询到。
  • Port Range
    如果协议为TCP、UDP、DCCP、SCTP或UDP-Lite的话,则这个字段代表的是传输层协议端口范围。如果协议为ICMP,则这个字段代表的是ICMP协议报文中的type字段。
  • Remote IP Prefix
    指的是远端IP前缀地址。对于ingress方向,代表的是源IP前缀地址;对于egress方向,代表的是目的IP前缀地址。
  • Remote group ID
    Remote group ID对应安全组所关联的所有端口的IP地址。这些IP地址是离散的。

    在Openstack中,对用户暴露的安全组规则添加接口,所有添加的规则都是ALLOW动作的,不会有DENY动作。即:用户只能添加白名单的规则而不允许添加黑名单的规则。

    2.3 安全组的实现

    Openstack中的安全组的实现有如下几个:

  • openvswitch + iptables + connection track
  • openvswitch + openflow + connection track
  • linuxbridge + iptables + connection track

由于本文阐述的是linuxbridge的使用场景,因此不会对前面两种的实现方式进行阐述。

采用linuxbridge + iptables + connection track的实现方式,主要涉及iptables表为filter。而connection track主要用于跟踪数据报文的状态信息(因为安全组是有状态的防火墙),该技术不是本文的重点,所以不会进行相关的阐述,有兴趣的读者可以参考链接:http://conntrack-tools.netfilter.org/manual.html

根据前面内容可知,安全组是作用在neutron port。本文主要分析虚拟机关联的安全组,因此这里只阐述虚拟机关联安全组后会产生哪些iptables规则。分为ingress和egress方向,在iptables中会产生两条链,即:neutron-linuxbri-oxxx和neutron-linuxbri-ixxx。其中字母’o’表示的是egress方向,’i’表示的是ingress方向,xxx则对应虚拟机所生成的neutron port的uuid的前10个字符,例如:neutron-linuxbri-offe6e45b-d和neutron-linuxbri-iffe6e45b-d。通过这种方式,进出虚拟机的报文都会去匹配这两条链上的规则,进而放行报文或丢弃报文。

2.4 默认安全组

在Openstack中,创建租户时会默认创建一个默认安全组,这个默认的安全组名字为default。
为了掌握默认安全组包含哪些默认的规则,我们这里提前进行实验分析。在我们的Openstack环境中,可以通过如下几个命令来创建租户及其租户用户:

Java
openstack project create --domain default --description "Test Project" test openstack user create --domain default --password-prompt test openstack role add --project test --user test admin
1
2
3
openstack project create--domain default--description"Test Project"test
openstack user create--domain default--password-prompt test
openstack role add--project test--user test admin

如上面这几条命令创建了一个test租户,并创建了test用户。我们登陆Openstack的dashboard查看test租户下的默认安全组包含了哪些规则,如下图所示:

06Iptables01.jpg

从上图中可以看到默认安全组包含了4条规则,两条ingress方向,两条egress方向。从图中所示的规则来看,默认安全组包含的这4条规则意义如下:

  • egress方向
    允许IPv4或IPv6报文,任何协议,任何端口,任何远端IP的报文通过。
  • ingress方向
    允许IPv4或IPv6报文,任何协议,任何端口,任何来自同一个安全组关联的端口IP的报文通过。

但是这个只是用dashboard的视图看到的规则。实际上默认安全组包含的默认规则不止上述这些。为了探究默认安全组包含的所有规则信息,我们可以事先启动一个虚拟机示例(默认关联这个默认安全组),然后通过iptables命令查看。

下图给出的是虚拟机关联的neutron port信息:(红色标注部分)

06iptable302.png

根据2.3节的阐述,该虚拟机关联默认安全组后,会创建两条iptables链,即:neutron-linuxbri-offe6e45b-d和neutron-linuxbri-iffe6e45b-d。我们可以通过执行iptables -t filter -nvL来查看这两条链的具体信息,如下所示:

  • egress方向

06iptable303.png

我们来分析上图所示的每一条规则的意义:
第一条:允许虚拟机发出的DHCP Client报文(广播)。
第二条:匹配所有的报文,然后会跳转到另外一条iptables链上继续匹配。这条链上的规则信息如下图所示。从图中的规则可以看出,从虚拟机发出来的报文需要严格匹配IP+MAC,即:MAC spoof prevention。因此,如果人为在虚拟机里面将网卡的IP地址修改为其他或修改网卡的MAC地址,将被安全组过滤掉发出的任何报文。

06iptable304.png

第三条:和第一条规则类似,也是允许虚拟机发出的DHCP Client报文。不同的是这条规则匹配的目的IP地址为0.0.0.0/0,这是因为有些DHCP Client报文是以单播的形式发出去的。因此这条规则是用来匹配单播的DHCP Client报文。
第四条:丢弃虚拟机发出的DHCP Server报文,即虚拟机不能充当DHCP Server。
第五条:允许状态为RELATED或ESTABLISHED的报文。
第六条:允许所有发出的报文(这条规则就是我们上面在dashboard看到的)
第七条:丢弃状态为INVALID的报文。
第八条:匹配所有的报文,然后跳转到另外一条链上,这条链上的规则信息如下图所示。从图中所示的规则可以看出,egress方向的最后一条iptables规则为丢弃所有发出的报文。

06iptable305.png

  • ingress方向

06iptable306.png

我们来分析上图所示的每一条规则的意义:
第一条:允许状态为RELATED或ESTABLISHED的报文进入虚拟机。
第二条:允许DHCP Server发来的报文(单播)进入虚拟机。
第三条:允许DHCP Server发来的报文(广播)进入虚拟机。
第四条:允许关联了同一个安全组的其他虚拟机发来的报文进入虚拟机(这条规则就是我们上面在dashboard看到的)。
第五条:丢弃状态为INVALID的报文。
第六条:匹配所有的报文,然后跳转到另外一条链上,这条链上的规则信息如下图所示。从图中所示的规则可以看出,ingress方向的最后一条iptables规则为丢弃所有进入的报文。

06iptable307.png

2.5 实验分析

这节我们主要通过几个实验来进一步分析安全组。涉及如下几个实验:

  • 虚拟机关联默认安全组,分别从dhcp namespace和另外一个虚拟机ping目标虚拟机。
    首先启动两个虚拟机,如下图所示:

06Iptables08.jpg

两个虚拟机都属于同一个子网。现在从dhcp namespace去ping testvm1,看看是否能ping通,结果如下图所示,无法ping通。

06iptable309.png

现在再从testvm2去ping testvm1看看是否能ping通,结果如下图所示,可以ping通。

06Iptables10.jpg

结果分析:按照前面内容的描述,testvm1和testvm2都关联了同一个默认安全组,因此从规则上二者是可以相互访问的。但是从dhcp neutron port是没有关联任何安全组的,因此是无法访问testvm1的。

为了从dhcp namespace里能够ping通testvm1,我们可以在默认安全组上添加相应的规则。如下图所示,添加了ingress方向上允许ICMP的报文。

06Iptables11.jpg

再查看下后台的iptables规则有哪些变化,如下图所示,红色框住的规则就是手工添加的。

06iptable312.png

现在再来看看从dhcp namespace里是否可以ping通testvm1,结果如下图所示(是可以ping通的):

06iptable313.png

同理,如果想从外部ssh到testvm1,同样需要手工添加允许TCP的规则,这里就不再赘述了。

  • 虚拟机不关联任何安全组
    将testvm1的虚拟机关联的安全组取消掉,再观察下后台的iptables规则会有哪些变化:
    egress方向
    变化后:

06iptable314.png

变化前:

06iptable315.png

对比前后的iptables规则,发现虚拟机取消关联安全组后,只剩下了隐藏的规则,在dashboard上能看到的所有规则都去掉了。这个时候从虚拟机再发送报文(非DHCP报文)都会被丢弃。

ingress方向
变化后:

06iptable316.png

变化前:

06iptable317.png

同样,只剩下了隐藏的规则,在dashboard上能看到的所有规则都去掉了。这个时候进入虚拟机的报文(非DHCP报文)都会被丢弃。

  • 虚拟机禁用安全组
    这种情况和上一种情况不同。上一种情况只是把虚拟机关联的安全组取消掉,但是虚拟机对应的neutron port依然是允许安全组的。我们可以通过查看虚拟机对应的neutron port的详细信息得知,如下图所示:

06iptable318.png

现在我们将完全禁用掉虚拟机使用安全组。可以通过修改虚拟机的neutron port属性来达到此目的,命令如下:

Java
neutron port-update <port uuid> --port-security-enabled false
1
neutron port-update<port uuid>--port-security-enabled false

设置后,再次查看neutron port的信息,如下图所示:

06iptable319.png

从上图看已经禁用掉了安全组。再观察后台的iptables规则的变化情况,已经完全看不到neutron-linuxbri-offe6e45b-d和neutron-linuxbri-iffe6e45b-d这两条链了。这个时候我们再次从dhcp namespace和testvm2去ping testvm1看看结果(先将之前添加的允许ICMP规则去掉),如下图所示:

06Iptables20.jpg

06Iptables21.jpg

从上面两个图可知,禁用掉虚拟机的安全组后,进出该虚拟机的报文将不再被限制了。

3 结论

本文从原理分析再到实验验证详细地阐述了Openstack中采用linuxbridge + iptables + connection track方式实现的安全组,对希望入门Openstack安全组提供了较好的帮助。


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK