def __send_message(self, message):
        """Send a query or getmore message and handles the response.

        If message is ``None`` this is an exhaust cursor, which reads
        the next result batch off the exhaust socket instead of
        sending getMore messages to the server.
        """
        client = self.__collection.database.connection

        if message:
            kwargs = {"_must_use_master": self.__must_use_master}
            kwargs["read_preference"] = self.__read_preference
            kwargs["tag_sets"] = self.__tag_sets
            kwargs["secondary_acceptable_latency_ms"] = (
                self.__secondary_acceptable_latency_ms)
            kwargs['exhaust'] = self.__exhaust
            if self.__connection_id is not None:
                kwargs["_connection_to_use"] = self.__connection_id
            kwargs.update(self.__kwargs)

            try:
                res = client._send_message_with_response(message, **kwargs)
                self.__connection_id, (response, sock, pool) = res
                if self.__exhaust:
                    self.__exhaust_mgr = _SocketManager(sock, pool)
            except AutoReconnect:
                # Don't try to send kill cursors on another socket
                # or to another server. It can cause a _pinValue
                # assertion on some server releases if we get here
                # due to a socket timeout.
                self.__killed = True
                raise
        else: # exhaust cursor - no getMore message
            response = client._exhaust_next(self.__exhaust_mgr.sock)

        try:
            response = helpers._unpack_response(response, self.__id,
                                                self.__as_class,
                                                self.__tz_aware,
                                                self.__uuid_subtype,
                                                self.__compile_re)
        except CursorNotFound:
            self.__killed = True
            # If this is a tailable cursor the error is likely
            # due to capped collection roll over. Setting
            # self.__killed to True ensures Cursor.alive will be
            # False. No need to re-raise.
            if self.__query_flags & _QUERY_OPTIONS["tailable_cursor"]:
                return
            raise
        except AutoReconnect:
            # Don't send kill cursors to another server after a "not master"
            # error. It's completely pointless.
            self.__killed = True
            client.disconnect()
            raise
        self.__id = response["cursor_id"]

        # starting from doesn't get set on getmore's for tailable cursors
        if not (self.__query_flags & _QUERY_OPTIONS["tailable_cursor"]):
            assert response["starting_from"] == self.__retrieved, (
                "Result batch started from %s, expected %s" % (
                    response['starting_from'], self.__retrieved))

        self.__retrieved += response["number_returned"]
        self.__data = deque(response["data"])

        if self.__limit and self.__id and self.__limit <= self.__retrieved:
            self.__die()

        # Don't wait for garbage collection to call __del__, return the
        # socket to the pool now.
        if self.__exhaust and self.__id == 0:
            self.__exhaust_mgr.close()
dataset/ETHPy150Open blynch/CloudMemeBackend/pymongo/cursor.py/Cursor.__send_message/original