How do I forward localhost traffic to a remote host with iptables?
Solution 1
I do not know how to configure iptables on this machine to do as you want. I usually use in such case SSH tunneling. I find it easy to set-up (personal opinion here!) ;-) but ... you need to have an SSH connection on your localhost (it does not need to be accessible from remote!).
The command syntax in this case is:
ssh -f -C -N -L [<bind address>:]<local port>:<remote host name>:<remote service port> [-p <ssh port>] [<username>@]<remote host outside name>
So for you that would mean:
ssh -f -C -N -L 127.0.0.1:8888:10.0.3.10:8888 localhost
Solution 2
The trick involves enabling localhost/localnet route processing for your outbound interface with:
sysctl -w net.ipv4.conf.all.route_localnet=1
Then this works:
iptables -t nat -A OUTPUT -m addrtype --src-type LOCAL --dst-type LOCAL -p tcp --dport 8888 -j DNAT --to-destination 10.0.3.10
iptables -t nat -A POSTROUTING -m addrtype --src-type LOCAL --dst-type UNICAST -j MASQUERADE
Related videos on Youtube
Jonathan
I'm a programmer living and working in Glasgow, Scotland. Day-to-day, I work with Java, SQL, some JEE technologies, like JPA, and Javascript. I'm passionate about performance, and really interested in highly-scalable web applications. I enjoy working with legacy code (Crazy, I know!) because of its trove of interesting challenges.
Updated on September 18, 2022Comments
-
Jonathan almost 2 years
I would like to set up my CentOS 6.5 box to forward connections to localhost (127.0.0.1) to the same port on a remote machine (e.g. 10.0.3.10).
I've tried the iptables rule below, but when I attempt to connect, it just hangs:
iptables -t nat -I OUTPUT --src 0/0 --dst 127.0.0.1 -p tcp --dport 8888 \ -j DNAT --to-destination=10.0.3.10:8888
Running
tcpdump
on the remote machine, I can see that there was no incoming traffic. I've done some google searches, but haven't turned up anything particularly useful. I've also confirmed that mysysctl.conf
file containsnet.ipv4.ip_forward = 1
.Edit I've added logging in response to one of the comments below. It produces no output when I go to 127.0.0.1:8888 but does produce output when going to 10.0.3.10:
# Generated by iptables-save v1.4.7 on Tue Jul 29 12:52:17 2014 *nat :PREROUTING ACCEPT [0:0] :POSTROUTING ACCEPT [11:1008] :OUTPUT ACCEPT [11:1008] :LOGGING - [0:0] -A OUTPUT -p tcp -m tcp -d 10.0.3.10 --dport 8888 -j LOGGING -A LOGGING -j LOG --log-prefix "IPTABLES: " -A LOGGING -j ACCEPT -A OUTPUT -d 127.0.0.1/32 -p tcp -m tcp --dport 8888 -j DNAT --to-destination 10.0.3.10:8 888 COMMIT # Completed on Tue Jul 29 12:52:17 2014 # Generated by iptables-save v1.4.7 on Tue Jul 29 12:52:17 2014 *filter :INPUT ACCEPT [50:2776] :FORWARD ACCEPT [0:0] :OUTPUT ACCEPT [49:4336] COMMIT # Completed on Tue Jul 29 12:52:17 2014
-
Dennis Nolte almost 10 yearsis this on the same network, or do you have some additional router in between? if so: did you check there if the traffic is reaching it. check tcpdump locally to see if it exits to your interface. Additionally you could add logging in iptables to check if you enter the chain.
-
Jonathan almost 10 yearsI've added logging and there are no messages being recorded. Both machines are on the same network (10.0.3.13 is my local machine, 10.0.3.10 is the remote). Tcpdump locally shows no traffic.
-
-
Jonathan almost 10 yearsThank-you. I ended up doing just this. iptables is so flexible but sometimes something that seems very simple on the surface is just impossible.