Link to home
Start Free TrialLog in
Avatar of Jerf
Jerf

asked on

Redhat 7.2 port forwarding question

I just upgraded from RH 6.2 to 7.2 and I'm as confused at everyone else about the new iptables.

What I'm looking for is a NAT/router box.  I have the NAT portion working now - my linux box is the default gateway for most of my network.  WHat I'm having problems with is the router part.  I'd like it to forward certain ports to different parts of the network.  I've read this howto:

 http://netfilter.samba.org/unreliable-guides/NAT-HOWTO/NAT-HOWTO.linuxdoc-6.html, but I can't seem to get anywhere.  

I ran this:

iptables -t nat -A PREROUTING -p tcp --dport 80 -i ppp0 -j DNAT --to 192.168.0.1:80

and from what I understand this should forward any requests from my dsl connection (ppp0) to my web server 192.168.0.1.  I'm not getting any response when I go outside and try to hit that IP.  Does anyone have any ideas?
Avatar of MFCRich
MFCRich

What IP are you "trying to hit"? You should be using the addr supllied by your ISP for ppp0 and the machine with addr 192.168.0.1 must have something listening on port 80.
Avatar of Jerf

ASKER

MFCRich -

I'm trying to hit my external IP (I have a static IP assigned by my ISP - for sake of argument let's say 1.2.3.4).  I was under the impression that I could have the interface that I wanted the traffic coming in on.  I have a web server running on 192.168.0.1.

I tried this rule:  iptables -t nat -A PREROUTING -p tcp --dport 80 -s 1.2.3.4 -j DNAT --to 192.168.0.1:80 but I got the same result.

Thanks,
Jeff
Avatar of Jerf

ASKER

I just realized that that address doesn't work.  This is the howto I'm looking at:  http://netfilter.samba.org/unreliable-guides/NAT-HOWTO/  and I'm looking at the stuff under section 6.

this is what happens when I run iptables --list:

# iptables --list
Chain INPUT (policy ACCEPT)
target     prot opt source               destination

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination

Shouldn't there be *stuff* in there?  Am I missing a config option or something?

Jeff
ASKER CERTIFIED SOLUTION
Avatar of jlevie
jlevie

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of Jerf

ASKER

jlevie - Thanks a lot for your help.  That's an excellent script you have there.  One problem - it's still not forwarding my port 80 - do you have any ideas?

Jeff

here's the results of an iptable-save (everything intact except for the external IP):

# Generated by iptables-save v1.2.3 on Tue Jun  4 11:08:37 2002
*mangle
:PREROUTING ACCEPT [9744:563876]
:OUTPUT ACCEPT [8329:986876]
COMMIT
# Completed on Tue Jun  4 11:08:37 2002
# Generated by iptables-save v1.2.3 on Tue Jun  4 11:08:37 2002
*filter
:INPUT DROP [0:0]
:FORWARD ACCEPT [119:6519]
:OUTPUT ACCEPT [3165:159558]
:firewalled - [0:0]
:silent - [0:0]
:tcpflags - [0:0]
-A INPUT -p tcp -m tcp --tcp-flags FIN,SYN,RST,PSH,ACK,URG FIN,PSH,URG -j tcpflags
-A INPUT -p tcp -m tcp --tcp-flags FIN,SYN,RST,PSH,ACK,URG FIN,SYN,RST,PSH,ACK,URG -j tcpflags
-A INPUT -p tcp -m tcp --tcp-flags FIN,SYN,RST,PSH,ACK,URG FIN,SYN,RST,ACK,URG -j tcpflags
-A INPUT -p tcp -m tcp --tcp-flags FIN,SYN,RST,PSH,ACK,URG NONE -j tcpflags
-A INPUT -p tcp -m tcp --tcp-flags SYN,RST SYN,RST -j tcpflags
-A INPUT -p tcp -m tcp --tcp-flags FIN,SYN FIN,SYN -j tcpflags
-A INPUT -p icmp -m icmp --icmp-type 0 -j ACCEPT
-A INPUT -p icmp -m icmp --icmp-type 3 -j ACCEPT
-A INPUT -p icmp -m icmp --icmp-type 11 -j ACCEPT
-A INPUT -p icmp -m icmp --icmp-type 8 -m limit --limit 1/sec -j ACCEPT
-A INPUT -p icmp -j firewalled
-A INPUT -i lo -j ACCEPT
-A INPUT -d 192.168.0.2 -i eth1 -j ACCEPT
-A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
-A INPUT -i ppp0 -p tcp -m tcp --dport 22 -j ACCEPT
-A INPUT -i ppp0 -p tcp -m tcp --dport 80 -j ACCEPT
-A INPUT -j firewalled
-A firewalled -m limit --limit 15/min -j LOG --log-prefix "Firewalled:"
-A firewalled -j DROP
-A silent -j DROP
-A tcpflags -m limit --limit 15/min -j LOG --log-prefix "TCPflags:"
-A tcpflags -j DROP
COMMIT
# Completed on Tue Jun  4 11:08:37 2002
# Generated by iptables-save v1.2.3 on Tue Jun  4 11:08:37 2002
*nat
:PREROUTING ACCEPT [4248:374436]
:POSTROUTING ACCEPT [3331:214208]
:OUTPUT ACCEPT [3328:214296]
-A PREROUTING -i ppp0 -p tcp -m tcp --dport 80 -j DNAT --to-destination 192.168.0.1
-A POSTROUTING -o ppp0 -j SNAT --to-source x.x.x.x
COMMIT
# Completed on Tue Jun  4 11:08:37 2002
It's not the easiest thing to do to look at the saved rules and infer what's wrong, but I think you've specified a forward with:

$IPTABLES -t nat -A PREROUTING -i $OUTSIDE -p tcp --dport 80 -j DNAT --to 192.168.0.1

That would be correct but you also have to allow the inbound traffic to the target IP with a rule like:

$IPTABLES -A INPUT -i $OUTSIDE -d 192.168.0.1 -p tcp --dport 80 -j ACCEPT
Avatar of Jerf

ASKER

Maybe this will help :)

here's the script you gave to me:

IPTABLES="/sbin/iptables"
OUTSIDE=ppp0
INSIDE=eth1

echo $IPTABLES

#
# Clear out any existing firewall rules, and any chains that might have
# been created. Then set the default policies.
#
$IPTABLES -F
$IPTABLES -F INPUT
$IPTABLES -F OUTPUT
$IPTABLES -F FORWARD
$IPTABLES -F -t mangle
$IPTABLES -F -t nat
$IPTABLES -X
$IPTABLES -P INPUT DROP
$IPTABLES -P OUTPUT ACCEPT
$IPTABLES -P FORWARD ACCEPT
#
# Begin setting up the rulesets. First define some rule chains to handle
# exception conditions. These chains will receive packetsthat we aren't
# willing to pass. Limiters on logging are used so as to not to swamp the
# firewall in a DOS scenario.
#
# silent         - Just dop the packet
# tcpflags     - Log packets with bad flags, most likely an attack
# firewalled   - Log packets that that we refuse, possibly from an attack
#
$IPTABLES -N silent
$IPTABLES -A silent -j DROP

$IPTABLES -N tcpflags
$IPTABLES -A tcpflags -m limit --limit 15/minute -j LOG --log-prefix TCPflags:
$IPTABLES -A tcpflags -j DROP

$IPTABLES -N firewalled
$IPTABLES -A firewalled -m limit --limit 15/minute -j LOG --log-prefix Firewalled:
$IPTABLES -A firewalled -j DROP
#
# Use up NPAT if you have a dynamic IP. Otherwise comment out the following
# line and use the Source NAT below.
#
#$IPTABLES -t nat -A POSTROUTING -o $OUTSIDE -j MASQUERADE
#
# Use Source NAT if to do the NPAT you have a static IP or netblock.
# Remember to change the IP to be that of your OUTSIDE NIC.
#
$IPTABLES -t nat -A POSTROUTING -o $OUTSIDE -j SNAT --to x.x.x.x
#
# Examples of Port forwarding.
#
# The first forwards HTTP traffic to 10.1.0.1
# The second forwards SSH to 10.1.0.1
# The third forwards a block of tcp and udp ports (2300-2400) to 10.1.0.1
#
# Remember that if you intend to forward something that you'll also
# have to add a rule to permit the inbound traffic.
#
$IPTABLES -t nat -A PREROUTING -i $OUTSIDE -p tcp --dport 80 -j DNAT --to 192.168.0.1
#$IPTABLES -t nat -A PREROUTING -i $OUTSIDE -p tcp --dport 22 -j DNAT --to 10.1.0.1
#$IPTABLES -t nat -A PREROUTING -i $OUTSIDE -p tcp --dport 2300:2400 -j DNAT --to 10.1.0.1
#$IPTABLES -t nat -A PREROUTING -i $OUTSIDE -p udp --dport 2300:2400 -j DNAT --to 10.1.0.1
#
# These are all TCP flag combinations that should never, ever, occur in the
# wild. All of these are illegal combinations that are used to attack a box
# in various ways.
#
$IPTABLES -A INPUT -p tcp --tcp-flags ALL FIN,URG,PSH -j tcpflags
$IPTABLES -A INPUT -p tcp --tcp-flags ALL ALL -j tcpflags
$IPTABLES -A INPUT -p tcp --tcp-flags ALL SYN,RST,ACK,FIN,URG -j tcpflags
$IPTABLES -A INPUT -p tcp --tcp-flags ALL NONE -j tcpflags
$IPTABLES -A INPUT -p tcp --tcp-flags SYN,RST SYN,RST -j tcpflags
$IPTABLES -A INPUT -p tcp --tcp-flags SYN,FIN SYN,FIN -j tcpflags
#
# Allow selected ICMP types and drop the rest.
#
$IPTABLES -A INPUT -p icmp --icmp-type 0 -j ACCEPT
$IPTABLES -A INPUT -p icmp --icmp-type 3 -j ACCEPT
$IPTABLES -A INPUT -p icmp --icmp-type 11 -j ACCEPT
$IPTABLES -A INPUT -p icmp --icmp-type 8 -m limit --limit 1/second -j ACCEPT
$IPTABLES -A INPUT -p icmp -j firewalled
#
# The loopback interface is inheritly trustworthy. Don't disable it or
# a number of things on the firewall will break. Uncomment the line following
# if the inside machines are trustworthy and there are services on the firewall,
# like DNS, web, DHCP etc., that they need to access. And remember to change the
# IP to be that of the INSIDE interface of the firewall.
#
$IPTABLES -A INPUT -i lo -j ACCEPT
$IPTABLES -A INPUT -i $INSIDE -d 192.168.0.2 -j ACCEPT
#
# Allow packets that are part of an established connection to pass
# through the firewall. This is required for normal Internet activity
# by inside clients.
#
$IPTABLES -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
#
# Silently drop and SMB traffic. We've slipped the surly bonds of windows
# and are dancing on the silvery wings of Linux, so block that windows trash.
#
#$IPTABLES -A INPUT -p udp --sport 137 --dport 137 -j silent
#
# If you want to be able to connect via SSH from the Internet
# uncomment the next line.
#
$IPTABLES -A INPUT -i $OUTSIDE -d 0/0 -p tcp --dport 22 -j ACCEPT
#
# Examples of allowing inbound for the port forwarding examples above.
#
$IPTABLES -A INPUT -i $OUTSIDE -d 192.168.0.1 -p tcp --dport 80 -j ACCEPT
#$IPTABLES -A INPUT -i $OUTSIDE -d 0/0 -p tcp --dport 80 -j ACCEPT
#$IPTABLES -A INPUT -i $OUTSIDE -d 0/0 -p tcp --dport 2300:2400 -j ACCEPT
#$IPTABLES -A INPUT -i $OUTSIDE -d 0/0 -p udp --dport 2300:2400 -j ACCEPT
#
# Anything that hasn't already matched gets logged and then dropped.
#
$IPTABLES -A INPUT -j firewalled  
Well... That looks good to me and it should work. You did enable IP forwarding, right? Note that if you did so by modifying /etc/sysctl.conf the change doesn't take affect until the next boot. You can manually enable forwarding by:

# echo 1 > /proc/sys/net/ipv4/ip_forward

Then apply the rules by executing the script. At that point I'd run tcpdump on the firewall (tcpdump -n -i eth1) and attempt a connection to the web server from the Internet. In the sniffer trace you should see the HTTP traffic leaving eth1 for 192.168.0.1. And if the web server is responding you should seen the return packets from 192.168.0.1 coming back to eth1 with a destination IP of your Internet test point.
Avatar of Jerf

ASKER

I got this - I have no idea what it means :)

[root@lennon jeff]# tcpdump -n -i ppp0 > dump
tcpdump: listening on ppp0

55 packets received by filter
0 packets dropped by kernel

[root@lennon jeff]# cat dump | grep http
20:14:41.584061 192.75.12.103.2110 > 192.168.0.1.http: S 668416803:668416803(0) win 6144 <mss 1460,nop,wscale 0,nop,nop,timestamp 1814460 0> (DF)

but nothing shows up in the log files in 192.168.0.1.  I'm baffled.
That tells me that a packet was received for the web server from 192.75.12.103 and that IPtables correctly decided that it was to be port forwarded to 192.168.0.1. However, since you ran tcpdump on the ppp interface we don't have conclusive hard evidence that the firewall routed the packet out the eth1 interface. I don't have much doubt that it in fact did so, but it would be nice to have the hard evidence. Run tcpdump again, but this time specify the INSIDE NIC, 'tcpdump -n -i eth1' I believe. I think that you'll see the same line in the output trace, which would indicate that the connection request made it through the firewall and out ont to internal net for 192.168.0.1. If that's the case then the web server isn't getting the packet, it doesn't think that it should respond, or it can't figure out how to respond.

Possible problems that could keep the web server from answering the request would be that it has local firewall rule set active. Also the web server could have been configured for other than access by any IP. Check to be sure that the directory where your web server looks for its htdocs is set for:

  Order allow,deny
  Allow from all

in your httpd.conf. Also make sure that your web server box is configured to use 192.168.0.2 (I believe that's the IP of eth1 on the firewall) as it's default route and the netmast on the firewall's eth1 interface and the webserver are the same (most likely they should use 255.255.255.0).

Note that if the default gateway on the web server is incorrect you'd still be able to access the web server from machines on your provate network. And that's because the traffic is purely local and the gateway isn't needed.
Avatar of Jerf

ASKER

Arg!  I'm a dumbass.  I just got the new DSL line and I was moving routers and I still had the cable box attached to the web server. Long story (kinda) short - I forgot to change the gateway of the web server.  jlevie - thanks a bunch for your help - I appreciate the extra effort you gave - I increased the points as well for my dumb mistake.

Hell - what do I know about computers?  I'm just a programmer :)
I figured that it might be something like that. I had good reason to believe that the firewall rule set would work because I use it like that all the time. So it just about had to be something else and a wrong gateway was pretty much at the top of my list. At any rate, I'me glad it's solved and you now have a good tool for other things that you might do with the firewall.

Cheers...