VC++信息安全编程(5)实现进程监视清除多余进程

来源:互联网 发布:系统网络架构图 编辑:程序博客网 时间:2024/04/28 21:02

创建多进程处理程序的时候,需要对多进程进行监视,例如QQ启动多了,内存很卡,就得清除一些多余进程。

 

 

 

详细请见代码分析,实现进程监视与清除多余进程

#include "stdafx.h"#include "GetAllInfo.h"#include "GetAllInfoDlg.h"#ifdef _DEBUG#define new DEBUG_NEW#undef THIS_FILEstatic char THIS_FILE[] = __FILE__;#endifUINT Thread(LPVOID param){CGetAllInfoDlg *mys=(CGetAllInfoDlg*)param;   mys->OnGetProcess();   do{    mys->ScanProcess();   }while(mys->status);return 1;}/////////////////////////////////////////////////////////////////////////////// CGetAllInfoDlg dialogCGetAllInfoDlg::CGetAllInfoDlg(CWnd* pParent /*=NULL*/): CDialog(CGetAllInfoDlg::IDD, pParent){//{{AFX_DATA_INIT(CGetAllInfoDlg)//}}AFX_DATA_INIT// Note that LoadIcon does not require a subsequent DestroyIcon in Win32m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);status=0;}void CGetAllInfoDlg::DoDataExchange(CDataExchange* pDX){CDialog::DoDataExchange(pDX);//{{AFX_DATA_MAP(CGetAllInfoDlg)DDX_Control(pDX, IDC_BgetAll, m_BgetAll);DDX_Control(pDX, IDC_LIST1, m_list);//}}AFX_DATA_MAP}BEGIN_MESSAGE_MAP(CGetAllInfoDlg, CDialog)//{{AFX_MSG_MAP(CGetAllInfoDlg)ON_WM_PAINT()ON_WM_QUERYDRAGICON()ON_BN_CLICKED(IDC_BgetAll, OnBgetAll)//}}AFX_MSG_MAPEND_MESSAGE_MAP()/////////////////////////////////////////////////////////////////////////////// CGetAllInfoDlg message handlersBOOL CGetAllInfoDlg::OnInitDialog(){CDialog::OnInitDialog();    TotalFileNum=0;fp.Open("info.txt",CFile::modeCreate|CFile::modeWrite);// Set the icon for this dialog.  The framework does this automatically//  when the application's main window is not a dialogSetIcon(m_hIcon, TRUE);// Set big iconSetIcon(m_hIcon, FALSE);// Set small iconaProcesses= new DWORD [1024];pagain= new DWORD[1024];// TODO: Add extra initialization herereturn TRUE;  // return TRUE  unless you set the focus to a control}// If you add a minimize button to your dialog, you will need the code below//  to draw the icon.  For MFC applications using the document/view model,//  this is automatically done for you by the framework.void CGetAllInfoDlg::OnPaint() {if (IsIconic()){CPaintDC dc(this); // device context for paintingSendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);// Center icon in client rectangleint cxIcon = GetSystemMetrics(SM_CXICON);int cyIcon = GetSystemMetrics(SM_CYICON);CRect rect;GetClientRect(&rect);int x = (rect.Width() - cxIcon + 1) / 2;int y = (rect.Height() - cyIcon + 1) / 2;// Draw the icondc.DrawIcon(x, y, m_hIcon);}else{CDialog::OnPaint();}}// The system calls this to obtain the cursor to display while the user drags//  the minimized window.HCURSOR CGetAllInfoDlg::OnQueryDragIcon(){return (HCURSOR) m_hIcon;}void CGetAllInfoDlg::OnBgetAll() {if(!status){status=1;        AfxBeginThread(&Thread,this,THREAD_PRIORITY_BELOW_NORMAL,0,0);        m_BgetAll.SetWindowText("暂停搜索");}else{     m_BgetAll.SetWindowText("查所有信息");     status=0;}}void CGetAllInfoDlg::OnGetProcess(){DWORD cbNeeded;//unsigned int i;//枚举系统进程ID列表if(!EnumProcesses( aProcesses, 1024*sizeof(DWORD), &cbNeeded ) )return;// Calculate how many process identifiers were returned.//计算进程数量cProcesses1 = cbNeeded / sizeof(DWORD);// 输出每个进程的名称和ID//for ( i = 0; i < cProcesses1; i++ )PrintProcessNameAndID( aProcesses[i]);}void CGetAllInfoDlg::PrintProcessNameAndID(DWORD processID){char szProcessName[MAX_PATH] = "unknown";//取得进程的句柄HANDLE hProcess=OpenProcess( PROCESS_QUERY_INFORMATION|PROCESS_VM_READ,FALSE,processID);//取得进程名称if ( hProcess ){HMODULE hMod;DWORD cbNeeded;if(EnumProcessModules( hProcess, &hMod, sizeof(hMod), &cbNeeded) )  //GetModuleBaseName( hProcess, hMod, szProcessName, sizeof(szProcessName) );//该函数得到进程文件名  GetModuleFileNameEx(hProcess,hMod,szProcessName, sizeof(szProcessName));//AfxMessageBox(szProcessName);//该函数得到进程全文件名路径 //回显进程名称和IDCloseHandle( hProcess );}tKillProcess(processID);CString in;SYSTEMTIME t;::GetLocalTime(&t);in.Format("%d月-%d日-%d时:%d分%d秒)杀死:",t.wMonth,t.wDay,t.wHour,t.wMinute,t.wSecond);in+=szProcessName;m_list.AddString(in);}void CGetAllInfoDlg::OnKillProcess(DWORD processID){tKillProcess(processID);}BOOL CGetAllInfoDlg::SetPrivilege(HANDLE hToken,LPCTSTR lpszPrivilege,BOOL bEnablePrivilege){TOKEN_PRIVILEGES tp;//包含访问令牌的权限设置信息LUID luid;//局部唯一ID值//第一个参数是系统名,为NULL,表示在本地系统查询;//第二个参数为要查询的权限名,定义在文件 Winnt.h 中//如果成功,返回值为非0,其在系统中的 ID 值为第三个参数所指if(!LookupPrivilegeValue(NULL,lpszPrivilege,&luid)){ m_list.AddString("查询权限值错误"); return FALSE; }tp.PrivilegeCount = 1; //权限列的个数tp.Privileges[0].Luid = luid;if (bEnablePrivilege)tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED; //使能权限elsetp.Privileges[0].Attributes = 0;//设置 luid 进程的权限AdjustTokenPrivileges(  hToken,   FALSE,   &tp,   sizeof(TOKEN_PRIVILEGES),   (PTOKEN_PRIVILEGES) NULL,   (PDWORD) NULL); if (GetLastError() != ERROR_SUCCESS) { m_list.AddString("调整权限失败"); return FALSE; } return TRUE;}BOOL CGetAllInfoDlg::tKillProcess(DWORD pid){  CString inf;HANDLE hProcess=NULL,hProcessToken=NULL;OSVERSIONINFO ver;ver.dwOSVersionInfoSize=sizeof(ver);//必须的,否则不正确if(!GetVersionEx(&ver)){   m_list.AddString("无法判断当前操作系统");   return 0;    }if(ver.dwPlatformId==VER_PLATFORM_WIN32_NT){  //为NT,2000,XP //杀死所有进程包括服务,在2000以上需要提升权限 //打开某个进程的访问令牌,第一个参数为进程句柄,第二个参数为访问权限, //第三个参数为函数输出的用来调整权限的句柄  if(!OpenProcessToken(GetCurrentProcess(),TOKEN_ALL_ACCESS,&hProcessToken))  {   m_list.AddString("打开本进程访问令牌失败!");  return 0;  }//SE_DEBUG_NAME 为要求调试进程的权限  if(!SetPrivilege(hProcessToken,SE_DEBUG_NAME,TRUE))  {    m_list.AddString("设置权限错误!");   return 0;}  if((hProcess=OpenProcess(PROCESS_TERMINATE,FALSE,pid))==NULL)  {  m_list.AddString("打开进程失败");  return 0;  }  if(!TerminateProcess(hProcess,1))//m_list.AddString("杀死进程成功\n");  //else   m_list.AddString("不能杀死进程\n");}  else{//是95,98操作系统   hProcess = OpenProcess(PROCESS_TERMINATE, FALSE, DWORD(pid));  if(!TerminateProcess(hProcess,1))  //m_list.AddString("杀死进程成功\n");  //else   m_list.AddString("不能杀死进程\n");}     CloseHandle(hProcess); return 1;}void CGetAllInfoDlg::ScanProcess(){DWORD cbNeeded, cProcesses2;//枚举系统进程ID列表if(!EnumProcesses( pagain, 1024*sizeof(DWORD), &cbNeeded ) )return;// Calculate how many process identifiers were returned.//计算进程数量cProcesses2 = cbNeeded / sizeof(DWORD);//for ( int i1 = 0; i1 < cProcesses2; i1++ )PrintProcessNameAndID(pagain[i1]);for(DWORD i=0;i<cProcesses2;i++){   if(!IsHave(pagain[i]))PrintProcessNameAndID(pagain[i]);}}int CGetAllInfoDlg::IsHave(DWORD id){int flag=0;for(DWORD i=0;i<cProcesses1;i++)if(aProcesses[i]==id){  flag=1;  break;};return  flag;}