aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJustin M. Keyes <justinkz@gmail.com>2018-03-15 02:33:20 +0100
committerJustin M. Keyes <justinkz@gmail.com>2018-03-16 10:55:12 +0100
commit330e5acbcec00d1bc43a9c1110c4325fa62ba9ad (patch)
treeb7f853a1714dbb513593193f16033ffd38bee3a1
parent12af7016e23e7b7f507dc99a1b73e64d0bb5ccf3 (diff)
downloadrneovim-330e5acbcec00d1bc43a9c1110c4325fa62ba9ad.tar.gz
rneovim-330e5acbcec00d1bc43a9c1110c4325fa62ba9ad.tar.bz2
rneovim-330e5acbcec00d1bc43a9c1110c4325fa62ba9ad.zip
win: nvim_get_proc_children()
TODO: Raymond Chen explains[1] racy behavior of the CreateToolhelp32Snapshot approach. Better approach: > create a job object and put process P in it. Then call > QueryInformationJobObject with JobObjectBasicProcessIdList to get the > list of child processes. [1] "Why is CreateToolhelp32Snapshot returning incorrect parent process IDs all of a sudden?" https://blogs.msdn.microsoft.com/oldnewthing/20150403-00/?p=44313
-rw-r--r--src/nvim/os/process.c33
1 files changed, 30 insertions, 3 deletions
diff --git a/src/nvim/os/process.c b/src/nvim/os/process.c
index 80c2dad64d..09769925ac 100644
--- a/src/nvim/os/process.c
+++ b/src/nvim/os/process.c
@@ -43,7 +43,6 @@ static bool os_proc_tree_kill_rec(HANDLE process, int sig)
if (!Process32First(h, &pe)) {
goto theend;
}
-
do {
if (pe.th32ParentProcessID == pid) {
HANDLE ph = OpenProcess(PROCESS_ALL_ACCESS, false, pe.th32ProcessID);
@@ -53,7 +52,6 @@ static bool os_proc_tree_kill_rec(HANDLE process, int sig)
}
}
} while (Process32Next(h, &pe));
-
CloseHandle(h);
}
}
@@ -111,11 +109,40 @@ int os_proc_children(int ppid, int **proc_list, size_t *proc_count)
// https://github.com/giampaolo/psutil/tree/master/psutil/arch
//
+ if (ppid < 0) {
+ return 2;
+ }
+
int *temp = NULL;
*proc_list = NULL;
*proc_count = 0;
-#if defined(__APPLE__) || defined(BSD)
+#ifdef WIN32
+ PROCESSENTRY32 pe;
+
+ // Snapshot of all processes.
+ HANDLE h = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
+ if(h == INVALID_HANDLE_VALUE) {
+ return 2;
+ }
+
+ pe.dwSize = sizeof(PROCESSENTRY32);
+ // Get root process.
+ if(!Process32First(h, &pe)) {
+ CloseHandle(h);
+ return 2;
+ }
+ // Collect processes whose parent matches `ppid`.
+ do {
+ if (pe.th32ParentProcessID == (DWORD)ppid) {
+ temp = xrealloc(temp, (*proc_count + 1) * sizeof(*temp));
+ temp[*proc_count] = (int)pe.th32ProcessID;
+ (*proc_count)++;
+ }
+ } while (Process32Next(h, &pe));
+ CloseHandle(h);
+
+#elif defined(__APPLE__) || defined(BSD)
# if defined(__APPLE__)
# define KP_PID(o) o.kp_proc.p_pid
# define KP_PPID(o) o.kp_eproc.e_ppid