Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1117)

Side by Side Diff: third_party/pexpect/pexpect/pty_spawn.py

Issue 1398903002: Add third_party/pexpect (Closed) Base URL: https://chromium.googlesource.com/crashpad/crashpad@end-to-end-test
Patch Set: Created 5 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « third_party/pexpect/pexpect/popen_spawn.py ('k') | third_party/pexpect/pexpect/pxssh.py » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 import os
2 import sys
3 import time
4 import select
5 import pty
6 import tty
7 import errno
8 import signal
9 from contextlib import contextmanager
10
11 import ptyprocess
12 from ptyprocess.ptyprocess import use_native_pty_fork
13
14 from .exceptions import ExceptionPexpect, EOF, TIMEOUT
15 from .spawnbase import SpawnBase
16 from .utils import which, split_command_line
17
18 @contextmanager
19 def _wrap_ptyprocess_err():
20 """Turn ptyprocess errors into our own ExceptionPexpect errors"""
21 try:
22 yield
23 except ptyprocess.PtyProcessError as e:
24 raise ExceptionPexpect(*e.args)
25
26 PY3 = (sys.version_info[0] >= 3)
27
28 class spawn(SpawnBase):
29 '''This is the main class interface for Pexpect. Use this class to start
30 and control child applications. '''
31
32 # This is purely informational now - changing it has no effect
33 use_native_pty_fork = use_native_pty_fork
34
35 def __init__(self, command, args=[], timeout=30, maxread=2000,
36 searchwindowsize=None, logfile=None, cwd=None, env=None,
37 ignore_sighup=False, echo=True, preexec_fn=None,
38 encoding=None, codec_errors='strict', dimensions=None):
39 '''This is the constructor. The command parameter may be a string that
40 includes a command and any arguments to the command. For example::
41
42 child = pexpect.spawn('/usr/bin/ftp')
43 child = pexpect.spawn('/usr/bin/ssh user@example.com')
44 child = pexpect.spawn('ls -latr /tmp')
45
46 You may also construct it with a list of arguments like so::
47
48 child = pexpect.spawn('/usr/bin/ftp', [])
49 child = pexpect.spawn('/usr/bin/ssh', ['user@example.com'])
50 child = pexpect.spawn('ls', ['-latr', '/tmp'])
51
52 After this the child application will be created and will be ready to
53 talk to. For normal use, see expect() and send() and sendline().
54
55 Remember that Pexpect does NOT interpret shell meta characters such as
56 redirect, pipe, or wild cards (``>``, ``|``, or ``*``). This is a
57 common mistake. If you want to run a command and pipe it through
58 another command then you must also start a shell. For example::
59
60 child = pexpect.spawn('/bin/bash -c "ls -l | grep LOG > logs.txt"')
61 child.expect(pexpect.EOF)
62
63 The second form of spawn (where you pass a list of arguments) is useful
64 in situations where you wish to spawn a command and pass it its own
65 argument list. This can make syntax more clear. For example, the
66 following is equivalent to the previous example::
67
68 shell_cmd = 'ls -l | grep LOG > logs.txt'
69 child = pexpect.spawn('/bin/bash', ['-c', shell_cmd])
70 child.expect(pexpect.EOF)
71
72 The maxread attribute sets the read buffer size. This is maximum number
73 of bytes that Pexpect will try to read from a TTY at one time. Setting
74 the maxread size to 1 will turn off buffering. Setting the maxread
75 value higher may help performance in cases where large amounts of
76 output are read back from the child. This feature is useful in
77 conjunction with searchwindowsize.
78
79 When the keyword argument *searchwindowsize* is None (default), the
80 full buffer is searched at each iteration of receiving incoming data.
81 The default number of bytes scanned at each iteration is very large
82 and may be reduced to collaterally reduce search cost. After
83 :meth:`~.expect` returns, the full buffer attribute remains up to
84 size *maxread* irrespective of *searchwindowsize* value.
85
86 When the keyword argument ``timeout`` is specified as a number,
87 (default: *30*), then :class:`TIMEOUT` will be raised after the value
88 specified has elapsed, in seconds, for any of the :meth:`~.expect`
89 family of method calls. When None, TIMEOUT will not be raised, and
90 :meth:`~.expect` may block indefinitely until match.
91
92
93 The logfile member turns on or off logging. All input and output will
94 be copied to the given file object. Set logfile to None to stop
95 logging. This is the default. Set logfile to sys.stdout to echo
96 everything to standard output. The logfile is flushed after each write.
97
98 Example log input and output to a file::
99
100 child = pexpect.spawn('some_command')
101 fout = open('mylog.txt','wb')
102 child.logfile = fout
103
104 Example log to stdout::
105
106 # In Python 2:
107 child = pexpect.spawn('some_command')
108 child.logfile = sys.stdout
109
110 # In Python 3, spawnu should be used to give str to stdout:
111 child = pexpect.spawnu('some_command')
112 child.logfile = sys.stdout
113
114 The logfile_read and logfile_send members can be used to separately log
115 the input from the child and output sent to the child. Sometimes you
116 don't want to see everything you write to the child. You only want to
117 log what the child sends back. For example::
118
119 child = pexpect.spawn('some_command')
120 child.logfile_read = sys.stdout
121
122 You will need to pass an encoding to spawn in the above code if you are
123 using Python 3.
124
125 To separately log output sent to the child use logfile_send::
126
127 child.logfile_send = fout
128
129 If ``ignore_sighup`` is True, the child process will ignore SIGHUP
130 signals. The default is False from Pexpect 4.0, meaning that SIGHUP
131 will be handled normally by the child.
132
133 The delaybeforesend helps overcome a weird behavior that many users
134 were experiencing. The typical problem was that a user would expect() a
135 "Password:" prompt and then immediately call sendline() to send the
136 password. The user would then see that their password was echoed back
137 to them. Passwords don't normally echo. The problem is caused by the
138 fact that most applications print out the "Password" prompt and then
139 turn off stdin echo, but if you send your password before the
140 application turned off echo, then you get your password echoed.
141 Normally this wouldn't be a problem when interacting with a human at a
142 real keyboard. If you introduce a slight delay just before writing then
143 this seems to clear up the problem. This was such a common problem for
144 many users that I decided that the default pexpect behavior should be
145 to sleep just before writing to the child application. 1/20th of a
146 second (50 ms) seems to be enough to clear up the problem. You can set
147 delaybeforesend to 0 to return to the old behavior. Most Linux machines
148 don't like this to be below 0.03. I don't know why.
149
150 Note that spawn is clever about finding commands on your path.
151 It uses the same logic that "which" uses to find executables.
152
153 If you wish to get the exit status of the child you must call the
154 close() method. The exit or signal status of the child will be stored
155 in self.exitstatus or self.signalstatus. If the child exited normally
156 then exitstatus will store the exit return code and signalstatus will
157 be None. If the child was terminated abnormally with a signal then
158 signalstatus will store the signal value and exitstatus will be None.
159 If you need more detail you can also read the self.status member which
160 stores the status returned by os.waitpid. You can interpret this using
161 os.WIFEXITED/os.WEXITSTATUS or os.WIFSIGNALED/os.TERMSIG.
162
163 The echo attribute may be set to False to disable echoing of input.
164 As a pseudo-terminal, all input echoed by the "keyboard" (send()
165 or sendline()) will be repeated to output. For many cases, it is
166 not desirable to have echo enabled, and it may be later disabled
167 using setecho(False) followed by waitnoecho(). However, for some
168 platforms such as Solaris, this is not possible, and should be
169 disabled immediately on spawn.
170
171 If preexec_fn is given, it will be called in the child process before
172 launching the given command. This is useful to e.g. reset inherited
173 signal handlers.
174
175 The dimensions attribute specifies the size of the pseudo-terminal as
176 seen by the subprocess, and is specified as a two-entry tuple (rows,
177 columns). If this is unspecified, the defaults in ptyprocess will apply.
178 '''
179 super(spawn, self).__init__(timeout=timeout, maxread=maxread, searchwind owsize=searchwindowsize,
180 logfile=logfile, encoding=encoding, codec_er rors=codec_errors)
181 self.STDIN_FILENO = pty.STDIN_FILENO
182 self.STDOUT_FILENO = pty.STDOUT_FILENO
183 self.STDERR_FILENO = pty.STDERR_FILENO
184 self.cwd = cwd
185 self.env = env
186 self.echo = echo
187 self.ignore_sighup = ignore_sighup
188 self.__irix_hack = sys.platform.lower().startswith('irix')
189 if command is None:
190 self.command = None
191 self.args = None
192 self.name = '<pexpect factory incomplete>'
193 else:
194 self._spawn(command, args, preexec_fn, dimensions)
195
196 def __str__(self):
197 '''This returns a human-readable string that represents the state of
198 the object. '''
199
200 s = []
201 s.append(repr(self))
202 s.append('command: ' + str(self.command))
203 s.append('args: %r' % (self.args,))
204 s.append('searcher: %r' % (self.searcher,))
205 s.append('buffer (last 100 chars): %r' % (
206 self.buffer[-100:] if self.buffer else self.buffer,))
207 s.append('before (last 100 chars): %r' % (
208 self.before[-100:] if self.before else self.before,))
209 s.append('after: %r' % (self.after,))
210 s.append('match: %r' % (self.match,))
211 s.append('match_index: ' + str(self.match_index))
212 s.append('exitstatus: ' + str(self.exitstatus))
213 s.append('flag_eof: ' + str(self.flag_eof))
214 s.append('pid: ' + str(self.pid))
215 s.append('child_fd: ' + str(self.child_fd))
216 s.append('closed: ' + str(self.closed))
217 s.append('timeout: ' + str(self.timeout))
218 s.append('delimiter: ' + str(self.delimiter))
219 s.append('logfile: ' + str(self.logfile))
220 s.append('logfile_read: ' + str(self.logfile_read))
221 s.append('logfile_send: ' + str(self.logfile_send))
222 s.append('maxread: ' + str(self.maxread))
223 s.append('ignorecase: ' + str(self.ignorecase))
224 s.append('searchwindowsize: ' + str(self.searchwindowsize))
225 s.append('delaybeforesend: ' + str(self.delaybeforesend))
226 s.append('delayafterclose: ' + str(self.delayafterclose))
227 s.append('delayafterterminate: ' + str(self.delayafterterminate))
228 return '\n'.join(s)
229
230 def _spawn(self, command, args=[], preexec_fn=None, dimensions=None):
231 '''This starts the given command in a child process. This does all the
232 fork/exec type of stuff for a pty. This is called by __init__. If args
233 is empty then command will be parsed (split on spaces) and args will be
234 set to parsed arguments. '''
235
236 # The pid and child_fd of this object get set by this method.
237 # Note that it is difficult for this method to fail.
238 # You cannot detect if the child process cannot start.
239 # So the only way you can tell if the child process started
240 # or not is to try to read from the file descriptor. If you get
241 # EOF immediately then it means that the child is already dead.
242 # That may not necessarily be bad because you may have spawned a child
243 # that performs some task; creates no stdout output; and then dies.
244
245 # If command is an int type then it may represent a file descriptor.
246 if isinstance(command, type(0)):
247 raise ExceptionPexpect('Command is an int type. ' +
248 'If this is a file descriptor then maybe you want to ' +
249 'use fdpexpect.fdspawn which takes an existing ' +
250 'file descriptor instead of a command string.')
251
252 if not isinstance(args, type([])):
253 raise TypeError('The argument, args, must be a list.')
254
255 if args == []:
256 self.args = split_command_line(command)
257 self.command = self.args[0]
258 else:
259 # Make a shallow copy of the args list.
260 self.args = args[:]
261 self.args.insert(0, command)
262 self.command = command
263
264 command_with_path = which(self.command)
265 if command_with_path is None:
266 raise ExceptionPexpect('The command was not found or was not ' +
267 'executable: %s.' % self.command)
268 self.command = command_with_path
269 self.args[0] = self.command
270
271 self.name = '<' + ' '.join(self.args) + '>'
272
273 assert self.pid is None, 'The pid member must be None.'
274 assert self.command is not None, 'The command member must not be None.'
275
276 kwargs = {'echo': self.echo, 'preexec_fn': preexec_fn}
277 if self.ignore_sighup:
278 def preexec_wrapper():
279 "Set SIGHUP to be ignored, then call the real preexec_fn"
280 signal.signal(signal.SIGHUP, signal.SIG_IGN)
281 if preexec_fn is not None:
282 preexec_fn()
283 kwargs['preexec_fn'] = preexec_wrapper
284
285 if dimensions is not None:
286 kwargs['dimensions'] = dimensions
287
288 if self.encoding is not None:
289 # Encode command line using the specified encoding
290 self.args = [a if isinstance(a, bytes) else a.encode(self.encoding)
291 for a in self.args]
292
293 self.ptyproc = ptyprocess.PtyProcess.spawn(self.args, env=self.env,
294 cwd=self.cwd, **kwargs)
295
296 self.pid = self.ptyproc.pid
297 self.child_fd = self.ptyproc.fd
298
299
300 self.terminated = False
301 self.closed = False
302
303 def close(self, force=True):
304 '''This closes the connection with the child application. Note that
305 calling close() more than once is valid. This emulates standard Python
306 behavior with files. Set force to True if you want to make sure that
307 the child is terminated (SIGKILL is sent if the child ignores SIGHUP
308 and SIGINT). '''
309
310 self.flush()
311 self.ptyproc.close(force=force)
312 self.isalive() # Update exit status from ptyproc
313 self.child_fd = -1
314
315 def isatty(self):
316 '''This returns True if the file descriptor is open and connected to a
317 tty(-like) device, else False.
318
319 On SVR4-style platforms implementing streams, such as SunOS and HP-UX,
320 the child pty may not appear as a terminal device. This means
321 methods such as setecho(), setwinsize(), getwinsize() may raise an
322 IOError. '''
323
324 return os.isatty(self.child_fd)
325
326 def waitnoecho(self, timeout=-1):
327 '''This waits until the terminal ECHO flag is set False. This returns
328 True if the echo mode is off. This returns False if the ECHO flag was
329 not set False before the timeout. This can be used to detect when the
330 child is waiting for a password. Usually a child application will turn
331 off echo mode when it is waiting for the user to enter a password. For
332 example, instead of expecting the "password:" prompt you can wait for
333 the child to set ECHO off::
334
335 p = pexpect.spawn('ssh user@example.com')
336 p.waitnoecho()
337 p.sendline(mypassword)
338
339 If timeout==-1 then this method will use the value in self.timeout.
340 If timeout==None then this method to block until ECHO flag is False.
341 '''
342
343 if timeout == -1:
344 timeout = self.timeout
345 if timeout is not None:
346 end_time = time.time() + timeout
347 while True:
348 if not self.getecho():
349 return True
350 if timeout < 0 and timeout is not None:
351 return False
352 if timeout is not None:
353 timeout = end_time - time.time()
354 time.sleep(0.1)
355
356 def getecho(self):
357 '''This returns the terminal echo mode. This returns True if echo is
358 on or False if echo is off. Child applications that are expecting you
359 to enter a password often set ECHO False. See waitnoecho().
360
361 Not supported on platforms where ``isatty()`` returns False. '''
362 return self.ptyproc.getecho()
363
364 def setecho(self, state):
365 '''This sets the terminal echo mode on or off. Note that anything the
366 child sent before the echo will be lost, so you should be sure that
367 your input buffer is empty before you call setecho(). For example, the
368 following will work as expected::
369
370 p = pexpect.spawn('cat') # Echo is on by default.
371 p.sendline('1234') # We expect see this twice from the child...
372 p.expect(['1234']) # ... once from the tty echo...
373 p.expect(['1234']) # ... and again from cat itself.
374 p.setecho(False) # Turn off tty echo
375 p.sendline('abcd') # We will set this only once (echoed by cat).
376 p.sendline('wxyz') # We will set this only once (echoed by cat)
377 p.expect(['abcd'])
378 p.expect(['wxyz'])
379
380 The following WILL NOT WORK because the lines sent before the setecho
381 will be lost::
382
383 p = pexpect.spawn('cat')
384 p.sendline('1234')
385 p.setecho(False) # Turn off tty echo
386 p.sendline('abcd') # We will set this only once (echoed by cat).
387 p.sendline('wxyz') # We will set this only once (echoed by cat)
388 p.expect(['1234'])
389 p.expect(['1234'])
390 p.expect(['abcd'])
391 p.expect(['wxyz'])
392
393
394 Not supported on platforms where ``isatty()`` returns False.
395 '''
396 return self.ptyproc.setecho(state)
397
398 self.echo = state
399
400 def read_nonblocking(self, size=1, timeout=-1):
401 '''This reads at most size characters from the child application. It
402 includes a timeout. If the read does not complete within the timeout
403 period then a TIMEOUT exception is raised. If the end of file is read
404 then an EOF exception will be raised. If a logfile is specified, a
405 copy is written to that log.
406
407 If timeout is None then the read may block indefinitely.
408 If timeout is -1 then the self.timeout value is used. If timeout is 0
409 then the child is polled and if there is no data immediately ready
410 then this will raise a TIMEOUT exception.
411
412 The timeout refers only to the amount of time to read at least one
413 character. This is not affected by the 'size' parameter, so if you call
414 read_nonblocking(size=100, timeout=30) and only one character is
415 available right away then one character will be returned immediately.
416 It will not wait for 30 seconds for another 99 characters to come in.
417
418 This is a wrapper around os.read(). It uses select.select() to
419 implement the timeout. '''
420
421 if self.closed:
422 raise ValueError('I/O operation on closed file.')
423
424 if timeout == -1:
425 timeout = self.timeout
426
427 # Note that some systems such as Solaris do not give an EOF when
428 # the child dies. In fact, you can still try to read
429 # from the child_fd -- it will block forever or until TIMEOUT.
430 # For this case, I test isalive() before doing any reading.
431 # If isalive() is false, then I pretend that this is the same as EOF.
432 if not self.isalive():
433 # timeout of 0 means "poll"
434 r, w, e = self.__select([self.child_fd], [], [], 0)
435 if not r:
436 self.flag_eof = True
437 raise EOF('End Of File (EOF). Braindead platform.')
438 elif self.__irix_hack:
439 # Irix takes a long time before it realizes a child was terminated.
440 # FIXME So does this mean Irix systems are forced to always have
441 # FIXME a 2 second delay when calling read_nonblocking? That sucks.
442 r, w, e = self.__select([self.child_fd], [], [], 2)
443 if not r and not self.isalive():
444 self.flag_eof = True
445 raise EOF('End Of File (EOF). Slow platform.')
446
447 r, w, e = self.__select([self.child_fd], [], [], timeout)
448
449 if not r:
450 if not self.isalive():
451 # Some platforms, such as Irix, will claim that their
452 # processes are alive; timeout on the select; and
453 # then finally admit that they are not alive.
454 self.flag_eof = True
455 raise EOF('End of File (EOF). Very slow platform.')
456 else:
457 raise TIMEOUT('Timeout exceeded.')
458
459 if self.child_fd in r:
460 return super(spawn, self).read_nonblocking(size)
461
462 raise ExceptionPexpect('Reached an unexpected state.') # pragma: no cov er
463
464 def write(self, s):
465 '''This is similar to send() except that there is no return value.
466 '''
467
468 self.send(s)
469
470 def writelines(self, sequence):
471 '''This calls write() for each element in the sequence. The sequence
472 can be any iterable object producing strings, typically a list of
473 strings. This does not add line separators. There is no return value.
474 '''
475
476 for s in sequence:
477 self.write(s)
478
479 def send(self, s):
480 '''Sends string ``s`` to the child process, returning the number of
481 bytes written. If a logfile is specified, a copy is written to that
482 log.
483
484 The default terminal input mode is canonical processing unless set
485 otherwise by the child process. This allows backspace and other line
486 processing to be performed prior to transmitting to the receiving
487 program. As this is buffered, there is a limited size of such buffer.
488
489 On Linux systems, this is 4096 (defined by N_TTY_BUF_SIZE). All
490 other systems honor the POSIX.1 definition PC_MAX_CANON -- 1024
491 on OSX, 256 on OpenSolaris, and 1920 on FreeBSD.
492
493 This value may be discovered using fpathconf(3)::
494
495 >>> from os import fpathconf
496 >>> print(fpathconf(0, 'PC_MAX_CANON'))
497 256
498
499 On such a system, only 256 bytes may be received per line. Any
500 subsequent bytes received will be discarded. BEL (``'\a'``) is then
501 sent to output if IMAXBEL (termios.h) is set by the tty driver.
502 This is usually enabled by default. Linux does not honor this as
503 an option -- it behaves as though it is always set on.
504
505 Canonical input processing may be disabled altogether by executing
506 a shell, then stty(1), before executing the final program::
507
508 >>> bash = pexpect.spawn('/bin/bash', echo=False)
509 >>> bash.sendline('stty -icanon')
510 >>> bash.sendline('base64')
511 >>> bash.sendline('x' * 5000)
512 '''
513
514 time.sleep(self.delaybeforesend)
515
516 s = self._coerce_send_string(s)
517 self._log(s, 'send')
518
519 b = self._encoder.encode(s, final=False)
520 return os.write(self.child_fd, b)
521
522 def sendline(self, s=''):
523 '''Wraps send(), sending string ``s`` to child process, with
524 ``os.linesep`` automatically appended. Returns number of bytes
525 written. Only a limited number of bytes may be sent for each
526 line in the default terminal mode, see docstring of :meth:`send`.
527 '''
528
529 n = self.send(s)
530 n = n + self.send(self.linesep)
531 return n
532
533 def _log_control(self, s):
534 """Write control characters to the appropriate log files"""
535 if self.encoding is not None:
536 s = s.decode(self.encoding, 'replace')
537 self._log(s, 'send')
538
539 def sendcontrol(self, char):
540 '''Helper method that wraps send() with mnemonic access for sending cont rol
541 character to the child (such as Ctrl-C or Ctrl-D). For example, to send
542 Ctrl-G (ASCII 7, bell, '\a')::
543
544 child.sendcontrol('g')
545
546 See also, sendintr() and sendeof().
547 '''
548 n, byte = self.ptyproc.sendcontrol(char)
549 self._log_control(byte)
550 return n
551
552 def sendeof(self):
553 '''This sends an EOF to the child. This sends a character which causes
554 the pending parent output buffer to be sent to the waiting child
555 program without waiting for end-of-line. If it is the first character
556 of the line, the read() in the user program returns 0, which signifies
557 end-of-file. This means to work as expected a sendeof() has to be
558 called at the beginning of a line. This method does not send a newline.
559 It is the responsibility of the caller to ensure the eof is sent at the
560 beginning of a line. '''
561
562 n, byte = self.ptyproc.sendeof()
563 self._log_control(byte)
564
565 def sendintr(self):
566 '''This sends a SIGINT to the child. It does not require
567 the SIGINT to be the first character on a line. '''
568
569 n, byte = self.ptyproc.sendintr()
570 self._log_control(byte)
571
572 @property
573 def flag_eof(self):
574 return self.ptyproc.flag_eof
575
576 @flag_eof.setter
577 def flag_eof(self, value):
578 self.ptyproc.flag_eof = value
579
580 def eof(self):
581 '''This returns True if the EOF exception was ever raised.
582 '''
583 return self.flag_eof
584
585 def terminate(self, force=False):
586 '''This forces a child process to terminate. It starts nicely with
587 SIGHUP and SIGINT. If "force" is True then moves onto SIGKILL. This
588 returns True if the child was terminated. This returns False if the
589 child could not be terminated. '''
590
591 if not self.isalive():
592 return True
593 try:
594 self.kill(signal.SIGHUP)
595 time.sleep(self.delayafterterminate)
596 if not self.isalive():
597 return True
598 self.kill(signal.SIGCONT)
599 time.sleep(self.delayafterterminate)
600 if not self.isalive():
601 return True
602 self.kill(signal.SIGINT)
603 time.sleep(self.delayafterterminate)
604 if not self.isalive():
605 return True
606 if force:
607 self.kill(signal.SIGKILL)
608 time.sleep(self.delayafterterminate)
609 if not self.isalive():
610 return True
611 else:
612 return False
613 return False
614 except OSError:
615 # I think there are kernel timing issues that sometimes cause
616 # this to happen. I think isalive() reports True, but the
617 # process is dead to the kernel.
618 # Make one last attempt to see if the kernel is up to date.
619 time.sleep(self.delayafterterminate)
620 if not self.isalive():
621 return True
622 else:
623 return False
624
625 def wait(self):
626 '''This waits until the child exits. This is a blocking call. This will
627 not read any data from the child, so this will block forever if the
628 child has unread output and has terminated. In other words, the child
629 may have printed output then called exit(), but, the child is
630 technically still alive until its output is read by the parent.
631
632 This method is non-blocking if :meth:`wait` has already been called
633 previously or :meth:`isalive` method returns False. It simply returns
634 the previously determined exit status.
635 '''
636
637 ptyproc = self.ptyproc
638 with _wrap_ptyprocess_err():
639 # exception may occur if "Is some other process attempting
640 # "job control with our child pid?"
641 exitstatus = ptyproc.wait()
642 self.status = ptyproc.status
643 self.exitstatus = ptyproc.exitstatus
644 self.signalstatus = ptyproc.signalstatus
645 self.terminated = True
646
647 return exitstatus
648
649 def isalive(self):
650 '''This tests if the child process is running or not. This is
651 non-blocking. If the child was terminated then this will read the
652 exitstatus or signalstatus of the child. This returns True if the child
653 process appears to be running or False if not. It can take literally
654 SECONDS for Solaris to return the right status. '''
655
656 ptyproc = self.ptyproc
657 with _wrap_ptyprocess_err():
658 alive = ptyproc.isalive()
659
660 if not alive:
661 self.status = ptyproc.status
662 self.exitstatus = ptyproc.exitstatus
663 self.signalstatus = ptyproc.signalstatus
664 self.terminated = True
665
666 return alive
667
668 def kill(self, sig):
669
670 '''This sends the given signal to the child application. In keeping
671 with UNIX tradition it has a misleading name. It does not necessarily
672 kill the child unless you send the right signal. '''
673
674 # Same as os.kill, but the pid is given for you.
675 if self.isalive():
676 os.kill(self.pid, sig)
677
678 def getwinsize(self):
679 '''This returns the terminal window size of the child tty. The return
680 value is a tuple of (rows, cols). '''
681 return self.ptyproc.getwinsize()
682
683 def setwinsize(self, rows, cols):
684 '''This sets the terminal window size of the child tty. This will cause
685 a SIGWINCH signal to be sent to the child. This does not change the
686 physical window size. It changes the size reported to TTY-aware
687 applications like vi or curses -- applications that respond to the
688 SIGWINCH signal. '''
689 return self.ptyproc.setwinsize(rows, cols)
690
691
692 def interact(self, escape_character=chr(29),
693 input_filter=None, output_filter=None):
694
695 '''This gives control of the child process to the interactive user (the
696 human at the keyboard). Keystrokes are sent to the child process, and
697 the stdout and stderr output of the child process is printed. This
698 simply echos the child stdout and child stderr to the real stdout and
699 it echos the real stdin to the child stdin. When the user types the
700 escape_character this method will return None. The escape_character
701 will not be transmitted. The default for escape_character is
702 entered as ``Ctrl - ]``, the very same as BSD telnet. To prevent
703 escaping, escape_character may be set to None.
704
705 If a logfile is specified, then the data sent and received from the
706 child process in interact mode is duplicated to the given log.
707
708 You may pass in optional input and output filter functions. These
709 functions should take a string and return a string. The output_filter
710 will be passed all the output from the child process. The input_filter
711 will be passed all the keyboard input from the user. The input_filter
712 is run BEFORE the check for the escape_character.
713
714 Note that if you change the window size of the parent the SIGWINCH
715 signal will not be passed through to the child. If you want the child
716 window size to change when the parent's window size changes then do
717 something like the following example::
718
719 import pexpect, struct, fcntl, termios, signal, sys
720 def sigwinch_passthrough (sig, data):
721 s = struct.pack("HHHH", 0, 0, 0, 0)
722 a = struct.unpack('hhhh', fcntl.ioctl(sys.stdout.fileno(),
723 termios.TIOCGWINSZ , s))
724 global p
725 p.setwinsize(a[0],a[1])
726 # Note this 'p' global and used in sigwinch_passthrough.
727 p = pexpect.spawn('/bin/bash')
728 signal.signal(signal.SIGWINCH, sigwinch_passthrough)
729 p.interact()
730 '''
731
732 # Flush the buffer.
733 self.write_to_stdout(self.buffer)
734 self.stdout.flush()
735 self.buffer = self.string_type()
736 mode = tty.tcgetattr(self.STDIN_FILENO)
737 tty.setraw(self.STDIN_FILENO)
738 if escape_character is not None and PY3:
739 escape_character = escape_character.encode('latin-1')
740 try:
741 self.__interact_copy(escape_character, input_filter, output_filter)
742 finally:
743 tty.tcsetattr(self.STDIN_FILENO, tty.TCSAFLUSH, mode)
744
745 def __interact_writen(self, fd, data):
746 '''This is used by the interact() method.
747 '''
748
749 while data != b'' and self.isalive():
750 n = os.write(fd, data)
751 data = data[n:]
752
753 def __interact_read(self, fd):
754 '''This is used by the interact() method.
755 '''
756
757 return os.read(fd, 1000)
758
759 def __interact_copy(self, escape_character=None,
760 input_filter=None, output_filter=None):
761
762 '''This is used by the interact() method.
763 '''
764
765 while self.isalive():
766 r, w, e = self.__select([self.child_fd, self.STDIN_FILENO], [], [])
767 if self.child_fd in r:
768 try:
769 data = self.__interact_read(self.child_fd)
770 except OSError as err:
771 if err.args[0] == errno.EIO:
772 # Linux-style EOF
773 break
774 raise
775 if data == b'':
776 # BSD-style EOF
777 break
778 if output_filter:
779 data = output_filter(data)
780 self._log(data, 'read')
781 os.write(self.STDOUT_FILENO, data)
782 if self.STDIN_FILENO in r:
783 data = self.__interact_read(self.STDIN_FILENO)
784 if input_filter:
785 data = input_filter(data)
786 i = -1
787 if escape_character is not None:
788 i = data.rfind(escape_character)
789 if i != -1:
790 data = data[:i]
791 if data:
792 self._log(data, 'send')
793 self.__interact_writen(self.child_fd, data)
794 break
795 self._log(data, 'send')
796 self.__interact_writen(self.child_fd, data)
797
798 def __select(self, iwtd, owtd, ewtd, timeout=None):
799
800 '''This is a wrapper around select.select() that ignores signals. If
801 select.select raises a select.error exception and errno is an EINTR
802 error then it is ignored. Mainly this is used to ignore sigwinch
803 (terminal resize). '''
804
805 # if select() is interrupted by a signal (errno==EINTR) then
806 # we loop back and enter the select() again.
807 if timeout is not None:
808 end_time = time.time() + timeout
809 while True:
810 try:
811 return select.select(iwtd, owtd, ewtd, timeout)
812 except select.error:
813 err = sys.exc_info()[1]
814 if err.args[0] == errno.EINTR:
815 # if we loop back we have to subtract the
816 # amount of time we already waited.
817 if timeout is not None:
818 timeout = end_time - time.time()
819 if timeout < 0:
820 return([], [], [])
821 else:
822 # something else caused the select.error, so
823 # this actually is an exception.
824 raise
825
826 def spawnu(*args, **kwargs):
827 """Deprecated: pass encoding to spawn() instead."""
828 kwargs.setdefault('encoding', 'utf-8')
829 return spawn(*args, **kwargs)
OLDNEW
« no previous file with comments | « third_party/pexpect/pexpect/popen_spawn.py ('k') | third_party/pexpect/pexpect/pxssh.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698