summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGiampaolo Rodola <g.rodola@gmail.com>2020-01-08 11:41:33 -0800
committerGiampaolo Rodola <g.rodola@gmail.com>2020-01-08 11:41:33 -0800
commit35b56cdce57d88897cf486cd9dca25503c20f140 (patch)
tree840bdc8ae581564b91d1a78f91e082e4cf9e32e4
parent9c7511e33c0c41e692964c11c613bbff0fb35516 (diff)
downloadpsutil-35b56cdce57d88897cf486cd9dca25503c20f140.tar.gz
progress with thread skeleton
-rw-r--r--psutil/arch/windows/process_handles.c221
1 files changed, 41 insertions, 180 deletions
diff --git a/psutil/arch/windows/process_handles.c b/psutil/arch/windows/process_handles.c
index ee593d10..57edb66d 100644
--- a/psutil/arch/windows/process_handles.c
+++ b/psutil/arch/windows/process_handles.c
@@ -12,84 +12,71 @@
#include "process_utils.h"
+// Global objects used by threads.
CRITICAL_SECTION g_cs;
BOOL g_initialized = FALSE;
NTSTATUS g_status;
HANDLE g_hFile = NULL;
-HANDLE g_hEvtStart = NULL;
-HANDLE g_hEvtFinish = NULL;
-HANDLE g_hThread = NULL;
PUNICODE_STRING g_pNameBuffer = NULL;
ULONG g_dwSize = 0;
ULONG g_dwLength = 0;
-#define NTQO_TIMEOUT 100
+#define NTQO_TIMEOUT 2000
#define MALLOC_ZERO(x) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (x))
-static VOID
+static DWORD
psutil_init_threads() {
if (g_initialized == TRUE)
- return;
-
- // Create events for signalling work between threads
- g_hEvtStart = CreateEvent(NULL, FALSE, FALSE, NULL);
- g_hEvtFinish = CreateEvent(NULL, FALSE, FALSE, NULL);
+ return 0;
InitializeCriticalSection(&g_cs);
g_initialized = TRUE;
+ return 0;
}
-static DWORD WINAPI
-psutil_wait_thread(LPVOID lpvParam) {
- // Loop infinitely waiting for work
- while (TRUE) {
- WaitForSingleObject(g_hEvtStart, INFINITE);
-
- // TODO: return code not checked
- g_status = NtQueryObject(
- g_hFile,
- ObjectNameInformation,
- g_pNameBuffer,
- g_dwSize,
- &g_dwLength);
- SetEvent(g_hEvtFinish);
- }
+static int
+psutil_get_filename(LPVOID lpvParam) {
+ printf("inside thread fun\n");
+ // Sleep(3000);
+ return 0;
}
static DWORD
psutil_create_thread() {
DWORD dwWait = 0;
+ HANDLE hThread = NULL;
+ DWORD threadRetValue;
- if (g_hThread == NULL)
- g_hThread = CreateThread(
- NULL,
- 0,
- psutil_wait_thread,
- NULL,
- 0,
- NULL);
- if (g_hThread == NULL)
- return GetLastError();
-
- // Signal the worker thread to start
- SetEvent(g_hEvtStart);
+ hThread = CreateThread(NULL, 0, psutil_get_filename, NULL, 0, NULL);
+ if (hThread == NULL) {
+ PyErr_SetFromOSErrnoWithSyscall("CreateThread");
+ return 1;
+ }
// Wait for the worker thread to finish
- dwWait = WaitForSingleObject(g_hEvtFinish, NTQO_TIMEOUT);
+ dwWait = WaitForSingleObject(hThread, NTQO_TIMEOUT);
- // If the thread hangs, kill it and cleanup
+ // If the thread hangs, kill it and cleanup.
if (dwWait == WAIT_TIMEOUT) {
- SuspendThread(g_hThread);
- TerminateThread(g_hThread, 1);
- WaitForSingleObject(g_hThread, INFINITE);
- CloseHandle(g_hThread);
-
- g_hThread = NULL;
+ printf("thread timed out\n");
+ SuspendThread(hThread);
+ TerminateThread(hThread, 1);
+ CloseHandle(hThread);
+ return 0;
+ }
+ else {
+ printf("thread completed\n");
+ if (GetExitCodeThread(hThread, &threadRetValue) == 0) {
+ CloseHandle(hThread);
+ PyErr_SetFromOSErrnoWithSyscall("GetExitCodeThread");
+ return 1;
+ }
+ CloseHandle(hThread);
+ printf("retcode = %i\n", threadRetValue);
+ return threadRetValue;
}
-
- return dwWait;
}
@@ -152,7 +139,12 @@ psutil_get_open_files(DWORD dwPid, HANDLE hProcess) {
return NULL;
if (g_initialized == FALSE)
- psutil_init_threads();
+ if (psutil_init_threads() != 0)
+ goto error;
+
+ ret = psutil_create_thread();
+ if (ret != 0)
+ goto error;
goto exit;
@@ -167,134 +159,3 @@ exit:
return py_retlist;
}
-
-/*
- if (g_initialized == FALSE)
- psutil_get_open_files_init(TRUE);
-
- // Due to the use of global variables, ensure only 1 call
- // to psutil_get_open_files() is running
- EnterCriticalSection(&g_cs);
-
- if (g_hEvtStart == NULL || g_hEvtFinish == NULL) {
- PyErr_SetFromWindowsErr(0);
- error = TRUE;
- goto cleanup;
- }
-
- // Py_BuildValue raises an exception if NULL is returned
- py_retlist = PyList_New(0);
- if (py_retlist == NULL) {
- error = TRUE;
- goto cleanup;
- }
-
- ret = psutil_enum_handles(&handlesList);
- if (ret != 0)
- goto cleanup;
-
- for (i = 0; i < handlesList->NumberOfHandles; i++) {
- hHandle = &handlesList->Handles[i];
-
- // Check if this hHandle belongs to the PID the user specified.
- if ((ULONG_PTR)hHandle->UniqueProcessId != dwPid)
- goto loop_cleanup;
-
- if (!DuplicateHandle(hProcess,
- (HANDLE)hHandle->HandleValue,
- GetCurrentProcess(),
- &g_hFile,
- 0,
- TRUE,
- DUPLICATE_SAME_ACCESS))
- {
- goto loop_cleanup;
- }
-
- // Guess buffer size is MAX_PATH + 1
- g_dwLength = (MAX_PATH+1) * sizeof(WCHAR);
-
- do {
- // Release any previously allocated buffer
- if (g_pNameBuffer != NULL) {
- FREE(g_pNameBuffer);
- g_pNameBuffer = NULL;
- g_dwSize = 0;
- }
-
- // NtQueryObject puts the required buffer size in g_dwLength
- // WinXP edge case puts g_dwLength == 0, just skip this handle
- if (g_dwLength == 0)
- goto loop_cleanup;
-
- g_dwSize = g_dwLength;
- if (g_dwSize > 0) {
- g_pNameBuffer = malloc(g_dwSize);
-
- if (g_pNameBuffer == NULL)
- goto loop_cleanup;
- }
-
- dwWait = psutil_create_thread();
-
- // If the call does not return, skip this handle
- if (dwWait != WAIT_OBJECT_0)
- goto loop_cleanup;
-
- } while (g_status == STATUS_INFO_LENGTH_MISMATCH);
-
- // NtQueryObject stopped returning STATUS_INFO_LENGTH_MISMATCH
- if (!NT_SUCCESS(g_status))
- goto loop_cleanup;
-
- // Convert to PyUnicode and append it to the return list
- if (g_pNameBuffer->Length > 0) {
- py_path = PyUnicode_FromWideChar(g_pNameBuffer->Buffer,
- g_pNameBuffer->Length / 2);
- if (py_path == NULL) {
- error = TRUE;
- goto loop_cleanup;
- }
-
- if (PyList_Append(py_retlist, py_path)) {
- error = TRUE;
- goto loop_cleanup;
- }
- }
-
-loop_cleanup:
- Py_XDECREF(py_path);
- py_path = NULL;
- if (g_pNameBuffer != NULL)
- FREE(g_pNameBuffer);
- g_pNameBuffer = NULL;
- g_dwSize = 0;
- g_dwLength = 0;
- if (g_hFile != NULL)
- CloseHandle(g_hFile);
- g_hFile = NULL;
-}
-
-cleanup:
- if (g_pNameBuffer != NULL)
- FREE(g_pNameBuffer);
- g_pNameBuffer = NULL;
- g_dwSize = 0;
- g_dwLength = 0;
-
- if (g_hFile != NULL)
- CloseHandle(g_hFile);
- g_hFile = NULL;
-
- if (handlesList != NULL)
- FREE(handlesList);
- handlesList = NULL;
-
- if (error) {
- Py_XDECREF(py_retlist);
- py_retlist = NULL;
- }
-
- LeaveCriticalSection(&g_cs);
- return py_retlist;
-*/