NtQuerySystemInformation属于未公开的函数,没有文档化,头文件中也不存在(winternl.h中有其及其部分数据结构的定义),该函数可以查询到非常大量的系统信息。这里来使用该函数来查询进程名和对应PID。
其在ntdll.dll中有导出
该代码摘自网络,我对其做了大量的修改,废弃掉了大部分不需要的内容并完善了程序, 其本来的用意是查询特定进程下的特定线程状态,我保留了原程序功能的核心代码仅将其注释掉。
#include <windows.h>
#include <tchar.h>
#include <stdio.h>
#define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0)
#define STATUS_SUCCESS ((NTSTATUS) 0x00000000)
#define SystemProcessInformation 5 // 功能号
#define NTAPI __stdcall
//typedef enum _KWAIT_REASON
//{
// Executive,
// FreePage,
// PageIn,
// PoolAllocation,
// DelayExecution,
// Suspended,
// UserRequest,
// WrExecutive,
// WrFreePage,
// WrPageIn,
// WrPoolAllocation,
// WrDelayExecution,
// WrSuspended,
// WrUserRequest,
// WrEventPair,
// WrQueue,
// WrLpcReceive,
// WrLpcReply,
// WrVirtualMemory,
// WrPageOut,
// WrRendezvous,
// Spare2,
// Spare3,
// Spare4,
// Spare5,
// Spare6,
// WrKernel,
// MaximumWaitReason
//}KWAIT_REASON;
//typedef struct _SYSTEM_THREAD_INFORMATION
//{
// LARGE_INTEGER KernelTime;
// LARGE_INTEGER UserTime;
// LARGE_INTEGER CreateTime;
// ULONG WaitTime;
// PVOID StartAddress;
// CLIENT_ID ClientId;
// KPRIORITY Priority;
// KPRIORITY BasePriority;
// ULONG ContextSwitchCount;
// LONG State;// 状态,是THREAD_STATE枚举类型中的一个值
// LONG WaitReason;//等待原因, KWAIT_REASON中的一个值
//} SYSTEM_THREAD_INFORMATION, * PSYSTEM_THREAD_INFORMATION;
// 线程状态的枚举常量
//typedef enum _THREAD_STATE
//{
// StateInitialized, // 初始化状态
// StateReady, // 准备状态
// StateRunning, // 运行状态
// StateStandby, //
// StateTerminated,//关闭
// StateWait, // 等待
// StateTransition, // 切换
// StateUnknown
//}THREAD_STATE;
typedef struct _UNICODE_STRING
{
USHORT Length;
USHORT MaximumLength;
PWSTR Buffer;
} UNICODE_STRING, * PUNICODE_STRING;
typedef LONG NTSTATUS;
typedef LONG KPRIORITY;
typedef struct _CLIENT_ID
{
DWORD UniqueProcess;
DWORD UniqueThread;
} CLIENT_ID, * PCLIENT_ID;
typedef struct _VM_COUNTERS
{
SIZE_T PeakVirtualSize;
SIZE_T VirtualSize;
ULONG PageFaultCount;
SIZE_T PeakWorkingSetSize;
SIZE_T WorkingSetSize;
SIZE_T QuotaPeakPagedPoolUsage;
SIZE_T QuotaPagedPoolUsage;
SIZE_T QuotaPeakNonPagedPoolUsage;
SIZE_T QuotaNonPagedPoolUsage;
SIZE_T PagefileUsage;
SIZE_T PeakPagefileUsage;
} VM_COUNTERS;
typedef struct _SYSTEM_PROCESS_INFORMATION
{
ULONG NextEntryDelta; // 指向下一个结构体的指针
ULONG ThreadCount; // 本进程的总线程数
ULONG Reserved1[6]; // 保留
LARGE_INTEGER CreateTime; // 进程的创建时间
LARGE_INTEGER UserTime; // 在用户层的使用时间
LARGE_INTEGER KernelTime; // 在内核层的使用时间
UNICODE_STRING ProcessName; // 进程名
KPRIORITY BasePriority; //
ULONG ProcessId; // 进程ID
ULONG InheritedFromProcessId;
ULONG HandleCount; // 进程的句柄总数
ULONG Reserved2[2]; // 保留
VM_COUNTERS VmCounters;
IO_COUNTERS IoCounters;
//SYSTEM_THREAD_INFORMATION Threads[5]; // 子线程信息数组
}SYSTEM_PROCESS_INFORMATION, * PSYSTEM_PROCESS_INFORMATION;
typedef DWORD(WINAPI* NTQUERYSYSTEMINFORMATION)(UINT, PVOID, DWORD, PDWORD);
VOID EnumProcesses()
{
int nRet = 0;
NTSTATUS status = STATUS_SUCCESS;
DWORD dwSize = 0xFFFFF;
NTQUERYSYSTEMINFORMATION NtQuerySystemInformation = NULL;
PSYSTEM_PROCESS_INFORMATION pInfo = { 0 };
LPTSTR pBuf = NULL;
NtQuerySystemInformation = (NTQUERYSYSTEMINFORMATION)GetProcAddress(
LoadLibrary("ntdll.dll"),
"NtQuerySystemInformation"
);
do
{
pBuf = new TCHAR[dwSize];
if (NULL == pBuf)
{
break;
}
pInfo = (PSYSTEM_PROCESS_INFORMATION)pBuf;
status = NtQuerySystemInformation(
SystemProcessInformation,
pInfo,
dwSize,
&dwSize
);
if (!NT_SUCCESS(status)) {/*如果函数执行失败*/
break;
}
// 遍历结构体,找到对应的进程
while (pInfo->NextEntryDelta) {
if (0 != pInfo->ProcessId)
{
_tprintf(TEXT("进程名: %wZ, PID: %d\n"), &(pInfo->ProcessName), pInfo->ProcessId);
}
//// 这段代码用于查询对应线程是否挂起
//if (pInfo->ProcessId == dwProcessID) {
// // 找到该进程下的对应的线程,也就是遍历所有线程
// for (DWORD i = 0; i < pInfo->ThreadCount; i++) {
// if (pInfo->Threads[i].ClientId.UniqueThread == dwThreadID) { //找到线程
// //如果线程被挂起
// if (pInfo->Threads[i].State == StateWait
// && pInfo->Threads[i].WaitReason == Suspended) {
// nRet = 1;
// break;
// }
// }
// }
// break;
//}
pInfo = (PSYSTEM_PROCESS_INFORMATION)(((PUCHAR)pInfo) + pInfo->NextEntryDelta);
}
} while (0);
if (NULL != pBuf)
{
delete[] pBuf;
pBuf = NULL;
}
}
int _tmain()
{
EnumProcesses();
system("pause");
return(0);
}
//BOOL IsThreadAlive(DWORD dwThreadID)
//{
// BOOL bRet = FALSE;
// DWORD ExitCode = 0;
//
// HANDLE hThread = OpenThread(THREAD_QUERY_INFORMATION, FALSE, dwThreadID);
// if (hThread != NULL) {
// if (GetExitCodeThread(hThread, &ExitCode)) {
// if (ExitCode == STILL_ACTIVE)
// bRet = TRUE;
// }
// CloseHandle(hThread);
// }
// return bRet;
//}
下面给出运行效果:
(完)