Sublime Forum

How to kill properly win32 processes spawned from ExecCommand?

#1

I’m having some problems trying to kill processes on win32. First things first, if we take a look to the used code by ExecCommand:

def kill(self):
    if not self.killed:
        self.killed = True
        if sys.platform == "win32":
            # terminate would not kill process opened by the shell cmd.exe,
            # it will only kill cmd.exe leaving the child running
            startupinfo = subprocess.STARTUPINFO()
            startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW
            subprocess.Popen(
                "taskkill /PID " + str(self.proc.pid),
                startupinfo=startupinfo)
        else:
            self.proc.terminate()
        self.listener = None

We can see the decission of ExecCommand is leaving child processes still running (dunno the reason)… Anyway, after researching a bit, I’ve found this thread https://stackoverflow.com/questions/1230669/subprocess-deleting-child-processes-in-windows and I’ve decided to give it a shot to the lightweight function:

def kill_command_windows(pid):
    '''Run command via subprocess'''
    dev_null = open(os.devnull, 'w')
    command = ['TASKKILL', '/F', '/T', '/PID', str(pid)]
    proc = subprocess.Popen(command, stdin=dev_null, stdout=sys.stdout, stderr=sys.stderr)

Problem is, this method will work very rarely, in one of my tests I’ve experienced how SublimeText process will be frozen. Could anyone advice how to kill properly win32 processes (parent+childs) from SublimeText?

You can reproduce very easily all of this with a couple of lines:

>>> sublime.active_window().run_command("exec", args={"shell_cmd": "notepad.exe"})
>>> sublime.active_window().run_command("exec", args={"kill": True})

And you’ll see notepad will still remain alive, then you can try the posted kill_command_windows and if you’re lucky enough you’ll leave ST hanging out after the first attempt.

Thx in advance.

PS: To check the processes info (PIDs) you can use the task admin from windows or even better, processExplorer, which is a really great tool. Or… just print self.proc.pid in the execCommand run method

0 Likes

#2

Actually, I’ve given another shot and I’ve checked this one:

def kill(self):
    if not self.killed:
        self.killed = True
        if sys.platform == "win32":
            # terminate would not kill process opened by the shell cmd.exe,
            # it will only kill cmd.exe leaving the child running
            # startupinfo = subprocess.STARTUPINFO()
            # startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW
            # subprocess.Popen(
            #     "taskkill /PID " + str(self.proc.pid),
            #     startupinfo=startupinfo)

            startupinfo = subprocess.STARTUPINFO()
            startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW
            subprocess.Popen(
                "taskkill /F /T /PID " + str(self.proc.pid),
                startupinfo=startupinfo)
        else:
            self.proc.terminate()
        self.listener = None

So far it’s killing the processes properly without SublimeText hanging out… in the previous post I’ve mentioned SublimeText sometimes would hang… maybe the reason being I was testing the method kill_command_windows in a separate python process? Dunno… anyway, let’s see how this new way go. So far so good :confused:

0 Likes

#3

I’m not sure if this is about the same thing, but there is an issue on the core tracker about build canceling not killing the entire process tree (on windows). I posted a possible solution with specific flag arguments to taskkill in that issue. I also think I tested it and it worked, but it’s been a while and I don’t use windows regularly anymore.

1 Like

#4

Oh yeah, found it… seems you’ve applied the same params I’ve used above. I’ll be testing this from now on… If I find Sublime hanging again I’ll try to figure out why.

Btw, do you know why that fix hasn’t gone to production? I seen your suggestion is back from 2014… Maybe there is any reason why the guys consider leaving orphan child processes is a good thing? I don’t get it :confused:

0 Likes