Commandline wrapper: help needed

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Toby

    #1

    Commandline wrapper: help needed

    I'm trying to write a simple commandline wrapper: a script that runs
    another program as a child and relays unbuffered stdin and stdout
    to/from the child process, possibly filtering it.

    The usefulness of such a program lies in the filtering stage, in a
    possible integration with readline, or in other interface enhancements.

    Still, I'd like to discuss with you the unfiltered, unembellished
    version, because I'm not satisfied with it and because I'm having some
    minor problems.

    Here's the script:


    #!/usr/bin/python

    import sys, os, thread

    def stdin_handler(c hild_stdin):
    while True:
    d = sys.stdin.read( 1)
    if not d: break
    child_stdin.wri te(d)
    child_stdin.flu sh()
    child_stdin.clo se()

    def stdout_handler( child_stdout):
    while True:
    try:
    d = child_stdout.re ad(1)
    if not d: break
    sys.stdout.writ e(d)
    sys.stdout.flus h()
    except KeyboardInterru pt:
    pass

    def wrap(cmd):
    child_stdin, child_stdout = os.popen2(cmd)
    thread.start_ne w_thread(stdin_ handler, (child_stdin,))
    stdout_handler( child_stdout)

    if __name__ == '__main__':
    wrap(sys.argv[1])


    You invoke it passing a program name as the first argument (such as
    bash, python itself, sbcl, whatever) and then you interact with the
    child process as if this wrapper wasn't there. Ctrl-C and Ctrl-D work
    as expected, sending SIGINT (that the child program can catch) and
    closing stdin respectively.

    Problems:

    1.

    I don't like the read(1) loops. I'd like to be able to read bigger
    chunks at a time, but I haven't found a way to do that while keeping the
    functionality intact. I have tried fidgeting with select() but I didn't
    get far. What I (think I) need is a non-blocking read(), but I'm not
    sure how to achieve that, at least with Python 2.4 on Linux.

    2.

    Even this version sometimes has problems. For example, if you launch
    the wrapper around sbcl (a free Lisp interpreter/compiler) it mostly
    works (entering 1 gives 1, entering (+ 2 3) gives 5...) until you get to
    the debugger, for example by entering an undefined name. Now, when the
    debugger says "0: [ABORT] Exit debugger...", entering 0 should get you
    back to the "*" prompt--and indeed does, unless you are using my
    wrapper, in which case everything hangs, and the only solution is to
    terminate everything with Ctrl-\ or such.

    Any idea how to improve the script and solve this problem?


    Toby
  • Toby A Inkster

    #2
    Re: Commandline wrapper: help needed

    Toby wrote:
    Any idea how to improve the script and solve this problem?
    Hello Toby, excellent name you have there. What advantage (if any) does
    this method have over standard UNIX-style pipes?

    --
    Toby A Inkster BSc (Hons) ARCS
    Contact Me ~ http://tobyinkster.co.uk/contact

    Comment

    • Toby

      #3
      Re: Commandline wrapper: help needed

      Toby A Inkster wrote:
      Hello Toby, excellent name you have there.
      Why, thank you!
      What advantage (if any) does this method have over standard UNIX-style
      pipes?
      The advantage is being able to write my own filters and input/output
      modules and have as small a granularity as needed (while standard UNIX
      filters such as cat, grep, sed and awk process entire lines at a time.)
      For example I can launch an interactive shell of some kind and use it
      both from the terminal I opened it in, and from the network, if my
      script is listening on a socket.

      By the way, I am using standard UNIX pipes, that's how popen() works!


      Toby

      Comment

      Working...