18fa2394bSMichał Górnyimport lldb 28fa2394bSMichał Górnyfrom lldbsuite.test.lldbtest import * 38fa2394bSMichał Górnyfrom lldbsuite.test.decorators import * 433c0f93fSPavel Labathfrom lldbsuite.test.gdbclientutils import * 533c0f93fSPavel Labathfrom lldbsuite.test.lldbgdbclient import GDBRemoteTestBase 68fa2394bSMichał Górny 78fa2394bSMichał Górny 8*eacefba9SDmitry Vasilyev@skipIf(hostoslist=["windows"]) 98fa2394bSMichał Górnyclass TestPty(GDBRemoteTestBase): 108fa2394bSMichał Górny server_socket_class = PtyServerSocket 118fa2394bSMichał Górny 124a7b4beaSMichał Górny def get_term_attrs(self): 134a7b4beaSMichał Górny import termios 142238dcc3SJonas Devlieghere 15f3b7cc8bSPavel Labath return termios.tcgetattr(self._secondary_socket) 164a7b4beaSMichał Górny 174a7b4beaSMichał Górny def setUp(self): 184a7b4beaSMichał Górny super().setUp() 19f3b7cc8bSPavel Labath # Duplicate the pty descriptors so we can inspect the pty state after 20f3b7cc8bSPavel Labath # they are closed 21f3b7cc8bSPavel Labath self._primary_socket = os.dup(self.server._socket._primary.name) 22f3b7cc8bSPavel Labath self._secondary_socket = os.dup(self.server._socket._secondary.name) 234a7b4beaSMichał Górny self.orig_attr = self.get_term_attrs() 244a7b4beaSMichał Górny 254a7b4beaSMichał Górny def assert_raw_mode(self, current_attr): 264a7b4beaSMichał Górny import termios 272238dcc3SJonas Devlieghere 282238dcc3SJonas Devlieghere self.assertEqual( 292238dcc3SJonas Devlieghere current_attr[0] 302238dcc3SJonas Devlieghere & ( 312238dcc3SJonas Devlieghere termios.BRKINT 322238dcc3SJonas Devlieghere | termios.PARMRK 332238dcc3SJonas Devlieghere | termios.ISTRIP 342238dcc3SJonas Devlieghere | termios.INLCR 352238dcc3SJonas Devlieghere | termios.IGNCR 362238dcc3SJonas Devlieghere | termios.ICRNL 372238dcc3SJonas Devlieghere | termios.IXON 382238dcc3SJonas Devlieghere ), 392238dcc3SJonas Devlieghere 0, 402238dcc3SJonas Devlieghere ) 414a7b4beaSMichał Górny self.assertEqual(current_attr[1] & termios.OPOST, 0) 424a7b4beaSMichał Górny self.assertEqual(current_attr[2] & termios.CSIZE, termios.CS8) 432238dcc3SJonas Devlieghere self.assertEqual( 442238dcc3SJonas Devlieghere current_attr[3] 452238dcc3SJonas Devlieghere & (termios.ICANON | termios.ECHO | termios.ISIG | termios.IEXTEN), 462238dcc3SJonas Devlieghere 0, 472238dcc3SJonas Devlieghere ) 484a7b4beaSMichał Górny self.assertEqual(current_attr[6][termios.VMIN], 1) 494a7b4beaSMichał Górny self.assertEqual(current_attr[6][termios.VTIME], 0) 504a7b4beaSMichał Górny 514a7b4beaSMichał Górny def get_parity_flags(self, attr): 524a7b4beaSMichał Górny import termios 532238dcc3SJonas Devlieghere 544a7b4beaSMichał Górny return attr[2] & (termios.PARENB | termios.PARODD) 554a7b4beaSMichał Górny 564a7b4beaSMichał Górny def get_stop_bit_flags(self, attr): 574a7b4beaSMichał Górny import termios 582238dcc3SJonas Devlieghere 594a7b4beaSMichał Górny return attr[2] & termios.CSTOPB 604a7b4beaSMichał Górny 618fa2394bSMichał Górny def test_process_connect_sync(self): 628fa2394bSMichał Górny """Test the process connect command in synchronous mode""" 638fa2394bSMichał Górny try: 648fa2394bSMichał Górny self.dbg.SetAsync(False) 652238dcc3SJonas Devlieghere self.expect( 662238dcc3SJonas Devlieghere "platform select remote-gdb-server", 672238dcc3SJonas Devlieghere substrs=["Platform: remote-gdb-server", "Connected: no"], 682238dcc3SJonas Devlieghere ) 692238dcc3SJonas Devlieghere self.expect( 702238dcc3SJonas Devlieghere "process connect " + self.server.get_connect_url(), 712238dcc3SJonas Devlieghere substrs=["Process", "stopped"], 722238dcc3SJonas Devlieghere ) 734a7b4beaSMichał Górny 744a7b4beaSMichał Górny current_attr = self.get_term_attrs() 754a7b4beaSMichał Górny # serial:// should set raw mode 764a7b4beaSMichał Górny self.assert_raw_mode(current_attr) 774a7b4beaSMichał Górny # other parameters should be unmodified 784a7b4beaSMichał Górny self.assertEqual(current_attr[4:6], self.orig_attr[4:6]) 792238dcc3SJonas Devlieghere self.assertEqual( 802238dcc3SJonas Devlieghere self.get_parity_flags(current_attr), 812238dcc3SJonas Devlieghere self.get_parity_flags(self.orig_attr), 822238dcc3SJonas Devlieghere ) 832238dcc3SJonas Devlieghere self.assertEqual( 842238dcc3SJonas Devlieghere self.get_stop_bit_flags(current_attr), 852238dcc3SJonas Devlieghere self.get_stop_bit_flags(self.orig_attr), 862238dcc3SJonas Devlieghere ) 878fa2394bSMichał Górny finally: 8845f97950SMichał Górny self.dbg.GetSelectedTarget().GetProcess().Kill() 894a7b4beaSMichał Górny # original mode should be restored on exit 904a7b4beaSMichał Górny self.assertEqual(self.get_term_attrs(), self.orig_attr) 918fa2394bSMichał Górny 928fa2394bSMichał Górny def test_process_connect_async(self): 938fa2394bSMichał Górny """Test the process connect command in asynchronous mode""" 948fa2394bSMichał Górny try: 958fa2394bSMichał Górny self.dbg.SetAsync(True) 962238dcc3SJonas Devlieghere self.expect( 972238dcc3SJonas Devlieghere "platform select remote-gdb-server", 982238dcc3SJonas Devlieghere substrs=["Platform: remote-gdb-server", "Connected: no"], 992238dcc3SJonas Devlieghere ) 1002238dcc3SJonas Devlieghere self.expect( 1012238dcc3SJonas Devlieghere "process connect " + self.server.get_connect_url(), 1028fa2394bSMichał Górny matching=False, 1032238dcc3SJonas Devlieghere substrs=["Process", "stopped"], 1042238dcc3SJonas Devlieghere ) 1052238dcc3SJonas Devlieghere lldbutil.expect_state_changes( 1062238dcc3SJonas Devlieghere self, self.dbg.GetListener(), self.process(), [lldb.eStateStopped] 1072238dcc3SJonas Devlieghere ) 1084a7b4beaSMichał Górny 1094a7b4beaSMichał Górny current_attr = self.get_term_attrs() 1104a7b4beaSMichał Górny # serial:// should set raw mode 1114a7b4beaSMichał Górny self.assert_raw_mode(current_attr) 1124a7b4beaSMichał Górny # other parameters should be unmodified 1134a7b4beaSMichał Górny self.assertEqual(current_attr[4:6], self.orig_attr[4:6]) 1142238dcc3SJonas Devlieghere self.assertEqual( 1152238dcc3SJonas Devlieghere self.get_parity_flags(current_attr), 1162238dcc3SJonas Devlieghere self.get_parity_flags(self.orig_attr), 1172238dcc3SJonas Devlieghere ) 1182238dcc3SJonas Devlieghere self.assertEqual( 1192238dcc3SJonas Devlieghere self.get_stop_bit_flags(current_attr), 1202238dcc3SJonas Devlieghere self.get_stop_bit_flags(self.orig_attr), 1212238dcc3SJonas Devlieghere ) 1228fa2394bSMichał Górny finally: 12345f97950SMichał Górny self.dbg.GetSelectedTarget().GetProcess().Kill() 1242238dcc3SJonas Devlieghere lldbutil.expect_state_changes( 1252238dcc3SJonas Devlieghere self, self.dbg.GetListener(), self.process(), [lldb.eStateExited] 1262238dcc3SJonas Devlieghere ) 1274a7b4beaSMichał Górny # original mode should be restored on exit 1284a7b4beaSMichał Górny self.assertEqual(self.get_term_attrs(), self.orig_attr) 1294a7b4beaSMichał Górny 1304a7b4beaSMichał Górny def test_connect_via_file(self): 1314a7b4beaSMichał Górny """Test connecting via the legacy file:// URL""" 1324a7b4beaSMichał Górny import termios 1332238dcc3SJonas Devlieghere 1344a7b4beaSMichał Górny try: 1352238dcc3SJonas Devlieghere self.expect( 1362238dcc3SJonas Devlieghere "platform select remote-gdb-server", 1372238dcc3SJonas Devlieghere substrs=["Platform: remote-gdb-server", "Connected: no"], 1382238dcc3SJonas Devlieghere ) 1392238dcc3SJonas Devlieghere self.expect( 1402238dcc3SJonas Devlieghere "process connect file://" + self.server.get_connect_address(), 1412238dcc3SJonas Devlieghere substrs=["Process", "stopped"], 1422238dcc3SJonas Devlieghere ) 1434a7b4beaSMichał Górny 1444a7b4beaSMichał Górny # file:// sets baud rate and some raw-related flags 1454a7b4beaSMichał Górny current_attr = self.get_term_attrs() 1462238dcc3SJonas Devlieghere self.assertEqual( 1472238dcc3SJonas Devlieghere current_attr[3] 1482238dcc3SJonas Devlieghere & (termios.ICANON | termios.ECHO | termios.ECHOE | termios.ISIG), 1492238dcc3SJonas Devlieghere 0, 1502238dcc3SJonas Devlieghere ) 1514a7b4beaSMichał Górny self.assertEqual(current_attr[4], termios.B115200) 1524a7b4beaSMichał Górny self.assertEqual(current_attr[5], termios.B115200) 1534a7b4beaSMichał Górny self.assertEqual(current_attr[6][termios.VMIN], 1) 1544a7b4beaSMichał Górny self.assertEqual(current_attr[6][termios.VTIME], 0) 1554a7b4beaSMichał Górny finally: 1564a7b4beaSMichał Górny self.dbg.GetSelectedTarget().GetProcess().Kill() 1574a7b4beaSMichał Górny 1584a7b4beaSMichał Górny def test_process_connect_params(self): 1594a7b4beaSMichał Górny """Test serial:// URL with parameters""" 1604a7b4beaSMichał Górny import termios 1612238dcc3SJonas Devlieghere 1624a7b4beaSMichał Górny try: 1632238dcc3SJonas Devlieghere self.expect( 1642238dcc3SJonas Devlieghere "platform select remote-gdb-server", 1652238dcc3SJonas Devlieghere substrs=["Platform: remote-gdb-server", "Connected: no"], 1662238dcc3SJonas Devlieghere ) 1672238dcc3SJonas Devlieghere self.expect( 1682238dcc3SJonas Devlieghere "process connect " 1692238dcc3SJonas Devlieghere + self.server.get_connect_url() 1702238dcc3SJonas Devlieghere + "?baud=115200&stop-bits=2", 1712238dcc3SJonas Devlieghere substrs=["Process", "stopped"], 1722238dcc3SJonas Devlieghere ) 1734a7b4beaSMichał Górny 1744a7b4beaSMichał Górny current_attr = self.get_term_attrs() 1754a7b4beaSMichał Górny self.assert_raw_mode(current_attr) 1764a7b4beaSMichał Górny self.assertEqual(current_attr[4:6], 2 * [termios.B115200]) 1772238dcc3SJonas Devlieghere self.assertEqual( 1782238dcc3SJonas Devlieghere self.get_parity_flags(current_attr), 1792238dcc3SJonas Devlieghere self.get_parity_flags(self.orig_attr), 1802238dcc3SJonas Devlieghere ) 1812238dcc3SJonas Devlieghere self.assertEqual(self.get_stop_bit_flags(current_attr), termios.CSTOPB) 1824a7b4beaSMichał Górny finally: 1834a7b4beaSMichał Górny self.dbg.GetSelectedTarget().GetProcess().Kill() 1844a7b4beaSMichał Górny # original mode should be restored on exit 1854a7b4beaSMichał Górny self.assertEqual(self.get_term_attrs(), self.orig_attr) 186