for x in Files:
Command_String = 'C:\Program Files\WinRK\WinRK.exe -create ' +
os.path.join(InputDirectory, os.path.splitext(x)[0]) + ' -set
compression_method ppmz -setg include_paths none -add ' +
os.path.join(InputDirectory, x) + ' -apply -quit'
PROC = subprocess.Popen(Command_String)
PROC.wait()
... # process WinRK output
This hangs occasionally, and is not repeatable - it never hangs on the
same file.
Replacing the PROC.wait() command with the loop
while PROC.poll() == None: time.sleep(1)
has not hung on approximately 7,000 calls to WinRK.
Earl
On Tue, 2005-03-22 at 09:35, Jeff Epler wrote:
> On Tue, Mar 22, 2005 at 07:16:11AM -0700, Earl Eiland wrote:
> > I've been having trouble with a program hanging when using the
> > subprocess modules "wait()" method. Replacing it with with a loop that
> > used "poll()" solved the problem.
>
> Please include an example, and more information about what platforn you're using
> This simple program worked fine for me on Linux with Python 2.4:
> #------------------------------------------------------------------------
> import subprocess, time
>
> s = subprocess.Popen(['sleep', '2'])
> while 1:
> time.sleep(.1)
> if s.poll() is not None: break
> print "polling wait done", s.returncode
>
> s = subprocess.Popen(['sleep', '2'])
> s.wait()
> print "blocking wait done", s.returncode
> #------------------------------------------------------------------------
>
> Jeff
Earl
On Tue, 2005-03-22 at 12:43, Jeff Epler wrote:
> I wrote a program to use subprocess.Popen 10000 times, and never had
> .wait() hang. If this is a bug, it may be Windows specific.
>
> Here's the program I ran:
> #-------------------------------------------------------------------------
> import subprocess, signal
> def timeout(*args):
> print "Timed out waiting on", i
> raise SystemExit, 1
>
> signal.signal(signal.SIGALRM, timeout)
>
> for i in xrange(10000):
> signal.alarm(5)
> subprocess.Popen(['/bin/true']).wait()
> if i % 100 == 0: print "done with", i
> print "done!"
> #-------------------------------------------------------------------------
>
> If the wait method ever hangs, the signal handler shuld be invoked. On
> Unix, "/bin/true" is a very simple program that does nothing, so it's
> virtually guaranteed to run in less than 5 seconds. On Windows, maybe
> you want something like subprocess.popen('cmd.exe /c rem') as a command
> that will do nothing and terminate quickly. What happens if you run my
> program with that change to the Popen line?
>
> Jeff
Earl
Earl
On Tue, 2005-03-22 at 13:49, Jeff Epler wrote:
> hm, I guess SIGALRM doesn't exist on Windows. You can run the program
> without the 'signal.signal' line or the 'signal.alarm' line, and you'll
> be stuck with a hung Python if subprocess.Popen exhibits the bug.
>
> Jeff
I don't have any idea. Both are implemented in terms of
win32event.WaitForSingleObject (which is itself a thin wrapper over the
win32 API of the same name[1]), one with a zero timeout and one with an
INFINITE timeout.
This caveat is in the msdn page on WFSO:
Use caution when calling the wait functions and code that directly
or indirectly creates windows. If a thread creates any windows, it
must process messages. Message broadcasts are sent to all windows in
the system. A thread that uses a wait function with no time-out
interval may cause the system to become deadlocked. Two examples of
code that indirectly creates windows are DDE and the CoInitialize
function. Therefore, if you have a thread that creates windows, use
MsgWaitForMultipleObjects or MsgWaitForMultipleObjectsEx, rather
than WaitForSingleObject.
... which is pretty much greek to this unix geek. If your Python
program has a GUI, can you strip out the gui-related parts to make it a
pure commandline program, and see if you still have the problem?
You could try something like (untested, obviously)
import subprocess
if subprocess.mswindows:
from win32event import WaitForSingleObject
from win32process import GetExitCodeProcess
def wait(self):
"""Wait for child process to terminate. Returns returncode
attribute."""
while self.returncode is None:
obj = WaitForSingleObject(self._handle, 1000)
self.returncode = GetExitCodeProcess(self._handle)
_active.remove(self)
return self.returncode
subprocess.Popen.wait = wait
to make the .wait() method call WFSO with a timeout, and then maybe you
can simply forget about the weird behavior you ran into.
Jeff
[1] http://msdn.microsoft.com/library/en-us/dllproc/base/waitforsingleobject.asp
>I'm running the following code on Windows 2000, 5.00.2195:
>
>for x in Files:
> Command_String = 'C:\Program Files\WinRK\WinRK.exe -create ' +
That can't be right. You need either
Command_String = 'C:\\Program Files\\WinRK\\WinRK.exe -create ' +
or
Command_String = r'C:\Program Files\WinRK\WinRK.exe -create ' +
--
- Tim Roberts, ti...@probo.com
Providenza & Boekelheide, Inc.
Earl
You're right about that, *as the code now stands*.
The danger is that you are using single backslashes.
The *only* reason this works right now is because none
of the characters you have following those backslashes
happen to be part of reserved escape sequences. See
http://docs.python.org/ref/strings.html to learn why
Tim is basically right, even though in this case you
are getting away with it...
(Yes, I know this doesn't solve the real problem.)
-Peter