By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
443,898 Members | 1,183 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 443,898 IT Pros & Developers. It's quick & easy.

Wrapping A Shell

P: n/a
I'm not sure if this is really the right place to ask this question, but
since the implementation is in Python, I figured I'd give it a shot.

I want to "wrap" a shell process using popen inside of python program
rather than creating a new shell process for each line I process in the
app. For example, the code might look like:
std = stdin, stdout, stderr = os.popen3("bash")

print >stdin, "ls"

print stdout.readline()

However, it appears my understanding of popen (or perhaps buffered IO)
is off somewhere, because this certainly doesn't work anything like I
expect it to (it hangs on stdout.readline).

Obviously the example above is very contrived, but eventually I'll be
using this in an OpenGL "terminal" widget. Am I approaching this the
wrong way?

Nov 28 '06 #1
Share this Question
Share on Google+
2 Replies


P: n/a

Jeremy Moles wrote:
I'm not sure if this is really the right place to ask this question, but
since the implementation is in Python, I figured I'd give it a shot.

I want to "wrap" a shell process using popen inside of python program
rather than creating a new shell process for each line I process in the
app. For example, the code might look like:
std = stdin, stdout, stderr = os.popen3("bash")

print >stdin, "ls"

print stdout.readline()

However, it appears my understanding of popen (or perhaps buffered IO)
is off somewhere, because this certainly doesn't work anything like I
expect it to (it hangs on stdout.readline).

Obviously the example above is very contrived, but eventually I'll be
using this in an OpenGL "terminal" widget. Am I approaching this the
wrong way?
Try flushing the bufffer for stdin.
Cheers,
-T

Nov 28 '06 #2

P: n/a
Jeremy Moles <je****@emperorlinux.comwrote:
I'm not sure if this is really the right place to ask this question, but
since the implementation is in Python, I figured I'd give it a shot.

I want to "wrap" a shell process using popen inside of python program
rather than creating a new shell process for each line I process in the
app. For example, the code might look like:
std = stdin, stdout, stderr = os.popen3("bash")

print >stdin, "ls"

print stdout.readline()

However, it appears my understanding of popen (or perhaps buffered IO)
is off somewhere, because this certainly doesn't work anything like I
expect it to (it hangs on stdout.readline).

Obviously the example above is very contrived, but eventually I'll be
using this in an OpenGL "terminal" widget. Am I approaching this the
wrong way?
Short answer: use pexpect

http://pexpect.sourceforge.net/

Long answer:

Firstly modern pythonistas use subprocess instead of os.popen*.

Secondly, buffering is going to cause you trouble and possible
deadlocks.

There are two ways to rid yourself of deadlock.

1) read and write from seperate threads / processes. This is the
traditional unix way

2) use non blocking IO

Here is a possible way to solve the problems with subprocess (unix
only) and non blocking IO.

However I suspect you really want to use pexpect for this job...

from os import O_NONBLOCK
from errno import EAGAIN
from subprocess import Popen, PIPE
from fcntl import fcntl, F_SETFL, F_GETFL
from time import time

p = Popen(["/bin/bash", "-i"], shell=False, bufsize=0, stdin=PIPE, stdout=PIPE, stderr=PIPE, close_fds=True)

# Make output streams non blocking (unix only)
for fd in (p.stdout.fileno(), p.stderr.fileno()):
fcntl(fd, F_SETFL, fcntl(fd, F_GETFL) | O_NONBLOCK)

def read_output(p, timeout=1.0):
"""Read the output from the subprocess, with timeout"""
end_time = time() + timeout
output = ""
while time() < end_time:
try:
output += p.stdout.read(1024)
except IOError, e:
if e.errno != EAGAIN:
raise
return output

p.stdin.write("ls\n")
print read_output(p)
p.stdin.write("uname -a\n")
print read_output(p)

--
Nick Craig-Wood <ni**@craig-wood.com-- http://www.craig-wood.com/nick
Nov 29 '06 #3

This discussion thread is closed

Replies have been disabled for this discussion.