当前位置:首页 > 百科

centos端口映射

CentOS 7 默认的端口 firewalld 拦掉了绝大多数入站端口。你装个 Nginx 想从外面访问 80,映射或者跑个 Redis 想暴露 6379,端口不手动放行就是映射连不上。这不是端口 bug,是映射默认策略。端口映射这件事,端口在 CentOS 上其实分两个层面:一个是映射防火墙层面的放行,一个是端口 NAT 层面的转发。很多人把这两件事混在一起说,映射实际场景里它们经常要配合使用。端口

先说防火墙放行。映射firewalld 的端口操作逻辑比 iptables 直观不少。查看当前放行了哪些端口:

firewall-cmd --list-ports

如果输出是映射空的,说明一个额外端口都没开。端口放行 8080 端口,加上 permanent 参数写入永久配置:

firewall-cmd --permanent --add-port=8080/tcp firewall-cmd --reload

reload 之后立即生效,不需要重启整个 firewalld 服务。这里有个细节:不加 --permanent 的规则在 reload 后会丢失,但当前会话内是生效的。我一般习惯直接加 permanent,省得后面忘了。

批量放行可以用 --add-port=8000-9000/tcp 这种范围写法。删除规则把 add 换成 remove 就行。有个坑是,如果你同时装了 iptables-services 并且它处于运行状态,firewalld 和 iptables 会打架。CentOS 7 之后默认用 firewalld,确认一下 systemctl status iptables 是不是 inactive 状态。

真正意义上的端口映射——也就是把外部请求转发到另一台机器或另一个端口——firewalld 也能做,靠的是 rich rule 或者直接配 forward-port。比如把本机 80 端口的流量转发到内网 192.168.1.100 的 8080:

firewall-cmd --permanent --add-forward-port=port=80:proto=tcp:toport=8080:toaddr=192.168.1.100 firewall-cmd --reload

这需要先开启 IP 转发。编辑 /etc/sysctl.conf,加上 net.ipv4.ip_forward = 1,然后 sysctl -p 生效。没开转发的话,规则配了也没用,包到了本机就断了。

另一种更常见的场景是用 iptables 做 DNAT。有些人不喜欢 firewalld 那套 zone 的概念,直接关掉它用 iptables。操作大概是这样:

iptables -t nat -A PREROUTING -p tcp --dport 80 -j DNAT --to-destination 192.168.1.100:8080 iptables -t nat -A POSTROUTING -p tcp -d 192.168.1.100 --dport 8080 -j SNAT --to-source 本机内网IP

SNAT 那一条容易被忽略。没有它,回包可能走默认路由出去,目标机器收到请求但响应回不来,表现为连接超时。这个坑我踩过好几次,抓包才看出来。

还有个轻量方案是 socat 或 rinetd,不依赖内核转发,用户态直接监听和转发。临时调试用 socat 一行命令搞定:

socat TCP-LISTEN:3306,fork,reuseaddr TCP:192.168.1.200:3306

性能不如内核 NAT,但胜在简单、不用改系统配置、不用 root 也能跑高位端口。生产环境长期用还是建议走 firewalld 或 iptables,socat 适合临时救急。

检查映射是否生效,ss -tlnp 看监听状态,iptables -t nat -L -n -v 看 NAT 规则命中计数。计数器不动,说明流量根本没匹配上规则,往回查路由和防火墙 zone 绑定是否正确。CentOS 的网卡默认绑在 public zone,如果你把接口换到了别的 zone,之前加的规则可能就不在这个 zone 里,自然不生效。

分享到: