Skip to content

Commit

Permalink
Dont rely on grandparent process to be shell
Browse files Browse the repository at this point in the history
- Change function to `get_shell`
- Allow `get_shell` to take `max_depth` as an arg
  • Loading branch information
techalchemy committed Mar 8, 2018
1 parent 631041d commit 5608d13
Show file tree
Hide file tree
Showing 2 changed files with 18 additions and 13 deletions.
27 changes: 16 additions & 11 deletions pew/_win_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@

ERROR_NO_MORE_FILES = 18
INVALID_HANDLE_VALUE = c_void_p(-1).value
SHELL_NAMES = ['cmd', 'powershell', 'cmder']


class PROCESSENTRY32(Structure):
Expand Down Expand Up @@ -74,7 +75,7 @@ def get_all_processes():
{
1509: {
'parent_pid': 1201,
'executable': 'C:\\Program\\\\ Files\\Python36\\python.exe'
'executable': 'python.exe'
}
}
"""
Expand All @@ -83,7 +84,7 @@ def get_all_processes():
pe = Process32First(h_process)
while pe:
pids[pe.th32ProcessID] = {
'executable': str(pe.szExeFile.decode('utf-8')),
'executable': str(pe.szExeFile.decode('utf-8'))
}
if pe.th32ParentProcessID:
pids[pe.th32ProcessID]['parent_pid'] = pe.th32ParentProcessID
Expand All @@ -92,16 +93,20 @@ def get_all_processes():
return pids


def get_grandparent_process(pid=None):
"""Get grandparent process name of the supplied pid or os.getpid().
:param int pid: The pid to track.
:return: Name of the grandparent process.
def get_shell(pid=None, max_depth=4):
"""Get the shell that the supplied pid or os.getpid() is running in.
"""
if not pid:
pid = os.getpid()
processes = get_all_processes()
ppid = processes[pid]['parent_pid']
parent = processes[ppid]
grandparent = processes[parent['parent_pid']]
return grandparent['executable']

def check_parent(pid, lvl=0):
ppid = processes[pid].get('parent_pid')
if ppid and processes[ppid]['executable'].lower().rsplit('.', 1)[0] in SHELL_NAMES:
return processes[ppid]['executable']
if lvl >= max_depth:
return
return check_parent(ppid, lvl=lvl+1)
if processes[pid]['executable'].lower().rsplit('.', 1)[0] in SHELL_NAMES:
return processes[pid]['executable']
return check_parent(pid)
4 changes: 2 additions & 2 deletions pew/pew.py
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@
InstallCommand = ListPythons = LocatePython = UninstallCommand = \
lambda : sys.exit('Command not supported on this platform')

from ._win_utils import get_grandparent_process
from ._win_utils import get_shell

from pew._utils import (check_call, invoke, expandpath, own, env_bin_dir,
check_path, temp_environ, NamedTemporaryFile, to_unicode)
Expand Down Expand Up @@ -184,7 +184,7 @@ def _detect_shell():
if 'CMDER_ROOT' in os.environ:
shell = 'Cmder'
elif windows:
shell = get_grandparent_process(os.getpid())
shell = get_shell(os.getpid())
else:
shell = 'sh'
return shell
Expand Down

0 comments on commit 5608d13

Please sign in to comment.