Exemple #1
0
    def __init__(self, *args, **kwargs):
        BaseChannel.__init__(self, *args, **kwargs)

        # Variables to hold the current state. We use only the message
        # as a reference, so we dont need a lock.
        # The package is used to make _recv() function more or less,
        # and to be able to determine if a state was set (because the
        # message may be set to None)
        self._current_package = None
        self._current_message = self.message_from_bytes(bytes())
Exemple #2
0
 def __init__(self, *args, **kwargs):
     BaseChannel.__init__(self, *args, **kwargs)
     
     # Variables to hold the current state. We use only the message
     # as a reference, so we dont need a lock.
     # The package is used to make _recv() function more or less,
     # and to be able to determine if a state was set (because the
     # message may be set to None)
     self._current_package = None
     self._current_message = self.message_from_bytes(bytes())
Exemple #3
0
    def __init__(self, req_channel, req, request_id):

        # For being a Future object
        self._result = None
        self._status = 0  # 0:waiting, 1:running, 2:canceled, 3:error, 4:success
        self._callbacks = []

        # For handling req/rep
        self._req_channel = req_channel
        self._req = req
        self._request_id = request_id
        self._rep = bytes()
        self._replier = 0

        # For resending
        self._first_send_time = time.time()
        self._next_send_time = self._first_send_time + 0.5
        self._auto_cancel_timeout = 10.0
Exemple #4
0
 def __init__(self, req_channel, req, request_id):
     
     # For being a Future object
     self._result = None
     self._status = 0 # 0:waiting, 1:running, 2:canceled, 3:error, 4:success
     self._callbacks = []
     
     # For handling req/rep
     self._req_channel = req_channel
     self._req = req
     self._request_id = request_id
     self._rep = bytes()
     self._replier = 0
     
     # For resending
     self._first_send_time = time.time()
     self._next_send_time = self._first_send_time + 0.5
     self._auto_cancel_timeout = 10.0
Exemple #5
0
    def _recv_n_bytes(self, socket_recv, n):
        """Receive exactly n bytes from the socket."""

        # First round
        data = socket_recv(n)
        if len(data) == 0:
            raise EOFError()

        # How many more do we need? For small n, we probably only need 1 round
        n -= len(data)
        if n == 0:
            return data  # We're lucky!

        # Else, we need more than one round
        parts = [data]
        while n:
            data = socket_recv(n)
            parts.append(data)
            n -= len(data)

        # Return combined data of multiple rounds
        return bytes().join(parts)
Exemple #6
0
 def _recv_n_bytes(self, socket_recv, n):
     """ Receive exactly n bytes from the socket.
     """
     
     # First round
     data = socket_recv(n)
     if len(data) == 0:
         raise EOFError()
     
     # How many more do we need? For small n, we probably only need 1 round
     n -= len(data)
     if n==0:
         return data  # We're lucky!
     
     # Else, we need more than one round
     parts = [data]
     while n:
         data = socket_recv(n)
         parts.append(data)
         n -= len(data)
     
     # Return combined data of multiple rounds
     return bytes().join(parts)
Exemple #7
0
    def recv(self, block=True):
        """recv(block=True)

        Receive a message from the channel. What was send as one
        message is also received as one message.

        If block is False, returns empty message if no data is available.
        If block is True, waits forever until data is available.
        If block is an int or float, waits that many seconds.
        If the channel is closed, returns empty message.

        """

        # Check queue status, maybe we need to block the sender
        self._check_queue_status()

        # Get package
        package = self._recv(block)

        # Return message content or None
        if package is not None:
            return self.message_from_bytes(package._data)
        else:
            return self.message_from_bytes(bytes())
Exemple #8
0
 def recv(self, block=True):
     """ recv(block=True)
     
     Receive a message from the channel. What was send as one
     message is also received as one message.
     
     If block is False, returns empty message if no data is available.
     If block is True, waits forever until data is available.
     If block is an int or float, waits that many seconds.
     If the channel is closed, returns empty message.
     
     """
     
     # Check queue status, maybe we need to block the sender
     self._check_queue_status()
     
     # Get package
     package = self._recv(block)
     
     # Return message content or None
     if package is not None:
         return self.message_from_bytes(package._data)
     else:
         return self.message_from_bytes(bytes())
Exemple #9
0
 def get_buffer(self):
     return bytes().join(self._buf)
Exemple #10
0
def recv_all(s, timeout=-1, end_at_crlf=True):
    """ recv_all(socket, timeout=-1, end_at_crlf=True)
    
    Receive text from the socket (untill socket receiving is shut down).
    Used during handshaking and in the clientserver module.
    
    If end_at_crlf, a message is also ended at a CRLF double-newline code,
    and a shutdown is not necessary. This takes a tiny bit longer.
    
    """
    
    # Init parts (start with one byte, such that len(parts) is always >= 2
    parts = [' '.encode('ascii'),]
    
    # Determine number of bytes to get per recv
    nbytesToGet = BUFFER_SIZE_IN
    if end_at_crlf:
        nbytesToGet = 1
    
    # Set end bytes
    end_bytes = '\r\n'.encode('ascii')
    
    # Set max time
    if timeout <= 0:
        timeout = 2**32
    maxtime = time.time() + timeout
    
    # Receive data
    while True:
        
        # Receive if we can
        if can_recv(s):
            
            # Get part
            try:
                part = s.recv(nbytesToGet)
                parts.append(part)
            except socket.error:
                return None # Socket closed down badly
            
            # Detect end by shutdown (EOF)
            if not part:
                break
            
            # Detect end by \r\n
            if end_at_crlf and (parts[-2] + parts[-1]).endswith(end_bytes):
                break
        
        else:
            # Sleep
            time.sleep(0.01)
            
            # Check time
            if time.time() > maxtime:
                bb  = bytes().join(parts[1:])
                return bb.decode('utf-8', 'ignore')
    
    # Combine parts (discared first (dummy) part)
    bb = bytes().join(parts[1:])
    
    # Try returning as Unicode
    try:
        return bb.decode('utf-8','ignore')
    except UnicodeError:
        return '<UnicodeError>'
Exemple #11
0
    
    def __str__(self):
        """ Representation of the package. Mainly for debugging. """
        return 'At slot %i: %s' % (self._slot, repr(self._data))
    
    
    @classmethod
    def from_header(cls, header):
        """ from_header(header)
        
        Create a package (without data) from the header of a message.
        Returns (package, data_length). If the header is invalid (checked
        using the four control bytes) this method returns (None, None).
        
        """
        # Unpack
        tmp = struct.unpack(HEADER_FORMAT, header)
        CTRL, slot, source_id, source_seq, dest_id, dest_seq, L = tmp
        # Create package
        p = Package(None, slot, source_id, source_seq, dest_id, dest_seq, 0)
        # Return
        if CTRL == CONTROL_BYTES:
            return p, L
        else:
            return None, None


# Constant Package instances (source_seq represents the signal)
PACKAGE_HEARTBEAT   = Package(bytes(), SLOT_DUMMY, 0, 0, 0, 0, 0)
PACKAGE_CLOSE       = Package(bytes(), SLOT_DUMMY, 0, 1, 0, 0, 0)
Exemple #12
0
 def get_buffer(self):
     return bytes().join(self._buf)
Exemple #13
0
def recv_all(s, timeout=-1, end_at_crlf=True):
    """recv_all(socket, timeout=-1, end_at_crlf=True)

    Receive text from the socket (untill socket receiving is shut down).
    Used during handshaking and in the clientserver module.

    If end_at_crlf, a message is also ended at a CRLF double-newline code,
    and a shutdown is not necessary. This takes a tiny bit longer.

    """

    # Init parts (start with one byte, such that len(parts) is always >= 2
    parts = [
        " ".encode("ascii"),
    ]

    # Determine number of bytes to get per recv
    nbytesToGet = BUFFER_SIZE_IN
    if end_at_crlf:
        nbytesToGet = 1

    # Set end bytes
    end_bytes = "\r\n".encode("ascii")

    # Set max time
    if timeout <= 0:
        timeout = 2**32
    maxtime = time.time() + timeout

    # Receive data
    while True:

        # Receive if we can
        if can_recv(s):

            # Get part
            try:
                part = s.recv(nbytesToGet)
                parts.append(part)
            except socket.error:
                return None  # Socket closed down badly

            # Detect end by shutdown (EOF)
            if not part:
                break

            # Detect end by \r\n
            if end_at_crlf and (parts[-2] + parts[-1]).endswith(end_bytes):
                break

        else:
            # Sleep
            time.sleep(0.01)

            # Check time
            if time.time() > maxtime:
                bb = bytes().join(parts[1:])
                return bb.decode("utf-8", "ignore")

    # Combine parts (discared first (dummy) part)
    bb = bytes().join(parts[1:])

    # Try returning as Unicode
    try:
        return bb.decode("utf-8", "ignore")
    except UnicodeError:
        return "<UnicodeError>"
Exemple #14
0
        return header, self._data

    def __str__(self):
        """ Representation of the package. Mainly for debugging. """
        return "At slot %i: %s" % (self._slot, repr(self._data))

    @classmethod
    def from_header(cls, header):
        """from_header(header)

        Create a package (without data) from the header of a message.
        Returns (package, data_length). If the header is invalid (checked
        using the four control bytes) this method returns (None, None).

        """
        # Unpack
        tmp = struct.unpack(HEADER_FORMAT, header)
        CTRL, slot, source_id, source_seq, dest_id, dest_seq, L = tmp
        # Create package
        p = Package(None, slot, source_id, source_seq, dest_id, dest_seq, 0)
        # Return
        if CTRL == CONTROL_BYTES:
            return p, L
        else:
            return None, None


# Constant Package instances (source_seq represents the signal)
PACKAGE_HEARTBEAT = Package(bytes(), SLOT_DUMMY, 0, 0, 0, 0, 0)
PACKAGE_CLOSE = Package(bytes(), SLOT_DUMMY, 0, 1, 0, 0, 0)