iptables redirect outside requests to 127.0.0.1
The iptables rule you are using will work, but there is one additional change you need to make:
sysctl -w net.ipv4.conf.eth0.route_localnet=1
(replacing eth0
with the nic 192.168.2.2
resides on)
By default this value is 0
, which instructs the kernel to not route external traffic destined to 127.0.0.0/8
. This is just for security as such traffic is not normal.
What if the correct answer with route_localnet
doesn't work?..
If your kernel doesn't include the patch for route_localnet
, then... upgrade the kernel!
Or there are other ways to forward the traffic coming to one interface to another port on another interface (in particular, to localhost) by running a process that would listen on the external interface and forward the traffic.
netcat
(nc
), xinetd
, and ssh
(and perhaps more) are all examples of programs able to do this (although choosing ssh
would be strange and ineffective).
I've written a configuration for xinetd
for this. Now this service is automatically brought up:
# cat /etc/xinetd.d/z-from-outside
# default: off
# description: Forward connections to the z port.
service z-from-outside
{
disable = no
socket_type = stream
type = UNLISTED
wait = no
user = nobody
bind = vaio.ob
port = 7070
redirect = localhost 7070
}
#
(vaio.ob
is the name of this host on the external network interface.)
After a service xinetd reload
, let's check that it is listening:
# lsof -i -P | fgrep 7070
xinetd 556 root 6u IPv4 1797906 0t0 TCP vaio.ob:7070 (LISTEN)
sshd 27438 tun_zzoom 4u IPv4 1059100 0t0 TCP localhost.localdomain:7070 (LISTEN)
#
And indeed, connections do go through!
You can redirect to localhost but not to loopback (127.0.0.0/8). Loopback is a loophole. You have to redirect to one of your real interfaces. Try using REDIRECT.
iptables -t nat -A PREROUTING ..... -j REDIRECT --to-port 222