PEP 324: popen5 - New POSIX process module

Paul Moore paul.moore at atosorigin.com
Mon Jan 5 23:53:47 CET 2004


I've read the PEP, and I'd like to help with an implementation for
Windows, if no-one else is doing it. Initially, I'll probably use
win32all (or maybe ctypes) but the intention is that longer term the
necessary functions be migrated into a supporting C extension.

I do have some comments, which may be of interest.

The whole interface feels very Unix-specific. In particular,

1. The preexec_* arguments have no meaning on Windows, where the
   low-level functionality is CreateProcess (spawn) rather than
   fork/exec. This isn't too crucial, as use of the argument can
   either be ignored, or probably better, treated as an error on
   Windows.

2. The method name poll() doesn't seem appropriate in a Windows
   context (I don't know how it fits with Unix). Better might be
   is_complete() returning True/False, and use returncode to get the
   status separately.

3. The whole thing about the return code encoding both the exit status
   and the signal number is very Unix-specific. Why not split them -
   status and signal attributes, and maybe have is_complete() return 3
   possible values - +1 = completed OK, 0 = still running, -1 = died
   due to a signal.

4. wait() should be defined as "wait for the subprocess to finish, and
   then return is_complete()". That's basically what you have now,
   it's just a bit clearer if you're explicit about the intent.

5. I don't like the names fromchild, tochild, and childerr. What's
   wrong with stdin, stdout, and stderr? OK, stdin is open for write,
   and the other two for read, but that's fairly obvious as soon as
   you think about it a bit.

The biggest issue, though, is that args as a sequence of program
arguments is very Unix-specific. This is a big incompatibility between
Unix and Windows - in Windows, the low-level operation (CreateProcess)
takes a *command line* which is passed unchanged to the child process. 
The child then parses that command line for itself (often, but not
always, in the C runtime). In Unix, exec() takes an *argument list*. 
If you have a command line, you have to split it yourself, a task
which is usually delegated to /bin/sh in the absence of anything else. 
This is hard to handle portably.

I'd suggest that the Windows implementation allow two possibilities
for the "args" argument. If args is a string, it is passed intact to
CreateProcess. That is the recommended, and safe, approach. The shell
is still not invoked, so there's no security issue. If a (non-string)
sequence is passed, the Windows implementation should (for Unix
compatibility) build a command line, using its best attempt to quote
things appropriately (this can never be safe, as different programs
can implement different command line parsing). This is not safe (wrong
answers are the main problem, not security holes), but will improve
portability.

I agree with Guido's comments on python-dev - this module (popen5 is a
*horrible* name - I'd prefer "process", but am happy if someone comes
up with a better suggestion) should aim to be the clear "best of
breed" process control module for all platforms.

Some other points may well come up as I try to implement a Windows
version.

I hope this is of some use,
Paul.
-- 
This signature intentionally left blank





More information about the Python-list mailing list