Launch a totally independent process from Python
Question:
I’m trying to launch a completely independent process from python. I can’t use something simple like os.startfile
since I need to pass arguments. Currently I’m using subprocess.popen
which gets me 90% of the way there.
args = ["some_exe.exe", "some_arg", "another_arg"]
subprocess.Popen(args, creationflags=DETACHED_PROCESS | CREATE_NEW_PROCESS_GROUP, stdout=subprocess.PIPE, stderr=subprocess.PIPE, stdin=subprocess.PIPE)
Using popen
with detached creation flags & pipes for std* does start a new process that lives after the parent process dies. So thats all good. The problem is that the new ‘child’ process still holds a phantom handle to the parent. So if I try to uninstall the parent exe (my python script is bundled into an exe via pyinstaller) msiexec complains that the parent exe is still in use.
So the goal is to spawn a totally independent process to run "some_exe.exe" that doesn’t have any handle back to the original process.
Note: This is for Windows XP and above. I’m developing on Win7.
Answers:
I found this here:
On windows (win xp), the parent process will not finish until the longtask.py has finished its work. It is not what you want in CGI-script. The problem is not specific to Python, in PHP community the problems are the same.
The solution is to pass DETACHED_PROCESS Process Creation Flag to the underlying CreateProcess function in win API. If you happen to have installed pywin32 you can import the flag from the win32process module, otherwise you should define it yourself:
DETACHED_PROCESS = 0x00000008
pid = subprocess.Popen([sys.executable, “longtask.py”],
creationflags=DETACHED_PROCESS).pid
I think I found the answer. By using Popen
with close_fds = True
I was able to start up a process that was independent and without handles to the parent.
For docs look here and search for close_fds
.
Or, on Windows, if close_fds is true then no handles will be inherited
by the child process. Note that on Windows, you cannot set close_fds
to true and also redirect the standard handles by setting stdin,
stdout or stderr.
Note this solution only works on Windows. I have no idea about any *nix system.
I’m trying to launch a completely independent process from python. I can’t use something simple like os.startfile
since I need to pass arguments. Currently I’m using subprocess.popen
which gets me 90% of the way there.
args = ["some_exe.exe", "some_arg", "another_arg"]
subprocess.Popen(args, creationflags=DETACHED_PROCESS | CREATE_NEW_PROCESS_GROUP, stdout=subprocess.PIPE, stderr=subprocess.PIPE, stdin=subprocess.PIPE)
Using popen
with detached creation flags & pipes for std* does start a new process that lives after the parent process dies. So thats all good. The problem is that the new ‘child’ process still holds a phantom handle to the parent. So if I try to uninstall the parent exe (my python script is bundled into an exe via pyinstaller) msiexec complains that the parent exe is still in use.
So the goal is to spawn a totally independent process to run "some_exe.exe" that doesn’t have any handle back to the original process.
Note: This is for Windows XP and above. I’m developing on Win7.
I found this here:
On windows (win xp), the parent process will not finish until the longtask.py has finished its work. It is not what you want in CGI-script. The problem is not specific to Python, in PHP community the problems are the same.
The solution is to pass DETACHED_PROCESS Process Creation Flag to the underlying CreateProcess function in win API. If you happen to have installed pywin32 you can import the flag from the win32process module, otherwise you should define it yourself:
DETACHED_PROCESS = 0x00000008
pid = subprocess.Popen([sys.executable, “longtask.py”],
creationflags=DETACHED_PROCESS).pid
I think I found the answer. By using Popen
with close_fds = True
I was able to start up a process that was independent and without handles to the parent.
For docs look here and search for close_fds
.
Or, on Windows, if close_fds is true then no handles will be inherited
by the child process. Note that on Windows, you cannot set close_fds
to true and also redirect the standard handles by setting stdin,
stdout or stderr.
Note this solution only works on Windows. I have no idea about any *nix system.