# x11 forwarding and iptables

## aaronf0

Hello, ive been all over google, the forums, the iptables site, and #iptables on freenode, but no one seems to know how to do this.

Is there any way at all to forward x11 connections over ssh (ssh -X) with iptables set to drop by default? I also cant figure out what ports X is using with the firewall off, so I cant enable them manually. Everything works fine when the firewall is off, and ssh works fine when the firewalls on, but X programs wont work. Any help?

----------

## Akhouk

When you do port forwarding over ssh like with X11 forwarding the data is sent within normal port 22 ssh tcp data. Therefore you don't need to open any port on the firewall accept TCP 22.

If you are talking about allowing ssh but disallowing X11 forwarding over SSH then this is next to impossible. The only thing you could do is to have something that either limits packet size or limits the amount of data sent (typically X11 over ssh will be much higher than interactive typing). Of course, this method would clobber use of scp and sftp since you cant tell what is in the encrypted packet.

----------

## aaronf0

No, just trying to get ssh and X to work. I have port 22 open, but its still stopping X. scp and normal ssh work fine though.

----------

## Akhouk

Are you sure the server side has X11 forwarding enabled in the sshd conf file. Also, make sure you have xauth on the X server so that it can create the authentication token.

----------

## aaronf0

as i said in the first post, X forwarding works fine without the firewall on.

when i turn it on, everything goes to hell.

xauth is installed already.

----------

## mks99

Let's say machine A is the machine you're sitting in front of, that has the X server running, where you expect the program windows to appear. Machine B is the machine you ssh into, where you start GUI programs (the GUI shall appear on A's screen).

When you do

```
user@A$ ssh -X B
```

ssh on B starts to listen on a port on the address 127.0.0.1 (loopback of B). The number of that port will be x+6000. By default x will be 10, i. e. ssh will bind to 127.0.0.1:6010. ssh will chose an other value for x if 6010 is already taken. Moreover ssh will set DISPLAY=localhost:10.0 (if x == 10). X clients started on B will then try to connect to 127.0.0.1:6010 and ssh will forward this connection to the X server on A.

Obviously, this won't work if iptables rules on B don't allow connections to 127.0.0.1:6010 (port number may be different as said above).

----------

## erik258

 *mks99 wrote:*   

> 
> 
> If you are talking about allowing ssh but disallowing X11 forwarding over SSH then this is next to impossible. The only thing you could do is to have something that either limits packet size or limits the amount of data sent (typically X11 over ssh will be much higher than interactive typing). Of course, this method would clobber use of scp and sftp since you cant tell what is in the encrypted packet.

 

you've got to be joking!  what about

 *`cat /etc/ssh/sshd_config` wrote:*   

> X11Forwarding no

 

or am I wrong?  I can't use X forwarding over ssh logins unless I uncomment that and turn it to "Yes"

 *aaronf0 wrote:*   

> X forwarding works fine without the firewall on. 

 

you could compare sequential packet counts in `iptables -v -L` to see where the packets are being dropped.

----------

## aaronf0

yes, everything works when the firewalls down. yes, i want x11-forwarding. heres the script, see if you can find any errors.

```
#!/bin/bash

IPTABLES="/sbin/iptables"

$IPTABLES -P INPUT DROP

$IPTABLES -P OUTPUT DROP

$IPTABLES -P FORWARD DROP

$IPTABLES -F

$IPTABLES -A INPUT -i eth0 -p all -m state --state ESTABLISHED,RELATED -j ACCEPT

$IPTABLES -A OUTPUT -o eth0 -j ACCEPT

$IPTABLES -A INPUT -i eth0 -p tcp --dport ssh --syn -m state --state NEW -j ACCEPT

$IPTABLES -A INPUT -i eth0 -p tcp --dport http --syn -m state --state NEW -j ACCEPT
```

----------

## mks99

 *aaronf0 wrote:*   

> yes, everything works when the firewalls down. yes, i want x11-forwarding. heres the script, see if you can find any errors.
> 
> ```
> #!/bin/bash
> 
> ...

 

As I said before: you have to allow connections to 127.0.0.1 resp. the loopback interface. That's what you don't do (provided the above snippet contains all the relevant rules). With the rules above you throw away absolutely everything - even packets from the local machine targeted to lo - except the few packet types going in and out eth0.

Add something like

```
$IPTABLES -A INPUT -i lo -j ACCEPT
```

Obviously, you can make the rule more restrictive (allowing only tcp, the relevant port etc.) but you should get the point.

----------

## erik258

$IPTABLES -A INPUT -i eth0 -p tcp --dport ssh --syn -m state --state NEW -j ACCEPT

$IPTABLES -A INPUT -i eth0 -p tcp --dport http --syn -m state --state NEW -j ACCEPT

I would have put 

```
$IPTABLES -A INPUT -i eth0 -p tcp --dport ssh -j ACCEPT
```

since I would be accepting new packets and established packets, i can't think of any packets to port 22 i wouldn't be accepting.

```
iptables -I INPUT -i lo -j ACCEPT
```

that should do the trick for loopback device.

----------

## aaronf0

ok, thank you, after enabling lo to do its stuff (input AND output) it works now. thanks.

----------

## erik258

sweet ; )

----------

