I’m trying to host a web server in a VM using port forwarding. I set up the required iptables rules, and I can successfully access my website using the host IP. However, after setting these rules, the VM is unable to access remote websites on port 80.
What works
external device => host => guest vm
guest vm => host => external device on ports other than 80 / 443
what works (without setting IPTABLES)
guest vm => host => external device (aka google.com:80)
what does not work (when setting IPTABLES)
guest vm => host => external device (aka google.com:80)
Iptables rules applied:
sudo iptables -I FORWARD -o virbr0 -p tcp -d 192.168.122.138 --dport 8080 -j ACCEPT
sudo iptables -t nat -I PREROUTING -p tcp --dport 80 -j DNAT --to 192.168.122.138:8080
sudo iptables -I FORWARD -o virbr0 -p tcp -d 192.168.122.138 --dport 8443 -j ACCEPT
sudo iptables -t nat -I PREROUTING -p tcp --dport 443 -j DNAT --to 192.168.122.138:8443
output of iptables -S
-P INPUT ACCEPT
-P FORWARD ACCEPT
-P OUTPUT ACCEPT
-N LIBVIRT_FWI
-N LIBVIRT_FWO
-N LIBVIRT_FWX
-N LIBVIRT_INP
-N LIBVIRT_OUT
-A INPUT -j LIBVIRT_INP
-A FORWARD -d 192.168.122.138/32 -o virbr0 -p tcp -m tcp --dport 8443 -j ACCEPT
-A FORWARD -d 192.168.122.138/32 -o virbr0 -p tcp -m tcp --dport 8080 -j ACCEPT
-A FORWARD -d 192.168.122.138/32 -o virbr0 -p tcp -m tcp --dport 8080 -j ACCEPT
-A FORWARD -j LIBVIRT_FWX
-A FORWARD -j LIBVIRT_FWI
-A FORWARD -j LIBVIRT_FWO
-A OUTPUT -j LIBVIRT_OUT
-A LIBVIRT_FWI -d 192.168.122.0/24 -o virbr0 -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
-A LIBVIRT_FWI -o virbr0 -j REJECT --reject-with icmp-port-unreachable
-A LIBVIRT_FWO -s 192.168.122.0/24 -i virbr0 -j ACCEPT
-A LIBVIRT_FWO -i virbr0 -j REJECT --reject-with icmp-port-unreachable
-A LIBVIRT_FWX -i virbr0 -o virbr0 -j ACCEPT
-A LIBVIRT_INP -i virbr0 -p udp -m udp --dport 53 -j ACCEPT
-A LIBVIRT_INP -i virbr0 -p tcp -m tcp --dport 53 -j ACCEPT
-A LIBVIRT_INP -i virbr0 -p udp -m udp --dport 67 -j ACCEPT
-A LIBVIRT_INP -i virbr0 -p tcp -m tcp --dport 67 -j ACCEPT
-A LIBVIRT_OUT -o virbr0 -p udp -m udp --dport 53 -j ACCEPT
-A LIBVIRT_OUT -o virbr0 -p tcp -m tcp --dport 53 -j ACCEPT
-A LIBVIRT_OUT -o virbr0 -p udp -m udp --dport 68 -j ACCEPT
-A LIBVIRT_OUT -o virbr0 -p tcp -m tcp --dport 68 -j ACCEPT
output iptables -S -t nat
-P PREROUTING ACCEPT
-P INPUT ACCEPT
-P OUTPUT ACCEPT
-P POSTROUTING ACCEPT
-N LIBVIRT_PRT
-A PREROUTING -p tcp -m tcp --dport 443 -j DNAT --to-destination 192.168.122.138:8443
-A PREROUTING -p tcp -m tcp --dport 80 -j DNAT --to-destination 192.168.122.138:8080
-A POSTROUTING -j LIBVIRT_PRT
-A LIBVIRT_PRT -s 192.168.122.0/24 -d 224.0.0.0/24 -j RETURN
-A LIBVIRT_PRT -s 192.168.122.0/24 -d 255.255.255.255/32 -j RETURN
-A LIBVIRT_PRT -s 192.168.122.0/24 ! -d 192.168.122.0/24 -p tcp -j MASQUERADE --to-ports 1024-65535
-A LIBVIRT_PRT -s 192.168.122.0/24 ! -d 192.168.122.0/24 -p udp -j MASQUERADE --to-ports 1024-65535
-A LIBVIRT_PRT -s 192.168.122.0/24 ! -d 192.168.122.0/24 -j MASQUERADE
I tried to change the guest port from 80 to 8080 (while keeping the iptables host port on 80)
I feel like it has something todo with the nat table as deleting the rule
sudo iptables -t nat -I PREROUTING -p tcp --dport 80 -j DNAT --to 192.168.122.138:8080
fixes the roule but (of course) the server is not reachable from the internet anymore