예제 #1
0
    def _run_method(self):
        self._receive_buffer = ""
        self._accumulated_output = ""

        if self._logger:
            self._logger.info("socket pump starting")

        # Keep looping around until we're asked to stop the thread.
        while not self._stop_thread:
            can_read, _, _ = select.select([self._socket], [], [], 0)
            if can_read and self._socket in can_read:
                try:
                    new_bytes = seven.bitcast_to_string(
                        self._socket.recv(4096))
                    if self._logger and new_bytes and len(new_bytes) > 0:
                        self._logger.debug(
                            "pump received bytes: {}".format(new_bytes))
                except:
                    # Likely a closed socket.  Done with the pump thread.
                    if self._logger:
                        self._logger.debug(
                            "socket read failed, stopping pump read thread\n" +
                            traceback.format_exc(3))
                    break
                self._process_new_bytes(new_bytes)

        if self._logger:
            self._logger.info("socket pump exiting")
예제 #2
0
 def _run(self):
     # For testing purposes, we only need to worry about one client
     # connecting just one time.
     try:
         # accept() is stubborn and won't fail even when the socket is
         # shutdown, so we'll use a timeout
         self._socket.settimeout(2.0)
         client, client_addr = self._socket.accept()
         self._client = client
         # The connected client inherits its timeout from self._socket,
         # but we'll use a blocking socket for the client
         self._client.settimeout(None)
     except:
         return
     self._shouldSendAck = True
     self._receivedData = ""
     self._receivedDataOffset = 0
     data = None
     while True:
         try:
             data = seven.bitcast_to_string(self._client.recv(4096))
             if data is None or len(data) == 0:
                 break
             self._receive(data)
         except Exception as e:
             self._client.close()
             break
예제 #3
0
 def run(self):
     # For testing purposes, we only need to worry about one client
     # connecting just one time.
     try:
         self._socket.accept()
     except:
         traceback.print_exc()
         return
     self._shouldSendAck = True
     self._receivedData = ""
     self._receivedDataOffset = 0
     data = None
     try:
         while True:
             data = seven.bitcast_to_string(self._socket.recv())
             if data is None or len(data) == 0:
                 break
             self._receive(data)
     except self.TerminateConnectionException:
         pass
     except Exception as e:
         print("An exception happened when receiving the response from the gdb server. Closing the client...")
         traceback.print_exc()
     finally:
         self._socket.close_connection()
         self._socket.close_server()
예제 #4
0
    def _run_method(self):
        self._receive_buffer = ""
        self._accumulated_output = ""

        if self._logger:
            self._logger.info("socket pump starting")

        # Keep looping around until we're asked to stop the thread.
        while not self._stop_thread:
            can_read, _, _ = select.select([self._socket], [], [], 0)
            if can_read and self._socket in can_read:
                try:
                    new_bytes = seven.bitcast_to_string(self._socket.recv(4096))
                    if self._logger and new_bytes and len(new_bytes) > 0:
                        self._logger.debug(
                            "pump received bytes: {}".format(new_bytes))
                except:
                    # Likely a closed socket.  Done with the pump thread.
                    if self._logger:
                        self._logger.debug(
                            "socket read failed, stopping pump read thread\n" +
                            traceback.format_exc(3))
                    break
                self._process_new_bytes(new_bytes)

        if self._logger:
            self._logger.info("socket pump exiting")
예제 #5
0
 def _run(self):
     # For testing purposes, we only need to worry about one client
     # connecting just one time.
     try:
         # accept() is stubborn and won't fail even when the socket is
         # shutdown, so we'll use a timeout
         self._socket.settimeout(2.0)
         client, client_addr = self._socket.accept()
         self._client = client
         # The connected client inherits its timeout from self._socket,
         # but we'll use a blocking socket for the client
         self._client.settimeout(None)
     except:
         return
     self._shouldSendAck = True
     self._receivedData = ""
     self._receivedDataOffset = 0
     data = None
     while True:
         try:
             data = seven.bitcast_to_string(self._client.recv(4096))
             if data is None or len(data) == 0:
                 break
             self._receive(data)
         except Exception as e:
             self._client.close()
             break
예제 #6
0
 def readMemory(self, addr, length):
     if addr == 0xee1000:
         return "00" * 0x30 + "0020ee0000000000"
     elif addr == 0xee2000:
         return "01000000000000000030ee0000000000dead00000000000000000000000000000000000000000000"
     elif addr == 0xef0000:
         with open(self.testcase.getBuildArtifact("libmodule_load.so"),
                   "rb") as f:
             contents = f.read(-1)
         return hex_encode_bytes(seven.bitcast_to_string(contents))
     return ("baadf00d00" * 1000)[0:length * 2]
예제 #7
0
 def _read(self, timeout_seconds, q):
     now = time.monotonic()
     deadline = now + timeout_seconds
     while q.empty() and now <= deadline:
         can_read, _, _ = select.select([self._socket], [], [], deadline-now)
         now = time.monotonic()
         if can_read and self._socket in can_read:
             try:
                 new_bytes = seven.bitcast_to_string(self._socket.recv(4096))
                 if self._logger and new_bytes and len(new_bytes) > 0:
                     self._logger.debug(
                         "pump received bytes: {}".format(new_bytes))
             except:
                 # Likely a closed socket.  Done with the pump thread.
                 if self._logger:
                     self._logger.debug(
                         "socket read failed, stopping pump read thread\n" +
                         traceback.format_exc(3))
                     break
             self._process_new_bytes(new_bytes)
     if q.empty():
         raise queue.Empty()
     return q.get(True)
예제 #8
0
def expect_lldb_gdbserver_replay(
        asserter,
        server,
        test_sequence,
        timeout_seconds,
        logger=None):
    """Replay socket communication with lldb-gdbserver and verify responses.

    Args:
        asserter: the object providing assertEqual(first, second, msg=None), e.g. TestCase instance.

        test_sequence: a GdbRemoteTestSequence instance that describes
            the messages sent to the gdb remote and the responses
            expected from it.

        timeout_seconds: any response taking more than this number of
           seconds will cause an exception to be raised.

        logger: a Python logger instance.

    Returns:
        The context dictionary from running the given gdbremote
        protocol sequence.  This will contain any of the capture
        elements specified to any GdbRemoteEntry instances in
        test_sequence.

        The context will also contain an entry, context["O_content"]
        which contains the text from the inferior received via $O
        packets.  $O packets should not attempt to be matched
        directly since they are not entirely deterministic as to
        how many arrive and how much text is in each one.

        context["O_count"] will contain an integer of the number of
        O packets received.
    """

    # Ensure we have some work to do.
    if len(test_sequence.entries) < 1:
        return {}

    context = {"O_count": 0, "O_content": ""}

    # Grab the first sequence entry.
    sequence_entry = test_sequence.entries.pop(0)

    # While we have an active sequence entry, send messages
    # destined for the stub and collect/match/process responses
    # expected from the stub.
    while sequence_entry:
        if sequence_entry.is_send_to_remote():
            # This is an entry to send to the remote debug monitor.
            send_packet = sequence_entry.get_send_packet()
            if logger:
                if len(send_packet) == 1 and send_packet[0] == chr(3):
                    packet_desc = "^C"
                else:
                    packet_desc = send_packet
                logger.info(
                    "sending packet to remote: {}".format(packet_desc))
            server.send_raw(send_packet.encode())
        else:
            # This is an entry expecting to receive content from the remote
            # debug monitor.

            # We'll pull from (and wait on) the queue appropriate for the type of matcher.
            # We keep separate queues for process output (coming from non-deterministic
            # $O packet division) and for all other packets.
            try:
                if sequence_entry.is_output_matcher():
                    # Grab next entry from the output queue.
                    content = server.get_raw_output_packet()
                else:
                    content = server.get_raw_normal_packet()
                content = seven.bitcast_to_string(content)
            except socket.timeout:
                asserter.fail(
                        "timed out while waiting for '{}':\n{}".format(sequence_entry, server))

            # Give the sequence entry the opportunity to match the content.
            # Output matchers might match or pass after more output accumulates.
            # Other packet types generally must match.
            asserter.assertIsNotNone(content)
            context = sequence_entry.assert_match(
                asserter, content, context=context)

        # Move on to next sequence entry as needed.  Some sequence entries support executing multiple
        # times in different states (for looping over query/response
        # packets).
        if sequence_entry.is_consumed():
            if len(test_sequence.entries) > 0:
                sequence_entry = test_sequence.entries.pop(0)
            else:
                sequence_entry = None

    # Fill in the O_content entries.
    context["O_count"] = 1
    context["O_content"] = server.consume_accumulated_output()

    return context