UPnP and iptables

Aight - I solved the issue :slight_smile:

WARNING: WILL MAKE YOUR SYSTEM SOMEWHAT VULNERABLE

Here is a script that will listen on port 1900 for udp packages and if one is received open up the ports 40000-65000 from the local subnet.

Just replace 10.10.10.254/24 with your own gateway - i.e. 192.168.0.1/24 etc.

    #########       UPnP        ###########

#allows for related ports to be opened along with ones already established. Does not work on its own
-A INPUT -s 10.10.10.254/24 -i eno1 -p udp -m state --state RELATED,ESTABLISHED -j ACCEPT

# Upon a udp package being received on port 1900 from the local subnet 
# the port range 40000:65000 is opened for 30 seconds.

# Create chain and give packages received name
-N INTO-PHASE2
-A INTO-PHASE2 -m recent --name PHASE1 --remove
-A INTO-PHASE2 -m recent --name PHASE2 --set
#log this event
-A INTO-PHASE2 -j LOG --log-prefix "INTO PHASE2: " --log-level 7

# Name incoming packages
-A INPUT -m recent --update --name PHASE1

# Move packages along the chain
-A INPUT -s 10.10.10.254/24 -i eno1 -p udp -m udp --dport 1900 -m recent --set --name PHASE1
-A INPUT -p udp -s 10.10.10.254/24 --match multiport --dports 40000:65000 -m recent --rcheck --name PHASE1 -j INTO-PHASE2

# Open up for ports 40000:65000 when a package from the local subnet passes is checked for existing in the chain INTO-PHASE2 and is an udp package.
-A INPUT -p udp -s 10.10.10.254/24 --match multiport --dports 40000:65000 -m recent --rcheck --seconds 10 --name PHASE2 -j ACCEPT

#############

Mind you this is only a part of a iptables config - but it is the part necessary for UPnP to work. It is not extremely secure but it will allow you to use syncthing while having iptables up n’ running.

On arch linux this data is entered into the file: /etc/iptables/iptables.rules It will depend from distro to distro.

Future improvements to this setup:

  1. Know the exact range of the ports that syncthing UPnP uses - anyone?
  2. Figure out exactly how long the ports need to stay open for the syncthing UPnP queries to work.

Cheers,

################### EDIT:

It seems did not quite solve it. Don’t know what happened, perhaps I deleted something in the beautification process… (making it readable)

Here is the updated version - I cannot quite figure out the issue

    ########################################
#########       UPnP        ###########

#allows for related ports to be opened along with ones already established. Does not work on its own
-A INPUT -s 10.10.10.254/24 -i eno1 -p udp -m state --state RELATED,ESTABLISHED -j ACCEPT

#Open up for the multicast discovery (THESE SHOULD BE DELETED ONE BY ONE TO TEST WHICH ARE NEEDED)
-A INPUT -i eno1 -d 224.0.0.0/8 -p igmp -j ACCEPT
-A INPUT -i eno1 -s 0.0.0.0/32 -d 224.0.0.1/32 -p igmp -j ACCEPT
-A INPUT -p igmp -j ACCEPT
-A INPUT -p icmp -j ACCEPT
-A INPUT -i lo -j ACCEPT

# Upon a udp package being received on port 1900 from the local subnet
# the port range 40000:65000 is opened for 30 seconds.

#0 Create chain and give packages received name
-N INTO-PHASE2

#3 Take all packages arriving in chain INTO-PHASE2 and rename them from PHASE1 to PHASE 2 and log the event
-A INTO-PHASE2 -m recent --name PHASE1 --remove
-A INTO-PHASE2 -m recent --name PHASE2 --set
-A INTO-PHASE2 -j LOG --log-prefix "INTO PHASE2: "

#1 Name incoming packages
-A INPUT -s 10.10.10.254/24 -p udp -m recent --update --name PHASE1

#1 Name packages from port 1900 from local subnet and name it PHASE1
-A INPUT -s 10.10.10.254/24 -i eno1 -p udp -m udp --dport 1900 -m recent --set --name PHASE1 -j INTO-PHASE2

# Check for whether a package received on portrange has a sender with the same IP as sender of package PHASE1, if so, pass package into the INTO-PHASE2 chain.
-A INPUT -s 10.10.10.254/24 -p udp --match multiport --dports 30000:65000 -m recent --rcheck --name PHASE1 -j ACCEPT

# Check packages arriving at portrange from local subnet to see if they have the name "PHASE2" - they they do and they are recent open accepting all packages the portrange for 30 seconds
-A INPUT -s 10.10.10.254/24 -p udp --match multiport --dports 30000:65000 -m recent --rcheck --seconds 30 --name PHASE2 -j ACCEPT

#test
#-A INPUT -s 10.10.10.254/24 -p udp --match multiport --dports 30000:65000 -j ACCEPT

#############