xpra icon
Bug tracker and wiki

Opened 4 years ago

Closed 4 years ago

Last modified 3 years ago

#952 closed defect (fixed)

proxy server is broken

Reported by: Antoine Martin Owned by: Antoine Martin
Priority: blocker Milestone: 0.16
Component: server Version: 0.15.x
Keywords: Cc:

Description

Not sure when it broke... but it needs work.
It needed updating for the new socket encryption code (see #933) - done in r10351, and also for the new pillow codec location - done in r10353.

Connecting a client via tcp seems to hang, the last messages are:

new_connection((1, <socket._socketobject object at 0x7f81d73b7c90>)) sock=<socket._socketobject object at 0x7f81d4c164b0>, timeout=0.1, sockname=('127.0.0.1', 10001), address=('127.0.0.1', 43991), peername=('127.0.0.1', 43991)
socket connection: tcp socket: 127.0.0.1:10001 <- 127.0.0.1:43991
New tcp connection received from 127.0.0.1:43991
socktype=tcp, auth class=<class 'xpra.server.auth.allow_auth.Authenticator'>, encryption=, keyfile=
io_thread_loop(write, <bound method Protocol._write of Protocol(tcp socket: 127.0.0.1:10001 <- 127.0.0.1:43991)>) loop starting

Change History (4)

comment:1 Changed 4 years ago by Antoine Martin

Status: newassigned

Mostly fixed with:

  • r10354: authentication fix (needs backporting)
  • r10355: missing threads init with the new glib replacing gobject
  • r10356: socket creation handling fix (may need backporting?)
  • this ugly patch should be replaced with blocking sockets: by the time the proxy is serving clients, we don't need timeouts (though I am not sure why we hit the retry on win32 and not on posix.. so maybe merge it too?):
    --- xpra/net/bytestreams.py	(revision 10350)
    +++ xpra/net/bytestreams.py	(working copy)
    @@ -16,7 +16,10 @@
     #on some platforms (ie: OpenBSD), reading and writing from sockets
     #raises an IOError but we should continue if the error code is EINTR
     #this wrapper takes care of it.
    -CONTINUE = {errno.EINTR : "EINTR"}
    +CONTINUE = {errno.EINTR : "EINTR",
    +            errno.EWOULDBLOCK : "EWOULDBLOCK"}
    +ERRNO_TEXT = dict((getattr(errno, x), x) for x in dir(errno) if x.startswith("E"))
    +
     ABORT = {
         errno.ECONNRESET    : "ECONNRESET",
         errno.EPIPE         : "EPIPE"}
    

comment:2 Changed 4 years ago by Antoine Martin

Resolution: fixed
Status: assignedclosed

In do_start_proxy the proxy server already does this:

                #now we can go back to using blocking sockets:
                self.set_socket_timeout(client_conn, None)
                client_conn.set_active(True)
                self.set_socket_timeout(server_conn, None)

But the proxy instance that gets started by this function still hits those EWOULDBLOCK errors.. because when the proxy server closes its socket wrappers, we call SocketConnection.close which now sets the socket to non-blocking so that we can exit the protocol read and write loops cleanly...

The code is inherently racy, with no easy way to fix it. I've tried re-ordering the subprocess start sequence and socket closing - and all I managed to do was to get more errors.

So r10373 takes the simple and more reliable approach of doing a more explicit handover using a dedicated message. (+ a very very odd fixup was required in r10374).

Backport not needed as 0.15 was not affected - not entirely sure why either!

comment:3 Changed 3 years ago by Antoine Martin

Found some more: r13527, r13529, r13530, r13531.

comment:4 Changed 3 years ago by Antoine Martin

See also #1264, #1271, #1298.

Found some more: r13538, r13555

Related authentication fixes: r13540, r13541, r13542, r13561 + r13565, r13564, and improvements: r13543, r13553, r13556

Note: See TracTickets for help on using tickets.