Implemented kernel32.GetThreadTimes on top of ntdll's equivalent

function.
This commit is contained in:
Eric Pouech 2005-09-12 22:01:33 +00:00 committed by Alexandre Julliard
parent ba41fe20bc
commit ad0168967e
2 changed files with 70 additions and 51 deletions

View File

@ -25,9 +25,6 @@
#include <fcntl.h> #include <fcntl.h>
#include <stdarg.h> #include <stdarg.h>
#include <sys/types.h> #include <sys/types.h>
#ifdef HAVE_SYS_TIMES_H
#include <sys/times.h>
#endif
#ifdef HAVE_UNISTD_H #ifdef HAVE_UNISTD_H
# include <unistd.h> # include <unistd.h>
#endif #endif
@ -545,59 +542,38 @@ BOOL WINAPI GetThreadTimes(
LPFILETIME kerneltime, /* [out] Time thread spent in kernel mode */ LPFILETIME kerneltime, /* [out] Time thread spent in kernel mode */
LPFILETIME usertime) /* [out] Time thread spent in user mode */ LPFILETIME usertime) /* [out] Time thread spent in user mode */
{ {
BOOL ret = TRUE; KERNEL_USER_TIMES kusrt;
NTSTATUS status;
if (creationtime || exittime) status = NtQueryInformationThread(thread, ThreadTimes, &kusrt,
sizeof(kusrt), NULL);
if (status)
{ {
/* We need to do a server call to get the creation time or exit time */ SetLastError( RtlNtStatusToDosError(status) );
/* This works on any thread */ return FALSE;
SERVER_START_REQ( get_thread_info )
{
req->handle = thread;
req->tid_in = 0;
if ((ret = !wine_server_call_err( req )))
{
if (creationtime)
RtlSecondsSince1970ToTime( reply->creation_time, (LARGE_INTEGER*)creationtime );
if (exittime)
RtlSecondsSince1970ToTime( reply->exit_time, (LARGE_INTEGER*)exittime );
}
}
SERVER_END_REQ;
} }
if (ret && (kerneltime || usertime)) if (creationtime)
{ {
/* We call times(2) for kernel time or user time */ creationtime->dwLowDateTime = kusrt.CreateTime.u.LowPart;
/* We can only (portably) do this for the current thread */ creationtime->dwHighDateTime = kusrt.CreateTime.u.HighPart;
if (thread == GetCurrentThread())
{
ULONGLONG time;
struct tms time_buf;
long clocks_per_sec = sysconf(_SC_CLK_TCK);
times(&time_buf);
if (kerneltime)
{
time = (ULONGLONG)time_buf.tms_stime * 10000000 / clocks_per_sec;
kerneltime->dwHighDateTime = time >> 32;
kerneltime->dwLowDateTime = (DWORD)time;
}
if (usertime)
{
time = (ULONGLONG)time_buf.tms_utime * 10000000 / clocks_per_sec;
usertime->dwHighDateTime = time >> 32;
usertime->dwLowDateTime = (DWORD)time;
}
}
else
{
if (kerneltime) kerneltime->dwHighDateTime = kerneltime->dwLowDateTime = 0;
if (usertime) usertime->dwHighDateTime = usertime->dwLowDateTime = 0;
FIXME("Cannot get kerneltime or usertime of other threads\n");
}
} }
return ret; if (exittime)
{
exittime->dwLowDateTime = kusrt.ExitTime.u.LowPart;
exittime->dwHighDateTime = kusrt.ExitTime.u.HighPart;
}
if (kerneltime)
{
kerneltime->dwLowDateTime = kusrt.KernelTime.u.LowPart;
kerneltime->dwHighDateTime = kusrt.KernelTime.u.HighPart;
}
if (usertime)
{
usertime->dwLowDateTime = kusrt.UserTime.u.LowPart;
usertime->dwHighDateTime = kusrt.UserTime.u.HighPart;
}
return TRUE;
} }

View File

@ -25,6 +25,9 @@
#ifdef HAVE_SYS_MMAN_H #ifdef HAVE_SYS_MMAN_H
#include <sys/mman.h> #include <sys/mman.h>
#endif #endif
#ifdef HAVE_SYS_TIMES_H
#include <sys/times.h>
#endif
#include "ntstatus.h" #include "ntstatus.h"
#include "thread.h" #include "thread.h"
@ -553,6 +556,46 @@ NTSTATUS WINAPI NtQueryInformationThread( HANDLE handle, THREADINFOCLASS class,
} }
return status; return status;
case ThreadTimes: case ThreadTimes:
{
KERNEL_USER_TIMES kusrt;
/* We need to do a server call to get the creation time or exit time */
/* This works on any thread */
SERVER_START_REQ( get_thread_info )
{
req->handle = handle;
req->tid_in = 0;
status = wine_server_call( req );
if (status == STATUS_SUCCESS)
{
RtlSecondsSince1970ToTime( reply->creation_time, &kusrt.CreateTime );
RtlSecondsSince1970ToTime( reply->exit_time, &kusrt.ExitTime );
}
}
SERVER_END_REQ;
if (status == STATUS_SUCCESS)
{
/* We call times(2) for kernel time or user time */
/* We can only (portably) do this for the current thread */
if (handle == GetCurrentThread())
{
struct tms time_buf;
long clocks_per_sec = sysconf(_SC_CLK_TCK);
times(&time_buf);
kusrt.KernelTime.QuadPart = (ULONGLONG)time_buf.tms_stime * 10000000 / clocks_per_sec;
kusrt.UserTime.QuadPart = (ULONGLONG)time_buf.tms_utime * 10000000 / clocks_per_sec;
}
else
{
kusrt.KernelTime.QuadPart = 0;
kusrt.UserTime.QuadPart = 0;
FIXME("Cannot get kerneltime or usertime of other threads\n");
}
if (data) memcpy( data, &kusrt, min( length, sizeof(kusrt) ));
if (ret_len) *ret_len = min( length, sizeof(kusrt) );
}
}
return status;
case ThreadPriority: case ThreadPriority:
case ThreadBasePriority: case ThreadBasePriority:
case ThreadAffinityMask: case ThreadAffinityMask: