我的本地网络上运行着一台服务器,它充当网络中计算机的路由器。我现在想要实现的是,通过 SSH 连接隧道传输到特定 IP 地址的传出 TCP 请求,而不让我网络中的人员使用该 SSH 隧道连接到任意主机。
到目前为止,我想到的方法是有一个实例红袜队监听 localhost 并将所有传出请求重定向到我想要转移到该 redsocks 实例的 IP 地址。我添加了以下 iptables 规则:
iptables -t nat -A PREROUTING -p tcp -d 1.2.3.4 -j DNAT --to-destination 127.0.0.1:12345
显然,Linux 内核将来自非 127.0.0.0/8 地址到 127.0.0.0/8 地址的数据包视为“火星数据包”并丢弃它们。然而,有效的方法是让 redsocks 监听 eth0 而不是 lo,然后让 iptables 将数据包 DNAT 到 eth0 地址(或使用 REDIRECT 规则)。这样做的问题是,我的网络上的每台计算机都可以使用 redsocks 实例连接到互联网上的每台主机,但我想将其使用限制在特定的一组 IP 地址上。
有什么方法可以将 iptables DNAT 数据包发送到 127.0.0.1 吗?否则,有人知道我如何在不向所有人开放隧道的情况下实现我的目标吗?
更新:我也尝试过更改数据包的来源,但是没有成功:
iptables -t nat -A POSTROUTING -p tcp -s 192.168.1.0/24 -d 1.2.3.4 -j SNAT --to-source 127.0.0.1
iptables -t nat -A POSTROUTING -p tcp -s 192.168.1.0/24 -d 127.0.0.1 -j SNAT --to-source 127.0.0.1
答案1
我找到了解决我的 dnat 到 127.0.0.1(环回)失败的方法,并在 netfilter irc 频道上得到了答案。
有一个 sysctl 设置允许 dnat 回环。要允许它
sysctl -w net.ipv4.conf.eth0.route_localnet=1
并检查设置
cat /proc/sys/net/ipv4/conf/eth0/route_localnet
答案2
您无法使用 127/8 网络执行此技巧,因为它在 Linux 内核中是专门处理的。但您可以创建虚拟网络接口,为其分配 IP 地址,将您的服务绑定到此地址并执行 NAT。
root@vm8583:~# ip link add bogus type dummy
root@vm8583:~# sysctl net.ipv4.conf.eth0.arp_ignore=3
root@vm8583:~# ip addr add 10.0.0.1/32 bogus scope host
root@vm8583:~# ip link set bogus up
root@vm8583:~# ip link show bogus
4: bogus: <BROADCAST,NOARP,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN mode DEFAULT
link/ether 5e:8b:38:f3:46:ce brd ff:ff:ff:ff:ff:ff
请注意,您可能需要net.ipv4.conf.eth0.arp_ignore=3
设置服务器不会响应通过 eth0 传入的 10.0.0.1 的 ARP 请求:
arp_ignore - INTEGER
Define different modes for sending replies in response to
received ARP requests that resolve local target IP addresses:
. . .
3 - do not reply for local addresses configured with scope host,
only resolutions for global and link addresses are replied
4-7 - reserved
答案3
您可以尝试禁用反向路径过滤(据我所知,这就是“火星人”的意思)。您可以以echo 0 > /proc/sys/net/ipv4/conf/all/rp_filter
root 身份执行此操作。(您可能只能在lo
界面上禁用它,但我会首先尝试完全禁用它。)