---
author: 田立军, 解宝琦
category: 系统运维
comments_data: []
count:
  commentnum: 0
  favtimes: 1
  likes: 0
  sharetimes: 0
  viewnum: 6448
date: '2020-05-11 15:08:00'
editorchoice: false
excerpt: 通过使用新的 GNU/Linux 系统提供的 nftables 防火墙机制建设属于自己的本机 IPS 能力
fromurl: ''
id: 12209
islctt: false
largepic: /images/p/202005/11/150831cohylvolcyfxaza4.jpg
permalink: /article-12209-1.html
pic: /images/p/202005/11/150831cohylvolcyfxaza4.jpg.thumb.jpg
related: []
reviewer: ''
selector: ''
summary: 通过使用新的 GNU/Linux 系统提供的 nftables 防火墙机制建设属于自己的本机 IPS 能力
tags:
- 防火墙
- nftables
- iptables
thumb: false
title: GNU/Linux 系统下 nftables 防火墙的本地 IPS 能力部署实例
titlepic: true
translator: ''
updated: '2020-05-11 15:08:00'
---

![](/images/p/202005/11/150831cohylvolcyfxaza4.jpg)


随着各 GNU/Linux 系统厂商以及社区逐步开始采用新的内核作为其发行版本的默认内核，防火墙机制采用了更新的 nftables 防火墙机制。


尽管红帽公司提供了 firewalld.service 防火墙服务组件以及相关的配置管理命令 `firewall-config`、`firewall-cmd` 来对防火墙进行管理，但该服务组件目前还没有在其他发行版或者社区版本内得到统一使用。


为了更好的帮助读者朋友们理解该防火墙机制，笔者将自己在工作中直接使用 nftables 进行手工创建配置，从而使系统具有本地 IPS 能力的过程进行总结。


目前多数主流的新发行版 GNU/Linux 系统，默认安装完成后 systemd 系统和服务管理器中已经添加了新的 nftables.serivce 子服务配置文件。同时依然支持 iptables 规则和 `iptables` 命令，不过为了彻底将防火墙升级到 nftables 机制，我们可以在没有 firewalld.service 的发行版系统中直接启用 nftables.service 服务来使用新的防火墙。


通过执行命令 `vi /lib/systemd/system/nftables.service`，从该文件中的语句 `ExecStart=/usr/sbin/nft -f /etc/nftables.conf` 我们可以清楚的看到，nftables 防火墙的默认配置和规则文件一般都放置在系统的 `/etc/nftables.conf` 目录中，不过该默认配置文件中只包含一个名为 `inet filter` 的简单 IPv4/IPv6 防火墙列表。


inet 过滤器可以同时适用于 IPv4 和 IPv6 的规则，但不能用于 NAT 类型的链，只能用于过滤器类型的链。


为了保持和 iptables 防火墙的规则类比，便于用户熟悉，我们可以使用如下 `nftables` 命令创建相应的表和链来建立一个类似于传统 iptables 防火墙框架，创建过程如下：


### 1、创建 nft 表


与 iptables 中的表不同，nftables 中没有内置表，表的数量和名称由用户决定。但是，每个表只有一个地址簇，并且只适用于该簇的数据包。


表可以指定五个（ip、ip6、inet、arp、bridge）簇中的一个，用户可以依次执行如下命令：



```
nft add table ip filter
nft add table ip6 filter
nft add table bridge filter”
```

nftables 将为我们分别建立三个 `ip`、`ipv6`、`bridge` 簇并且表名均为 `filter` 的防火墙框架。


### 2、创建链


表包含链，链的目的是保存规则。


与 iptables 中的链不同，nftables 也没有内置链。这意味着与 iptables 不同，如果链不匹配 nftables 框架中的簇或钩子，则流经这些链的数据包不会被 nftables 触及。


链有两种类型。基础链是来自网络栈的数据包的入口点，其中指定了钩子，其实可以理解为 iptables 防火墙的默认规则。常规链可以理解为其它用户自定义的规则链。


使用如下命令为每一个表建立 `INPUT`、`FORWARD`、`OUTPUT` 链，并且设置基础链，其中 `ip` 簇 `filter` 表 `INPUT` 链默认为丢弃所有数据包的相应的命令格式如下。


添加 `ip` 簇 `filter` 表相应链命令集：



```
nft add chain ip filter INPUT { type filter hook input priority 0\; policy drop\; }  

nft add chain ip filter FORWARD { type filter hook forward priority 0\; policy accept\; }  

nft add chain ip filter OUTPUT { type filter hook output priority 0\; policy accept\; }
```

添加 `ipv6` 簇 `filter` 表相应链命令集： 



```
nft add chain ip6 filter INPUT { type filter hook input priority 0\; policy accept\; }  

nft add chain ip6 filter FORWARD { type filter hook forward priority 0\; policy accept\; }  

nft add chain ip6 filter OUTPUT { type filter hook output priority 0\; policy accept\; }
```

添加 `bridge` 簇 `filter` 表相应链命令集：



```
nft add chain bridge filter INPUT { type filter hook input priority 0\; policy accept\; }  

nft add chain bridge filter FORWARD { type filter hook forward priority 0\; policy accept\; }  

nft add chain bridge filter OUTPUT { type filter hook forward priority 0\; policy accept\; }
```

### 3、添加规则


规则由语句或表达式构成，包含在链中。


将一条规则添加到链中使用如下语法：



```
nft add rule family table chain handle statement
```

规则添加到 handle 处，这是可选的。如果不指定，则规则添加到链的末尾，类似于 `iptables -A` 方法。


将规则插入到指定位置使用如下语法：



```
nft insert rule family table chain handle statement
```

如果未指定handle，则规则插入到链的开头，类似于 `iptables -I` 方法。


以下是用户根据自己的实际情况添加的具体规则：


放行本地回环接口 `lo` 的所有流量：



```
nft add rule ip filter INPUT iif lo accept
```

放行 `established`、`related` 状态的数据包，这一点很重要，因为多数对外访问的数据包在收到对端主机回包时多为这两种状态，如果在 INPUT 链中不放行该类型数据包，即使本机的 `OUTPUT` 链默认为 `ACCEPT`，让所有数据包出站，系统也会主动在 `INPUT` 链中丢弃掉相应的回包而导致数据无法交互。具体命令如下：



```
nft add rule ip filter INPUT ct state established,related accept
```

阻断存在重大安全隐患的系统端口，包括已经公布的比如勒索病毒等端口。nftables 在配置过程中，当用户使用端口进行添加后，nftables 会自动将端口转换为 service 模式，用户可以通过使用命令 `nft describe tcp dport` 对照查看。阻断安全隐患的系统端口具体命令如下： 



```
nft add rule ip filter INPUT meta l4proto tcp tcp dport { loc-srv, 136, netbios-ns, netbios-dgm, netbios-ssn, microsoft-ds, 3389, radmin-port } counter drop

nft add rule ip filter INPUT meta l4proto udp udp dport { loc-srv, 136, netbios-ns, netbios-dgm, netbios-ssn, microsoft-ds, 3389, radmin-port } counter drop
```

对服务进行限流控制，防止 DDoS 攻击或者 CC 攻击造成系统服务中断，可以通过 `limit` 限制通信速率，以下是接受一个每秒最多 10 个 web 或者 https 或者 dns 查询请求的数据包，同时可以有 2 个包超出限制的规则具体命令： 



```
nft add rule ip filter INPUT meta l4proto tcp tcp dport { 80,443,53 } ct state new limit rate 10/second burst 4 packets accept
  
nft add rule ip filter INPUT meta l4proto udp udp dport { 80,443,53 } ct state new limit rate 10/second burst 4 packets accept
```

### 总结


经过以上配置后，我们的主机就具有了很好的本机 IPS 能力。应对不论是面向南北跨路由器的访问流量，还是本地网络内的东西访问流量，常规的恶意扫描或者恶意攻击基本是够用了。


之后用户可以使用命令 `nft list ruleset > /etc/nftables.conf` 将这些规则保存在 nftables 的默认配置文件中，并使用 `systemctl enable nftables.service` 打开该服务的默认启动模式，之后系统将在开机时自动启动 nftables 防火墙并应用相应规则。


用户也可以通过命令 `vi /etc/nftables.conf` 来直接按照相应规则编辑该文件来修改防火墙配置，以确保自己的系统处于本机防火墙 IPS 能力的保护之下。


希望本文对你有用并能帮助到你。