From 372b8d404a2c34e027e76681bb4fd22f0a079f7d Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Tom=C3=A1=C5=A1=20Cerha?= <t.cerha@gmail.com>
Date: Tue, 21 Jun 2022 14:46:48 +0200
Subject: [PATCH] Prevent infinite loop in X2GoRevFwTunnel handler

Without this change, we observed a running X2Go session freezing after about 3
hours running on Windows with the following output:

WARN: Reverse tunnel <paramiko.Channel 16 (open) window=2036405 ->
<paramiko.Transport at 0x4e4f270L (cipher aes128-ctr, 128 bits) (active; 2 open
channel(s))>> encoutered socket error: [Errno 10054] An existing connection was
forcibly closed by the remote host

Breaking after catching 1024 socket errors prevents looping forever.  The
tunnel is automatically closed, which allows the application to reopen it
automatically and recover gracefully from the situation.
---
 x2go/rforward.py | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/x2go/rforward.py b/x2go/rforward.py
index e60931b..c5eae5d 100644
--- a/x2go/rforward.py
+++ b/x2go/rforward.py
@@ -330,6 +330,7 @@ def x2go_rev_forward_channel_handler(chan=None, addr='', port=0, parent_thread=N
     logger('Connected! Reverse tunnel open %r -> %r -> %r' % (chan.origin_addr,
                                                               chan.getpeername(), (addr, port)),
                                                               loglevel=log.loglevel_INFO)
+    n = 0
     while parent_thread._accept_channels:
         r, w, x = select.select([fw_socket, chan], [], [])
         try:
@@ -345,6 +346,9 @@ def x2go_rev_forward_channel_handler(chan=None, addr='', port=0, parent_thread=N
                 fw_socket.send(data)
         except socket.error as e:
             logger('Reverse tunnel %s encoutered socket error: %s' % (chan, str(e)), loglevel=log.loglevel_WARN)
+            n += 1
+            if n >= 1024:
+                break
 
     chan.close()
     fw_socket.close()
-- 
2.33.0

