一 查找固定进程的代码
DWORD ProcessHelper::FindProcessByName(const std::string& processName)//0 not found ; other found; processName "processName.exe"
-
{
-
HANDLE hProcessSnap;
-
PROCESSENTRY32 pe32;
-
hProcessSnap = CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );
-
if( hProcessSnap == INVALID_HANDLE_VALUE )
-
{
-
return( 0 );
-
}
-
pe32.dwSize = sizeof( PROCESSENTRY32 );
-
if( !Process32First( hProcessSnap, &pe32 ) )
-
{
-
CloseHandle( hProcessSnap ); // clean the snapshot object
-
return( 0 );
-
}
-
DWORD processId = 0;
-
do
-
{
-
if(std::wstring(pe32.szExeFile) == StringHelper::ANSIToUnicode(processName))//进程名称
-
{
-
processId = pe32.th32ProcessID;//进程ID
-
break;
-
}
-
} while( Process32Next( hProcessSnap, &pe32 ) );
-
CloseHandle( hProcessSnap );
-
return( processId )}
二、查找固定目录的进程(类,可以使用)
头文件如下:
#ifndef __FIND_FILE_HANDLE_H__
#define __FIND_FILE_HANDLE_H__
#include <tchar.h>
#include <windows.h>
#include <psapi.h>
#include <strsafe.h>
#include <assert.h>
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <WinIoCtl.h>
#include <Ntddscsi.h>
#include <fstream>
#include <tlhelp32.h>
#include <winternl.h>
#include <bcrypt.h>
#include <set>
#include <map>
#include "boost/filesystem.hpp"
#include "boost/lexical_cast.hpp"
#pragma comment(lib,"PSAPI.LIB")
//#pragma comment(lib,"Ntoskrnl.lib")
#pragma warning(disable:4200) //zero-sized array in struct/union
namespace FileHandleFinder
{
typedef struct _FILE_HANDLE_INFO
{
ULONG ProcessId;
std::string sProcessName;
std::string sProcessCmdLine;
std::string FilePath;
} FILE_HANDLE_INFO,*PILE_HANDLE_INFO;
void GetFileHandleInUse(const std::string& sPathInclude,const std::string& sPathExclude,
std::vector<FILE_HANDLE_INFO>& vecFileInfo);
bool KillProcess(ULONG ProcessId);
}
#endif
实现代码:
#include "FindFileHandle.h"
namespace FileHandleFinder
{/*
typedef struct _FILE_HANDLE_INFO
{
ULONG ProcessId;
std::string sProcessName;
std::string sProcessCmdLine;
std::string FilePath;
} FILE_HANDLE_INFO,*PILE_HANDLE_INFO;//*/
typedef struct _IO_STATUS_BLOCK
{
union
{
NTSTATUS Status;
PVOID Pointer;
};
ULONG_PTR Information;
} IO_STATUS_BLOCK, *PIO_STATUS_BLOCK;
typedef struct _SYSTEM_HANDLE
{
ULONG ProcessId;
UCHAR ObjectTypeNumber;
UCHAR Flags;
USHORT Handle;
PVOID Object;
ACCESS_MASK GrantedAccess;
} SYSTEM_HANDLE,*PSYSTEM_HANDLE;
typedef struct _SYSTEM_HANDLE_INFORMATION
{
ULONG NumberOfHandles;
SYSTEM_HANDLE HandleInfo[1];
}SYSTEM_HANDLE_INFORMATION,*PSYSTEM_HANDLE_INFORMATION;
typedef struct _SYSTEM_HANDLE_INFORMATION_EX
{
ULONG NumberOfHandles;
SYSTEM_HANDLE Information[655360];
}SYSTEM_HANDLE_INFORMATION_EX, *PSYSTEM_HANDLE_INFORMATION_EX;
typedef enum _SYSTEM_INFORMATION_CLASS
{
SystemBasicInformation,
SystemProcessorInformation,
SystemPerformanceInformation,
SystemTimeOfDayInformation,
SystemPathInformation,
SystemProcessInformation,
SystemCallCountInformation,
SystemDeviceInformation,
SystemProcessorPerformanceInformation,
SystemFlagsInformation,
SystemCallTimeInformation,
SystemModuleInformation,
SystemLocksInformation,
SystemStackTraceInformation,
SystemPagedPoolInformation,
SystemNonPagedPoolInformation,
SystemHandleInformation,
SystemObjectInformation,
SystemPageFileInformation,
SystemVdmInstemulInformation,
SystemVdmBopInformation,
SystemFileCacheInformation,
SystemPoolTagInformation,
SystemInterruptInformation,
SystemDpcBehaviorInformation,
SystemFullMemoryInformation,
SystemLoadGdiDriverInformation,
SystemUnloadGdiDriverInformation,
SystemTimeAdjustmentInformation,
SystemSummaryMemoryInformation,
SystemNextEventIdInformation,
SystemEventIdsInformation,
SystemCrashDumpInformation,
SystemExceptionInformation,
SystemCrashDumpStateInformation,
SystemKernelDebuggerInformation,
SystemContextSwitchInformation,
SystemRegistryQuotaInformation,
SystemExtendServiceTableInformation,
SystemPrioritySeperation,
SystemPlugPlayBusInformation,
SystemDockInformation,
SystemProcessorSpeedInformation,
SystemCurrentTimeZoneInformation,
SystemLookasideInformation,
SystemTimeSlipNotification,
SystemSessionCreate,
SystemSessionDetach,
SystemSessionInformation,
SystemRangeStartInformation,
SystemVerifierInformation,
SystemVerifierThunkExtend,
SystemSessionProcessInformation,
SystemLoadGdiDriverInSystemSpace,
SystemNumaProcessorMap,
SystemPrefetcherInformation,
SystemExtendedProcessInformation,
SystemRecommendedSharedDataAlignment,
SystemComPlusPackage,
SystemNumaAvailableMemory,
SystemProcessorPowerInformation,
SystemEmulationBasicInformation,
SystemEmulationProcessorInformation,
SystemExtendedHandleInformation,
SystemLostDelayedWriteInformation,
SystemBigPoolInformation,
SystemSessionPoolTagInformation,
SystemSessionMappedViewInformation,
SystemHotpatchInformation,
SystemObjectSecurityMode,
SystemWatchdogTimerHandler,
SystemWatchdogTimerInformation,
SystemLogicalProcessorInformation,
SystemWow64SharedInformation,
SystemRegisterFirmwareTableInformationHandler,
SystemFirmwareTableInformation,
SystemModuleInformationEx,
SystemVerifierTriageInformation,
SystemSuperfetchInformation,
SystemMemoryListInformation,
SystemFileCacheInformationEx,
MaxSystemInfoClass // MaxSystemInfoClass should always be the last enum
} SYSTEM_INFORMATION_CLASS, *PSYSTEM_INFORMATION_CLASS;
typedef enum _FILE_INFORMATION_CLASS
{
FileDirectoryInformation = 1,
FileFullDirectoryInformation,
FileBothDirectoryInformation,
FileBasicInformation,
FileStandardInformation,
FileInternalInformation,
FileEaInformation,
FileAccessInformation,
FileNameInformation,
FileRenameInformation,
FileLinkInformation,
FileNamesInformation,
FileDispositionInformation,
FilePositionInformation,
FileFullEaInformation,
FileModeInformation,
FileAlignmentInformation,
FileAllInformation,
FileAllocationInformation,
FileEndOfFileInformation,
FileAlternateNameInformation,
FileStreamInformation,
FilePipeInformation,
FilePipeLocalInformation,
FilePipeRemoteInformation,
FileMailslotQueryInformation,
FileMailslotSetInformation,
FileCompressionInformation,
FileObjectIdInformation,
FileCompletionInformation,
FileMoveClusterInformation,
FileQuotaInformation,
FileReparsePointInformation,
FileNetworkOpenInformation,
FileAttributeTagInformation,
FileTrackingInformation,
FileIdBothDirectoryInformation,
FileIdFullDirectoryInformation,
FileValidDataLengthInformation,
FileShortNameInformation,
FileIoCompletionNotificationInformation,
FileIoStatusBlockRangeInformation,
FileIoPriorityHintInformation,
FileSfioReserveInformation,
FileSfioVolumeInformation,
FileHardLinkInformation,
FileProcessIdsUsingFileInformation,
FileNormalizedNameInformation,
FileNetworkPhysicalNameInformation,
FileIdGlobalTxDirectoryInformation,
FileIsRemoteDeviceInformation,
FileAttributeCacheInformation,
FileNumaNodeInformation,
FileStandardLinkInformation,
FileRemoteProtocolInformation,
FileReplaceCompletionInformation,
FileMaximumInformation
} FILE_INFORMATION_CLASS, *PFILE_INFORMATION_CLASS;
typedef struct _FILE_NAME_INFORMATION
{
ULONG FileNameLength;
WCHAR FileName[1];
} FILE_NAME_INFORMATION, *PFILE_NAME_INFORMATION;
typedef enum _OBJECT_INFORMATION_CLASS
{
ObjectBasicInformation,
ObjectNameInformation,
ObjectTypeInformation,
ObjectAllInformation,
ObjectDataInformation
} OBJECT_INFORMATION_CLASS, *POBJECT_INFORMATION_CLASS;
typedef struct _LSA_UNICODE_STRING
{
USHORT Length;
USHORT MaximumLength;
PWSTR Buffer;
}LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING;
typedef struct _OBJECT_NAME_INFORMATION
{
UNICODE_STRING Name;
WCHAR NameBuffer[0];
} OBJECT_NAME_INFORMATION, *POBJECT_NAME_INFORMATION;
typedef long(__stdcall*PNtQueryObject)(HANDLE ObjectHandle,ULONG ObjectInformationClass,PVOID ObjectInformation,ULONG ObjectInformationLength,PULONG ReturnLength);
//声明Native API函数
typedef NTSTATUS (WINAPI *NTQUERYSYSTEMINFOMATION)(
IN SYSTEM_INFORMATION_CLASS SystemClass,
OUT LPVOID SystemInfo,
IN ULONG SystemInfoLength,
OUT PULONG ReturnLength
);
typedef NTSTATUS (WINAPI *NtQueryInformationProcessFake)(HANDLE, DWORD, PVOID, ULONG, PULONG);
HANDLE hCopy=0;
ULONG lCurPID=0;
std::string sFilterInclude("");
std::string sFilterExclude("");
std::vector<FILE_HANDLE_INFO> vecFileHandleInfo;
std::string sRoot("");
const CHAR OBJECT_FILE_HANDLE = 0x1c;//文件句柄
const ULONG SYSTEM_PID = 4;//系统进程
#define STR_NTDLL _T("Ntdll.dll")
DWORD WINAPI GetFileName(LPVOID p )
{
int* ProcessId = (int*)p;
HMODULE hNtDll = LoadLibrary(STR_NTDLL);
if(hNtDll == NULL)
{
return 0;
}
PNtQueryObject NtQueryObject=(PNtQueryObject)GetProcAddress(hNtDll,"NtQueryObject");
POBJECT_NAME_INFORMATION pObject=NULL;
pObject=(POBJECT_NAME_INFORMATION)HeapAlloc(GetProcessHeap(),0,MAX_PATH*2);
memset(pObject,0,MAX_PATH*2);
ULONG returnLength;
DWORD dwReturn = NtQueryObject(hCopy,ObjectNameInformation,pObject,MAX_PATH*2,&returnLength);
//将卷路径名修改成盘符路径
if((pObject->NameBuffer!=NULL)&&(dwReturn==0))
{
DWORD n = WideCharToMultiByte(CP_OEMCP,NULL,pObject->NameBuffer,-1,NULL,0,NULL,FALSE);
char* name = new char[n + 1];
memset(name,0,n + 1);
WideCharToMultiByte(CP_OEMCP,NULL,pObject->NameBuffer,-1,name,n,NULL,FALSE);
std::string sFilePath(name);
std::transform(sFilePath.begin(), sFilePath.end(), sFilePath.begin(), ::tolower);
if (std::string::npos != sFilePath.find(sFilterInclude) &&
std::string::npos == sFilePath.find(sFilterExclude))
{
FILE_HANDLE_INFO fhi = {*ProcessId,"","",name};
vecFileHandleInfo.push_back(fhi);
}
delete[] name;
}
HeapFree(GetProcessHeap(),0,pObject);
return dwReturn;
}
//根据进程ID获取当前进程所使用的所有文件的句柄
void EnumFileHandle()
{
HMODULE hNtDll = LoadLibrary(STR_NTDLL);
if(hNtDll == NULL)
{
return;
}
//开始获取,其他API地址
NTQUERYSYSTEMINFOMATION NtQuerySystemInformation = (NTQUERYSYSTEMINFOMATION)
GetProcAddress(hNtDll,"NtQuerySystemInformation");
if(NtQuerySystemInformation == NULL)
{
return;
}
//开始为我们需要信息开辟内存
DWORD nSize = 4096,nReturn = 0;
PSYSTEM_HANDLE_INFORMATION pHandleInfo=(PSYSTEM_HANDLE_INFORMATION)
HeapAlloc(GetProcessHeap(),0,nSize);
while(NtQuerySystemInformation(SystemHandleInformation,pHandleInfo,nSize,&nReturn) == 0xc0000004)
{
HeapFree(GetProcessHeap(),0,pHandleInfo);
nSize += 4096;
pHandleInfo = (PSYSTEM_HANDLE_INFORMATION)HeapAlloc(GetProcessHeap(),0,nSize);
}
//开辟成功,然后打开指定的进程
for(ULONG i = 0; i < pHandleInfo->NumberOfHandles; i++)
{
PSYSTEM_HANDLE pHandle = (PSYSTEM_HANDLE)&(pHandleInfo->HandleInfo[i]);
if((pHandle->ObjectTypeNumber == OBJECT_FILE_HANDLE)
&&(pHandle->ProcessId != SYSTEM_PID))
{
//如果是当前进程的某个文件,这说明,该进程下有文件操作
HANDLE hProcess = OpenProcess(PROCESS_DUP_HANDLE|PROCESS_QUERY_INFORMATION|PROCESS_VM_READ,FALSE,
pHandle->ProcessId);
if(hProcess == NULL)
{
//int a = GetLastError();
continue;
}
if(!DuplicateHandle(hProcess,(HANDLE)pHandle->Handle,GetCurrentProcess(),
&hCopy,MAXIMUM_ALLOWED,FALSE,0))
{
continue;
}
lCurPID = pHandle->ProcessId;
HANDLE hThread = CreateThread(NULL,0,GetFileName,(LPVOID)&lCurPID,0,NULL);
if(WaitForSingleObject(hThread,100) == WAIT_TIMEOUT)
{
TerminateThread(hThread,0);
}
CloseHandle(hThread);
CloseHandle(hCopy);
hCopy = 0;
CloseHandle(hProcess);
hProcess = 0;
}
}
HeapFree(GetProcessHeap(),0,pHandleInfo);
}
bool EnableDebugPrivilege()
{
HANDLE hToken;
LUID sedebugnameValue;
TOKEN_PRIVILEGES tkp;
if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken))
{
return FALSE;
}
if (!LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &sedebugnameValue))
{
CloseHandle(hToken);
return false;
}
tkp.PrivilegeCount = 1;
tkp.Privileges[0].Luid = sedebugnameValue;
tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
if (!AdjustTokenPrivileges(hToken, FALSE, &tkp, sizeof(tkp), NULL, NULL))
{
CloseHandle(hToken);
return false;
}
return true;
}
/******************************************************************************
* Function: get disk's physical number from its drive letter
* e.g. C-->0 (C: is on disk0)
* input: letter, drive letter
* output: N/A
* return: Succeed, disk number
* Fail, -1
******************************************************************************/
int WINAPI GetDrivePartitionNumber(char letter)
{
int iRet = 0;
HANDLE hDevice = INVALID_HANDLE_VALUE;
do
{
char devName[16] = {0};
char drive[4] = {0};
sprintf(drive, "%c:\\", letter);
sprintf(devName, "\\\\?\\%c:", letter);
hDevice = CreateFileA(devName,
GENERIC_READ,
FILE_SHARE_READ | FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
NULL,
NULL);
if(INVALID_HANDLE_VALUE == hDevice)
{
break;
}
if(DRIVE_REMOVABLE == GetDriveTypeA(drive))
{
break;
}
DWORD returned = 0;
PARTITION_INFORMATION pi = {0};
if(!DeviceIoControl(hDevice,
IOCTL_DISK_GET_PARTITION_INFO,
NULL,
0,
&pi,
sizeof(pi),
&returned,
NULL))
{
break;
}
iRet = pi.PartitionNumber;
} while (FALSE);
if(INVALID_HANDLE_VALUE != hDevice)
{
::CloseHandle(hDevice);
}
return iRet;
}
bool GetProcessCmdLine(unsigned long ulPID,std::string& sCmdLine)
{
sCmdLine.clear();
HANDLE hproc = ::OpenProcess(PROCESS_ALL_ACCESS, FALSE, ulPID);
if (INVALID_HANDLE_VALUE != hproc)
{
HANDLE hnewdup = NULL;
PEB peb;
RTL_USER_PROCESS_PARAMETERS upps;
HMODULE hm = LoadLibrary(STR_NTDLL);
NtQueryInformationProcessFake ntQ ;
ntQ = (NtQueryInformationProcessFake)GetProcAddress(hm, "NtQueryInformationProcess");
if ( DuplicateHandle(GetCurrentProcess(), hproc, GetCurrentProcess(), &hnewdup, 0, FALSE, DUPLICATE_SAME_ACCESS) )
{
PROCESS_BASIC_INFORMATION pbi;
NTSTATUS isok = ntQ(hnewdup, 0,(PVOID)&pbi, sizeof(PROCESS_BASIC_INFORMATION),0);
if (BCRYPT_SUCCESS(isok))
{
if (ReadProcessMemory(hnewdup, pbi.PebBaseAddress, &peb, sizeof(PEB), 0))
{
if (ReadProcessMemory(hnewdup, peb.ProcessParameters, &upps, sizeof(RTL_USER_PROCESS_PARAMETERS), 0))
{
WCHAR *buffer = new WCHAR[upps.CommandLine.Length + 1];
ZeroMemory(buffer, (upps.CommandLine.Length + 1) * sizeof(WCHAR));
ReadProcessMemory(hnewdup, upps.CommandLine.Buffer, buffer, upps.CommandLine.Length, 0);
char* output = new char[upps.CommandLine.Length + 1];
sprintf_s(output,upps.CommandLine.Length, "%ws", buffer);
sCmdLine = std::string(output);
::CloseHandle(hnewdup);
::CloseHandle(hproc);
delete output;
delete buffer;
return true;
}
}
}
::CloseHandle(hnewdup);
}
::CloseHandle(hproc);
}
return false;
}
bool GetPrcocessInfoByPID(FILE_HANDLE_INFO& PrcoInfo)
{
std::string sCmdLine;
HANDLE hSnapshot = ::CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
if (INVALID_HANDLE_VALUE == hSnapshot)
{
return false;
}
PROCESSENTRY32 pe = { sizeof(pe) };
char output[MAX_PATH];
for (BOOL fOk = ::Process32First(hSnapshot, &pe); fOk; fOk = ::Process32Next(hSnapshot, &pe))
{
if (pe.th32ProcessID == PrcoInfo.ProcessId)
{
#ifdef UNICODE
sprintf_s(output, sizeof(output),"%ws", pe.szExeFile);
#else
sprintf_s(output, sizeof(output),"%s", pe.szExeFile);
#endif
GetProcessCmdLine(pe.th32ProcessID,sCmdLine);
PrcoInfo.sProcessName = std::string(output);
PrcoInfo.sProcessCmdLine = sCmdLine;
}
}
::CloseHandle(hSnapshot);
return true;
}
bool GetAllPID(std::map<unsigned long,std::string>& mapPNamePID)
{
HANDLE hSnapshot = ::CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
if (INVALID_HANDLE_VALUE == hSnapshot)
{
return false;
}
PROCESSENTRY32 pe = { sizeof(pe) };
for (BOOL fOk = ::Process32First(hSnapshot, &pe); fOk; fOk = ::Process32Next(hSnapshot, &pe))
{
char output[MAX_PATH];
#ifdef UNICODE
sprintf_s(output, sizeof(output),"%ws", pe.szExeFile);
#else
sprintf_s(output, sizeof(output),"%s", pe.szExeFile);
#endif
mapPNamePID.insert(std::pair<unsigned long,std::string>(pe.th32ProcessID,std::string(output)));
}
::CloseHandle(hSnapshot);
return mapPNamePID.size() > 0 ? true : false;
}
std::string ConvertPath(const std::string sPath)
{
std::string sAfterConvert = sPath;
boost::filesystem::path p(sPath);
sRoot = p.root_path().string();
if (sRoot.find("\\") == std::string::npos)
{
sRoot.append("\\");
}
int iD = GetDrivePartitionNumber(*sRoot.c_str());
std::string sRootR = "\\Device\\HarddiskVolume" + boost::lexical_cast<std::string>(iD);
sAfterConvert.replace(0,2,sRootR);
std::transform(sAfterConvert.begin(), sAfterConvert.end(), sAfterConvert.begin(), ::tolower);
return sAfterConvert;
}
std::string DeConvertPath(const std::string sPath)
{
std::string sp("\\Device\\HarddiskVolume");
std::string sAfterConvert = sPath;
sAfterConvert.replace(0,sp.size()+2,sRoot);
return sAfterConvert;
}
void GetFileHandleInUse(const std::string& sPathInclude,const std::string& sPathExclude,
std::vector<FILE_HANDLE_INFO>& vecFileInfo)
{
vecFileInfo.clear();
vecFileHandleInfo.clear();
std::map<unsigned long,std::string> mapPNamePID;
GetAllPID( mapPNamePID);
std::map<unsigned long,std::string>::iterator itrMap = mapPNamePID.begin();
for (; itrMap != mapPNamePID.end(); ++itrMap)
{
FILE_HANDLE_INFO fi;
fi.ProcessId = itrMap->first;
GetPrcocessInfoByPID(fi);
if (sPathInclude.size() != 0 && std::string::npos != fi.sProcessCmdLine.find(sPathInclude))
{
vecFileInfo.push_back(fi);
}
}
sFilterInclude = ConvertPath(sPathInclude);
sFilterExclude = "???";
if (sPathExclude.size() != 0)
{
sFilterExclude = ConvertPath(sPathExclude);
}
EnableDebugPrivilege();
EnumFileHandle();
std::vector<FILE_HANDLE_INFO>::iterator itr = vecFileHandleInfo.begin();
for (; itr != vecFileHandleInfo.end(); ++itr)
{
itr->FilePath = DeConvertPath(itr->FilePath);
GetPrcocessInfoByPID(*itr);
vecFileInfo.push_back(*itr);
}
}
//通过进程ID来终止杀死进程
bool KillProcess(ULONG ProcessId)
{
HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS,TRUE,ProcessId);
if(hProcess == NULL)
{
return false;
}
if(!TerminateProcess(hProcess,0))
{
return false;
}
return true;
}
}
使用实例:
std::vector<FileHandleFinder::FILE_HANDLE_INFO> vecFileInfo;
FileHandleFinder::GetFileHandleInUse(D_UIH,D_UIH_LOG,vecFileInfo);
std::vector<FileHandleFinder::FILE_HANDLE_INFO>::iterator itr = vecFileHandleInfo.begin();
for (; itr != vecFileHandleInfo.end(); ++itr)
{ setPID.insert(itr->ProcessId); }
std::set<ULONG>::iterator itrPid = setPID.begin();
for (; itrPid != setPID.end(); ++itrPid)
{ std::string sRet = FileHandleFinder::KillProcess(*itrPid) ? "Successful" : "Failed"; }
以上的代码经过测试可以直接使用。