summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGiampaolo Rodola <g.rodola@gmail.com>2019-02-17 10:00:58 -0800
committerGiampaolo Rodola <g.rodola@gmail.com>2019-02-17 10:00:58 -0800
commite5926872ba69cc5de807ac81afd2ba2ccb1a86a0 (patch)
tree4b769073c0a6b39137d5a044a58bbc9ef89e5c76
parenta6381abe6ef6197d9090bafd5028c3cd37bddda3 (diff)
downloadpsutil-e5926872ba69cc5de807ac81afd2ba2ccb1a86a0.tar.gz
add logic to support windows XP
-rw-r--r--psutil/_psutil_windows.c21
-rw-r--r--psutil/_pswindows.py38
2 files changed, 53 insertions, 6 deletions
diff --git a/psutil/_psutil_windows.c b/psutil/_psutil_windows.c
index 7c94b816..30bd96cb 100644
--- a/psutil/_psutil_windows.c
+++ b/psutil/_psutil_windows.c
@@ -763,22 +763,39 @@ static PyObject *
psutil_proc_exe(PyObject *self, PyObject *args) {
long pid;
HANDLE hProcess;
- PDWORD size = MAX_PATH;
wchar_t exe[MAX_PATH];
+#if (_WIN32_WINNT >= 0x0600) // >= Vista
+ PDWORD size = MAX_PATH;
+#endif
if (! PyArg_ParseTuple(args, "l", &pid))
return NULL;
hProcess = psutil_handle_from_pid(pid, PROCESS_QUERY_LIMITED_INFORMATION);
if (NULL == hProcess)
return NULL;
- // before this was using GetProcessImageFileNameW see:
+
+ // Here we differentiate between XP and Vista+ because
+ // QueryFullProcessImageNameW is better than GetProcessImageFileNameW
+ // (avoid using QueryDosDevice on the returned path), see:
// https://github.com/giampaolo/psutil/issues/1394
+#if (_WIN32_WINNT >= 0x0600) // Windows >= Vista
memset(exe, 0, MAX_PATH);
if (QueryFullProcessImageNameW(hProcess, 0, exe, &size) == 0) {
PyErr_SetFromWindowsErr(0);
CloseHandle(hProcess);
return NULL;
}
+#else // Windows XP
+ if (GetProcessImageFileNameW(hProcess, exe, MAX_PATH) == 0) {
+ // see: https://github.com/giampaolo/psutil/issues/1394
+ if (GetLastError() == 0) {
+ PyErr_SetFromWindowsErr(ERROR_ACCESS_DENIED);
+ else
+ PyErr_SetFromWindowsErr(0);
+ CloseHandle(hProcess);
+ return NULL;
+ }
+#endif
CloseHandle(hProcess);
return PyUnicode_FromWideChar(exe, wcslen(exe));
}
diff --git a/psutil/_pswindows.py b/psutil/_pswindows.py
index 8aeb9263..0441b8a1 100644
--- a/psutil/_pswindows.py
+++ b/psutil/_pswindows.py
@@ -147,6 +147,28 @@ ZombieProcess = None
AccessDenied = None
TimeoutExpired = None
+# More values at: https://stackoverflow.com/a/20804735/376587
+WIN_10 = (10, 0)
+WIN_8 = (6, 2)
+WIN_7 = (6, 1)
+WIN_SERVER_2008 = (6, 0)
+WIN_VISTA = (6, 0)
+WIN_SERVER_2003 = (5, 2)
+WIN_XP = (5, 1)
+
+
+@lru_cache()
+def get_winver():
+ """Usage:
+ >>> if get_winver() <= WIN_VISTA:
+ ... ...
+ """
+ wv = sys.getwindowsversion()
+ return (wv.major, wv.minor)
+
+
+IS_WIN_XP = get_winver() < WIN_VISTA
+
# =====================================================================
# --- named tuples
@@ -694,10 +716,18 @@ class Process(object):
@wrap_exceptions
def exe(self):
- exe = cext.proc_exe(self.pid)
- if not PY3:
- exe = py2_strencode(exe)
- return exe
+ # Dual implementation, see:
+ # https://github.com/giampaolo/psutil/pull/1413
+ if not IS_WIN_XP:
+ exe = cext.proc_exe(self.pid)
+ else:
+ if self.pid in (0, 4):
+ # https://github.com/giampaolo/psutil/issues/414
+ # https://github.com/giampaolo/psutil/issues/528
+ raise AccessDenied(self.pid, self._name)
+ exe = cext.proc_exe(self.pid)
+ exe = convert_dos_path(exe)
+ return py2_strencode(exe)
@wrap_exceptions
def cmdline(self):