예제 #1
0
 def import_ns(self, namespace):
     """
     """
     pythonshare._send(Request_ns(namespace), self._to_server)
     rv = pythonshare._recv(self._from_server)
     if isinstance(rv, Ns_rv) and rv.status:
         return True
     else:
         raise pythonshare.PythonShareError(rv.errormsg)
예제 #2
0
파일: server.py 프로젝트: askervin/fMBT
def _remote_execute(ns, exec_msg):
    rns = _g_remote_namespaces[ns]
    pythonshare._send(exec_msg, rns.to_remote)
    try:
        return pythonshare._recv(rns.from_remote)
    except AttributeError:
        # If another thread closes the connection between send/recv,
        # cPickle.load() may raise "'NoneType' has no attribute 'recv'".
        # Make this look like EOF (connection lost)
        raise EOFError()
예제 #3
0
def _remote_execute(ns, exec_msg):
    rns = _g_remote_namespaces[ns]
    pythonshare._send(exec_msg, rns.to_remote)
    try:
        return pythonshare._recv(rns.from_remote)
    except AttributeError:
        # If another thread closes the connection between send/recv,
        # cPickle.load() may raise "'NoneType' has no attribute 'recv'".
        # Make this look like EOF (connection lost)
        raise EOFError()
예제 #4
0
    def __init__(self, host_or_from_server, port_or_to_server,
                 password=None, namespace="default"):
        """Connect to a pythonshare server

        The server is listening to connections at host:port, or it can be
        communicated via file-like objects from_server and to_server.

        Parameters:

          host_or_from_server (string or file-like object)
                  string: host
                  file: file for receiving messages from the server

          port_or_to_server (int or file-like object)
                  int: port number
                  file: file for sending messages to the server

          password (string, optional)
                  server password. The default is None, that is,
                  do not send password to the server when connecting.

          namespace (string, optional)
                  the default namespace that is used on eval_() and exec_().
                  The default is "default".
        """
        self.set_namespace(namespace)

        if isinstance(host_or_from_server, str) and isinstance(port_or_to_server, int):
            host = host_or_from_server
            port = port_or_to_server
            pythonshare._check_hook("before:client.socket.connect", {"host": host, "port": port})
            self._s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
            self._s.connect((host, port))
            self._from_server = self._s.makefile("r")
            self._to_server = self._s.makefile("w")
        elif isinstance(host_or_from_server, file) and isinstance(port_or_to_server, file):
            self._s = None
            self._to_server = port_or_to_server
            self._from_server = host_or_from_server
        else:
            raise ValueError("invalid host:port (str:int) or to_server:from_server (file:file)")

        if password:
            # authenticate to server
            pythonshare._send(password, self._to_server)
            auth_rv = pythonshare._recv(self._from_server)
            try:
                auth_ok = auth_rv.success
            except AttributeError:
                auth_ok = False
            if not auth_ok:
                raise pythonshare.AuthenticationError("Permission denied")
예제 #5
0
def _remote_execute_and_forward(ns, exec_msg, to_client, peername=None):
    """returns (forward_status, info)
    forward_status values:
       True:  everything successfully forwarded,
              info contains pair (forwarded byte count, full length).
       False: not everything forwarded,
              info contains pair (forwarded byte count, full length).
              to_client file/socket is not functional.
       None:  no forwarding,
              info contains Exec_rv that should be sent normally.
    Raises EOFError if connection to remote namespace is not functional.

    The peername parameter is used for logging only.
    """
    client_supports_rv_info = exec_msg.recv_cap_data_info()
    exec_msg.set_recv_cap_data_info(True)
    rns = _g_remote_namespaces[ns]
    pythonshare._send(exec_msg, rns.to_remote)
    from_remote = rns.from_remote
    # Must keep simultaneously two locks:
    # - send lock on to_client
    # - recv lock on from_remote
    pythonshare._acquire_recv_lock(from_remote)
    try:
        response = pythonshare._recv(from_remote, acquire_recv_lock=False)
        if not isinstance(response, messages.Data_info):
            # Got direct response without forward mode
            return (None, response)
        pythonshare._acquire_send_lock(to_client)
        if client_supports_rv_info:
            # send data_info to client
            pythonshare._send(response, to_client, acquire_send_lock=False)
        try:
            if opt_debug and peername:
                daemon_log("%s:%s <= Exec_rv([forwarding %s B])" %
                           (peername + (response.data_length, )))
            forwarded_bytes = pythonshare._forward(from_remote,
                                                   to_client,
                                                   response.data_length,
                                                   acquire_recv_lock=False,
                                                   acquire_send_lock=False)
            if forwarded_bytes == response.data_length:
                return (True, (forwarded_bytes, response.data_length))
            else:
                return (False, (forwarded_bytes, response.data_length))
        finally:
            pythonshare._release_send_lock(to_client)
    finally:
        exec_msg.set_recv_cap_data_info(client_supports_rv_info)
        pythonshare._release_recv_lock(from_remote)
예제 #6
0
def _serve_connection(conn, conn_opts):
    global _g_async_rv_counter
    global _g_server_shutdown
    if isinstance(conn, client.Connection):
        to_client = conn._to_server
        from_client = conn._from_server
    else: # conn is a connected socket
        to_client = conn.makefile("w")
        from_client = conn.makefile("r")
    try:
        peername = conn.getpeername()
    except socket.error:
        peername = ("unknown", "?")
    if opt_debug:
        daemon_log("connected %s:%s" % peername)
    conn_id = "%s-%s" % (timestamp(), id(conn))
    auth_ok = False
    passwords = [k for k in conn_opts.keys() if k.startswith("password.")]
    kill_server_on_close = conn_opts.get("kill-server-on-close", False)
    if passwords:
        # password authentication is required for this connection
        try:
            received_password = pythonshare._recv(from_client)
        except Exception, e:
            daemon_log('error receiving password: %r' % (e,))
            received_password = None
        for password_type in passwords:
            algorithm = password_type.split(".")[1]
            if type(received_password) == str:
                if (algorithm == "plaintext" and
                    received_password == conn_opts[password_type]):
                    auth_ok = True
                elif (hasattr(hashlib, algorithm) and
                      getattr(hashlib, algorithm)(received_password).hexdigest() ==
                      conn_opts[password_type]):
                    auth_ok = True
        try:
            if auth_ok:
                pythonshare._send(messages.Auth_rv(True), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication ok" % peername)
            elif not received_password is None:
                pythonshare._send(messages.Auth_rv(False), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication failed" % peername)
        except socket.error:
            daemon_log("authentication failed due to socket error")
            auth_ok = False
예제 #7
0
파일: server.py 프로젝트: 01org/fMBT
def _serve_connection(conn, conn_opts):
    global _g_async_rv_counter
    global _g_server_shutdown
    if isinstance(conn, client.Connection):
        to_client = conn._to_server
        from_client = conn._from_server
    else: # conn is a connected socket
        to_client = conn.makefile("w")
        from_client = conn.makefile("r")
    try:
        peername = conn.getpeername()
    except socket.error:
        peername = ("unknown", "?")
    if opt_debug:
        daemon_log("connected %s:%s" % peername)
    conn_id = "%s-%s" % (timestamp(), id(conn))
    auth_ok = False
    passwords = [k for k in conn_opts.keys() if k.startswith("password.")]
    kill_server_on_close = conn_opts.get("kill-server-on-close", False)
    if passwords:
        # password authentication is required for this connection
        try:
            received_password = pythonshare._recv(from_client)
        except Exception, e:
            daemon_log('error receiving password: %r' % (e,))
            received_password = None
        for password_type in passwords:
            algorithm = password_type.split(".")[1]
            if type(received_password) == str:
                if (algorithm == "plaintext" and
                    received_password == conn_opts[password_type]):
                    auth_ok = True
                elif (hasattr(hashlib, algorithm) and
                      getattr(hashlib, algorithm)(received_password).hexdigest() ==
                      conn_opts[password_type]):
                    auth_ok = True
        try:
            if auth_ok:
                pythonshare._send(messages.Auth_rv(True), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication ok" % peername)
            elif not received_password is None:
                pythonshare._send(messages.Auth_rv(False), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication failed" % peername)
        except socket.error:
            daemon_log("authentication failed due to socket error")
            auth_ok = False
예제 #8
0
파일: server.py 프로젝트: 01org/fMBT
def _remote_execute_and_forward(ns, exec_msg, to_client, peername=None):
    """returns (forward_status, info)
    forward_status values:
       True:  everything successfully forwarded,
              info contains pair (forwarded byte count, full length).
       False: not everything forwarded,
              info contains pair (forwarded byte count, full length).
              to_client file/socket is not functional.
       None:  no forwarding,
              info contains Exec_rv that should be sent normally.
    Raises EOFError if connection to remote namespace is not functional.

    The peername parameter is used for logging only.
    """
    client_supports_rv_info = exec_msg.recv_cap_data_info()
    exec_msg.set_recv_cap_data_info(True)
    rns = _g_remote_namespaces[ns]
    from_remote = rns.from_remote
    # Must keep simultaneously two locks:
    # - send lock on to_client
    # - recv lock on from_remote
    pythonshare._acquire_recv_lock(from_remote)
    try:
        pythonshare._send(exec_msg, rns.to_remote)
        response = pythonshare._recv(from_remote, acquire_recv_lock=False)
        if not isinstance(response, messages.Data_info):
            # Got direct response without forward mode
            return (None, response)
        pythonshare._acquire_send_lock(to_client)
        if client_supports_rv_info:
            # send data_info to client
            pythonshare._send(response, to_client, acquire_send_lock=False)
        try:
            if opt_debug and peername:
                daemon_log("%s:%s <= Exec_rv([forwarding %s B])" % (peername + (response.data_length,)))
            forwarded_bytes = pythonshare._forward(
                from_remote, to_client, response.data_length,
                acquire_recv_lock=False,
                acquire_send_lock=False)
            if forwarded_bytes == response.data_length:
                return (True, (forwarded_bytes, response.data_length))
            else:
                return (False, (forwarded_bytes, response.data_length))
        finally:
            pythonshare._release_send_lock(to_client)
    finally:
        exec_msg.set_recv_cap_data_info(client_supports_rv_info)
        pythonshare._release_recv_lock(from_remote)
예제 #9
0
    def drop_ns(self, namespace):
        """Delete namespace from the remote peer

        Parameters:

          namespace (string)
                  Namespace to be dropped, can be local or
                  remote to the server.

        Returns True on success or raises an exception.
        """
        pythonshare._send(Drop_ns(namespace), self._to_server)
        rv = pythonshare._recv(self._from_server)
        if isinstance(rv, Ns_rv) and rv.status:
            return True
        else:
            raise pythonshare.PythonShareError(rv.errormsg)
예제 #10
0
    def unlock_ns(self, namespace):
        """Unlock namespace on the remote peer

        Parameters:

          namespace (string)
                  Namespace to be unlocked, can be local or
                  remote to the server.

        Returns True on success or raises an exception.
        """
        pythonshare._send(Server_ctl("unlock", namespace), self._to_server)
        rv = pythonshare._recv(self._from_server)
        if isinstance(rv, Server_ctl_rv) and rv.status == 0:
            return True
        else:
            raise pythonshare.PythonShareError(rv.message)
예제 #11
0
    def export_ns(self, namespace):
        """Export namespace to remote peer

        Parameters:

          namespace (string)
                  Namespace to be exported, can be local or
                  remote to current host.

        Returns True on success or raises an exception.  If succeeded,
        this connection becomes a server for requests from remote
        peer. (The remote peer accesses registered namespace through
        this connection object.)
        """
        pythonshare._send(Register_ns(namespace), self._to_server)
        rv = pythonshare._recv(self._from_server)
        if isinstance(rv, Ns_rv) and rv.status:
            return True
        else:
            raise pythonshare.PythonShareError(rv.errormsg)
예제 #12
0
파일: client.py 프로젝트: askervin/fMBT
                  returned. The default is False.

          lock (boolean, optional)
                  lock the namespace from others until this execution
                  has finished. The default is True.

        Returns return value from expr or None.

        Raise RemoteExecError or RemoteEvalError if code or expr caused
        an exception in remote end, respectively.

        """
        if namespace == None:
            namespace = self.namespace()
        try:
            pythonshare._send(Exec(namespace, code, expr, async=async, lock=lock), self._to_server)
            return self.make_local(pythonshare._recv(self._from_server))
        except EOFError:
            raise pythonshare.PythonShareError(
                'No connection to namespace "%s"' % (namespace,))

    def eval_(self, expr, **kwargs):
        """Evaluate expr in the default namespace.

        See eval_in for optional parameters."""
        return self.eval_in(self._ns, expr, **kwargs)

    def eval_in(self, namespace, expr, async=False, lock=True):
        """Evaluate expr in a namespace.

        Parameters:
예제 #13
0
                    _drop_remote_namespace(obj.ns)
                else:
                    raise ValueError('Unknown namespace "%s"' % (obj.ns, ))
                pythonshare._send(messages.Ns_rv(True), to_client)
            except Exception, e:
                if opt_debug:
                    daemon_log("namespace drop error: %s" % (e, ))
                pythonshare._send(
                    messages.Ns_rv(False, exception2string(sys.exc_info())),
                    to_client)

        elif isinstance(obj, messages.Request_ns):
            ns = obj.ns
            if (ns in _g_remote_namespaces or ns in _g_local_namespaces):
                _register_exported_namespace(ns, conn)
                pythonshare._send(messages.Ns_rv(True), to_client)
                # from this point on, this connection is reserved for
                # receiving executions on requested namespace. This
                # thread starts serving the connection.

        elif isinstance(obj, messages.Exec):
            ns = obj.namespace
            if ns in _g_remote_namespaces:  # execute in remote namespace
                try:
                    exec_rv = _remote_execute(ns, obj)
                except (EOFError, socket.error):  # connection lost
                    daemon_log('connection lost to "%s"' % (ns, ))
                    _drop_remote_namespace(ns)
                    break
            else:  # execute in local namespace
                if whitelist_local == None or ns in whitelist_local:
예제 #14
0
        auth_ok = True # no password required

    whitelist_local = conn_opts.get("whitelist_local", None)

    while auth_ok:
        try:
            obj = pythonshare._recv(from_client)
            if opt_debug:
                daemon_log("%s:%s => %s" % (peername + (obj,)))
        except (EOFError, pythonshare.socket.error):
            break

        if isinstance(obj, messages.Register_ns):
            try:
                _init_remote_namespace(obj.ns, conn, to_client, from_client)
                pythonshare._send(messages.Ns_rv(True), to_client)
                # from this point on, this connection is reserved for
                # sending remote namespace traffic. The connection will be
                # used by other threads, this thread stops here.
                return
            except Exception, e:
                pythonshare._send(messages.Ns_rv(False, exception2string(sys.exc_info())), to_client)

        elif isinstance(obj, messages.Drop_ns):
            try:
                if obj.ns in _g_local_namespaces:
                    _drop_local_namespace(obj.ns)
                elif obj.ns in _g_remote_namespaces:
                    _drop_remote_namespace(obj.ns)
                else:
                    raise ValueError('Unknown namespace "%s"' % (obj.ns,))
예제 #15
0
def _remote_execute(ns, exec_msg):
    rns = _g_remote_namespaces[ns]
    pythonshare._send(exec_msg, rns.to_remote)
    # _recv raises EOFError() if disconnected,
    # let it raise through.
    return pythonshare._recv(rns.from_remote)
예제 #16
0
파일: server.py 프로젝트: askervin/fMBT
                elif obj.ns in _g_remote_namespaces:
                    _drop_remote_namespace(obj.ns)
                else:
                    raise ValueError('Unknown namespace "%s"' % (obj.ns,))
                pythonshare._send(messages.Ns_rv(True), to_client)
            except Exception, e:
                if opt_debug:
                    daemon_log("namespace drop error: %s" % (e,))
                pythonshare._send(messages.Ns_rv(False, exception2string(sys.exc_info())), to_client)

        elif isinstance(obj, messages.Request_ns):
            ns = obj.ns
            if (ns in _g_remote_namespaces or
                ns in _g_local_namespaces):
                _register_exported_namespace(ns, conn)
                pythonshare._send(messages.Ns_rv(True), to_client)
                # from this point on, this connection is reserved for
                # receiving executions on requested namespace. This
                # thread starts serving the connection.

        elif isinstance(obj, messages.Exec):
            ns = obj.namespace
            if ns in _g_remote_namespaces: # execute in remote namespace
                try:
                    exec_rv = _remote_execute(ns, obj)
                except (EOFError, socket.error): # connection lost
                    daemon_log('connection lost to "%s"' % (ns,))
                    _drop_remote_namespace(ns)
                    break
            else: # execute in local namespace
                if whitelist_local == None or ns in whitelist_local:
예제 #17
0
 def kill_server(self, namespace=None):
     """Send server shutdown message"""
     if namespace == None:
         namespace = self.namespace()
     pythonshare._send(Server_ctl("die", namespace), self._to_server)
     return True
예제 #18
0
파일: server.py 프로젝트: askervin/fMBT
def _serve_connection(conn, conn_opts):
    global _g_async_rv_counter
    global _g_server_shutdown
    if isinstance(conn, client.Connection):
        to_client = conn._to_server
        from_client = conn._from_server
    else: # conn is a connected socket
        to_client = conn.makefile("w")
        from_client = conn.makefile("r")
    try:
        peername = conn.getpeername()
    except socket.error:
        peername = ("unknown", "?")
    if opt_debug:
        daemon_log("connected %s:%s" % peername)
    conn_id = "%s-%s" % (timestamp(), id(conn))
    auth_ok = False
    passwords = [k for k in conn_opts.keys() if k.startswith("password.")]
    kill_server_on_close = conn_opts.get("kill-server-on-close", False)
    if passwords:
        # password authentication is required for this connection
        received_password = pythonshare._recv(from_client)
        for password_type in passwords:
            algorithm = password_type.split(".")[1]
            if type(received_password) == str:
                if (algorithm == "plaintext" and
                    received_password == conn_opts[password_type]):
                    auth_ok = True
                elif (hasattr(hashlib, algorithm) and
                      getattr(hashlib, algorithm)(received_password).hexdigest() ==
                      conn_opts[password_type]):
                    auth_ok = True
        try:
            if auth_ok:
                pythonshare._send(messages.Auth_rv(True), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication ok" % peername)
            else:
                pythonshare._send(messages.Auth_rv(False), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication failed" % peername)
        except socket.error:
            daemon_log("authentication failed due to socket error")
            auth_ok = False
    else:
        auth_ok = True # no password required

    whitelist_local = conn_opts.get("whitelist_local", None)

    while auth_ok:
        try:
            obj = pythonshare._recv(from_client)
            if opt_debug:
                daemon_log("%s:%s => %s" % (peername + (obj,)))
        except (EOFError, pythonshare.socket.error):
            break

        if isinstance(obj, messages.Register_ns):
            try:
                _init_remote_namespace(obj.ns, conn, to_client, from_client)
                pythonshare._send(messages.Ns_rv(True), to_client)
                # from this point on, this connection is reserved for
                # sending remote namespace traffic. The connection will be
                # used by other threads, this thread stops here.
                return
            except Exception, e:
                pythonshare._send(messages.Ns_rv(False, exception2string(sys.exc_info())), to_client)

        elif isinstance(obj, messages.Drop_ns):
            try:
                if obj.ns in _g_local_namespaces:
                    _drop_local_namespace(obj.ns)
                elif obj.ns in _g_remote_namespaces:
                    _drop_remote_namespace(obj.ns)
                else:
                    raise ValueError('Unknown namespace "%s"' % (obj.ns,))
                pythonshare._send(messages.Ns_rv(True), to_client)
            except Exception, e:
                if opt_debug:
                    daemon_log("namespace drop error: %s" % (e,))
                pythonshare._send(messages.Ns_rv(False, exception2string(sys.exc_info())), to_client)
예제 #19
0
파일: client.py 프로젝트: 01org/fMBT
          lock (boolean, optional)
                  lock the namespace from others until this execution
                  has finished. The default is True.

        Returns return value from expr or None.

        Raise RemoteExecError or RemoteEvalError if code or expr caused
        an exception in remote end, respectively.

        """
        if namespace == None:
            namespace = self.namespace()
        pythonshare._check_hook("before:client.exec_in", {"code": code, "expr": expr, "namespace": namespace, "async": async, "lock": lock})
        try:
            pythonshare._send(Exec(
                namespace, code, expr, async=async, lock=lock,
                recv_caps=pythonshare.messages.RECV_CAP_COMPRESSION), self._to_server)
            response = pythonshare._recv_with_info(self._from_server)
            return self.make_local(response)
        except EOFError:
            raise pythonshare.PythonShareError(
                'No connection to namespace "%s"' % (namespace,))

    def eval_(self, expr, **kwargs):
        """Evaluate expr in the default namespace.

        See eval_in for optional parameters."""
        return self.eval_in(self._ns, expr, **kwargs)

    def eval_in(self, namespace, expr, async=False, lock=True):
예제 #20
0
파일: server.py 프로젝트: 01org/fMBT
def _remote_execute(ns, exec_msg):
    rns = _g_remote_namespaces[ns]
    pythonshare._send(exec_msg, rns.to_remote)
    # _recv raises EOFError() if disconnected,
    # let it raise through.
    return pythonshare._recv(rns.from_remote)
예제 #21
0
def _serve_connection(conn, conn_opts):
    global _g_async_rv_counter
    global _g_server_shutdown
    if isinstance(conn, client.Connection):
        to_client = conn._to_server
        from_client = conn._from_server
    else:  # conn is a connected socket
        to_client = conn.makefile("w")
        from_client = conn.makefile("r")
    try:
        peername = conn.getpeername()
    except socket.error:
        peername = ("unknown", "?")
    if opt_debug:
        daemon_log("connected %s:%s" % peername)
    conn_id = "%s-%s" % (timestamp(), id(conn))
    auth_ok = False
    passwords = [k for k in conn_opts.keys() if k.startswith("password.")]
    kill_server_on_close = conn_opts.get("kill-server-on-close", False)
    if passwords:
        # password authentication is required for this connection
        received_password = pythonshare._recv(from_client)
        for password_type in passwords:
            algorithm = password_type.split(".")[1]
            if type(received_password) == str:
                if (algorithm == "plaintext"
                        and received_password == conn_opts[password_type]):
                    auth_ok = True
                elif (hasattr(hashlib, algorithm) and getattr(
                        hashlib, algorithm)(received_password).hexdigest()
                      == conn_opts[password_type]):
                    auth_ok = True
        try:
            if auth_ok:
                pythonshare._send(messages.Auth_rv(True), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication ok" % peername)
            else:
                pythonshare._send(messages.Auth_rv(False), to_client)
                if opt_debug:
                    daemon_log("%s:%s authentication failed" % peername)
        except socket.error:
            daemon_log("authentication failed due to socket error")
            auth_ok = False
    else:
        auth_ok = True  # no password required

    whitelist_local = conn_opts.get("whitelist_local", None)

    while auth_ok:
        try:
            obj = pythonshare._recv(from_client)
            if opt_debug:
                daemon_log("%s:%s => %s" % (peername + (obj, )))
        except (EOFError, pythonshare.socket.error):
            break

        if isinstance(obj, messages.Register_ns):
            try:
                _init_remote_namespace(obj.ns, conn, to_client, from_client)
                pythonshare._send(messages.Ns_rv(True), to_client)
                # from this point on, this connection is reserved for
                # sending remote namespace traffic. The connection will be
                # used by other threads, this thread stops here.
                return
            except Exception, e:
                pythonshare._send(
                    messages.Ns_rv(False, exception2string(sys.exc_info())),
                    to_client)

        elif isinstance(obj, messages.Drop_ns):
            try:
                if obj.ns in _g_local_namespaces:
                    _drop_local_namespace(obj.ns)
                elif obj.ns in _g_remote_namespaces:
                    _drop_remote_namespace(obj.ns)
                else:
                    raise ValueError('Unknown namespace "%s"' % (obj.ns, ))
                pythonshare._send(messages.Ns_rv(True), to_client)
            except Exception, e:
                if opt_debug:
                    daemon_log("namespace drop error: %s" % (e, ))
                pythonshare._send(
                    messages.Ns_rv(False, exception2string(sys.exc_info())),
                    to_client)
예제 #22
0
파일: server.py 프로젝트: 01org/fMBT
        auth_ok = True # no password required

    whitelist_local = conn_opts.get("whitelist_local", None)

    while auth_ok:
        try:
            obj = pythonshare._recv(from_client)
            if opt_debug:
                daemon_log("%s:%s => %s" % (peername + (obj,)))
        except (EOFError, pythonshare.socket.error):
            break

        if isinstance(obj, messages.Register_ns):
            try:
                _init_remote_namespace(obj.ns, conn, to_client, from_client)
                pythonshare._send(messages.Ns_rv(True), to_client)
                # from this point on, this connection is reserved for
                # sending remote namespace traffic. The connection will be
                # used by other threads, this thread stops here.
                return
            except Exception, e:
                pythonshare._send(messages.Ns_rv(False, exception2string(sys.exc_info())), to_client)

        elif isinstance(obj, messages.Drop_ns):
            try:
                if obj.ns in _g_local_namespaces:
                    _drop_local_namespace(obj.ns)
                elif obj.ns in _g_remote_namespaces:
                    _drop_remote_namespace(obj.ns)
                else:
                    raise ValueError('Unknown namespace "%s"' % (obj.ns,))