diff --git a/Lib/telnetlib.py b/Lib/telnetlib.py --- a/Lib/telnetlib.py +++ b/Lib/telnetlib.py @@ -206,7 +206,6 @@ self.sb = 0 # flag for SB and SE sequence. self.sbdataq = b'' self.option_callback = None - self._has_poll = hasattr(select, 'poll') if host is not None: self.open(host, port, timeout) @@ -289,16 +288,6 @@ is closed and no cooked data is available. """ - if self._has_poll: - return self._read_until_with_poll(match, timeout) - else: - return self._read_until_with_select(match, timeout) - - def _read_until_with_poll(self, match, timeout): - """Read until a given string is encountered or until timeout. - - This method uses select.poll() to implement the timeout. - """ n = len(match) call_timeout = timeout if timeout is not None: @@ -307,31 +296,29 @@ self.process_rawq() i = self.cookedq.find(match) if i < 0: - poller = select.poll() - poll_in_or_priority_flags = select.POLLIN | select.POLLPRI - poller.register(self, poll_in_or_priority_flags) - while i < 0 and not self.eof: - try: - ready = poller.poll(call_timeout) - except OSError as e: - if e.errno == errno.EINTR: - if timeout is not None: - elapsed = time() - time_start - call_timeout = timeout-elapsed - continue - raise - for fd, mode in ready: - if mode & poll_in_or_priority_flags: - i = max(0, len(self.cookedq)-n) - self.fill_rawq() - self.process_rawq() - i = self.cookedq.find(match, i) - if timeout is not None: - elapsed = time() - time_start - if elapsed >= timeout: - break - call_timeout = timeout-elapsed - poller.unregister(self) + with select.Selector() as selector: + selector.register(self, select.SELECT_IN) + while i < 0 and not self.eof: + try: + ready = selector.select(call_timeout) + except OSError as e: + if e.errno == errno.EINTR: + if timeout is not None: + elapsed = time() - time_start + call_timeout = timeout-elapsed + continue + raise + for fd, mode in ready: + if mode & select.SELECT_IN: + i = max(0, len(self.cookedq)-n) + self.fill_rawq() + self.process_rawq() + i = self.cookedq.find(match, i) + if timeout is not None: + elapsed = time() - time_start + if elapsed >= timeout: + break + call_timeout = timeout-elapsed if i >= 0: i = i + n buf = self.cookedq[:i] @@ -339,42 +326,6 @@ return buf return self.read_very_lazy() - def _read_until_with_select(self, match, timeout=None): - """Read until a given string is encountered or until timeout. - - The timeout is implemented using select.select(). - """ - n = len(match) - self.process_rawq() - i = self.cookedq.find(match) - if i >= 0: - i = i+n - buf = self.cookedq[:i] - self.cookedq = self.cookedq[i:] - return buf - s_reply = ([self], [], []) - s_args = s_reply - if timeout is not None: - s_args = s_args + (timeout,) - from time import time - time_start = time() - while not self.eof and select.select(*s_args) == s_reply: - i = max(0, len(self.cookedq)-n) - self.fill_rawq() - self.process_rawq() - i = self.cookedq.find(match, i) - if i >= 0: - i = i+n - buf = self.cookedq[:i] - self.cookedq = self.cookedq[i:] - return buf - if timeout is not None: - elapsed = time() - time_start - if elapsed >= timeout: - break - s_args = s_reply + (timeout-elapsed,) - return self.read_very_lazy() - def read_all(self): """Read all data until EOF; block until connection closed.""" self.process_rawq() @@ -646,23 +597,13 @@ results are undeterministic, and may depend on the I/O timing. """ - if self._has_poll: - return self._expect_with_poll(list, timeout) - else: - return self._expect_with_select(list, timeout) - - def _expect_with_poll(self, expect_list, timeout=None): - """Read until one from a list of a regular expressions matches. - - This method uses select.poll() to implement the timeout. - """ re = None - expect_list = expect_list[:] - indices = range(len(expect_list)) + list = list[:] + indices = range(len(list)) for i in indices: - if not hasattr(expect_list[i], "search"): + if not hasattr(list[i], "search"): if not re: import re - expect_list[i] = re.compile(expect_list[i]) + list[i] = re.compile(list[i]) call_timeout = timeout if timeout is not None: from time import time @@ -670,43 +611,41 @@ self.process_rawq() m = None for i in indices: - m = expect_list[i].search(self.cookedq) + m = list[i].search(self.cookedq) if m: e = m.end() text = self.cookedq[:e] self.cookedq = self.cookedq[e:] break if not m: - poller = select.poll() - poll_in_or_priority_flags = select.POLLIN | select.POLLPRI - poller.register(self, poll_in_or_priority_flags) - while not m and not self.eof: - try: - ready = poller.poll(call_timeout) - except OSError as e: - if e.errno == errno.EINTR: - if timeout is not None: - elapsed = time() - time_start - call_timeout = timeout-elapsed - continue - raise - for fd, mode in ready: - if mode & poll_in_or_priority_flags: - self.fill_rawq() - self.process_rawq() - for i in indices: - m = expect_list[i].search(self.cookedq) - if m: - e = m.end() - text = self.cookedq[:e] - self.cookedq = self.cookedq[e:] - break - if timeout is not None: - elapsed = time() - time_start - if elapsed >= timeout: - break - call_timeout = timeout-elapsed - poller.unregister(self) + with select.Selector() as selector: + selector.register(self, select.SELECT_IN) + while not m and not self.eof: + try: + ready = selector.select(call_timeout) + except OSError as e: + if e.errno == errno.EINTR: + if timeout is not None: + elapsed = time() - time_start + call_timeout = timeout-elapsed + continue + raise + for fd, mode in ready: + if mode & select.SELECT_IN: + self.fill_rawq() + self.process_rawq() + for i in indices: + m = list[i].search(self.cookedq) + if m: + e = m.end() + text = self.cookedq[:e] + self.cookedq = self.cookedq[e:] + break + if timeout is not None: + elapsed = time() - time_start + if elapsed >= timeout: + break + call_timeout = timeout-elapsed if m: return (i, m, text) text = self.read_very_lazy() @@ -714,46 +653,6 @@ raise EOFError return (-1, None, text) - def _expect_with_select(self, list, timeout=None): - """Read until one from a list of a regular expressions matches. - - The timeout is implemented using select.select(). - """ - re = None - list = list[:] - indices = range(len(list)) - for i in indices: - if not hasattr(list[i], "search"): - if not re: import re - list[i] = re.compile(list[i]) - if timeout is not None: - from time import time - time_start = time() - while 1: - self.process_rawq() - for i in indices: - m = list[i].search(self.cookedq) - if m: - e = m.end() - text = self.cookedq[:e] - self.cookedq = self.cookedq[e:] - return (i, m, text) - if self.eof: - break - if timeout is not None: - elapsed = time() - time_start - if elapsed >= timeout: - break - s_args = ([self.fileno()], [], [], timeout-elapsed) - r, w, x = select.select(*s_args) - if not r: - break - self.fill_rawq() - text = self.read_very_lazy() - if not text and self.eof: - raise EOFError - return (-1, None, text) - def test(): """Test program for telnetlib.