在项目开发中,有时会需要判断某个程序是否已经运行,一般是通过程序与程序间建立IPC通讯,则能准确的获取想要的信息。但是如果仅仅只是判断某程序时否正在运行,专门修改两个程序的代码建立进程通信就小题大做了。 一般,操作系统都会记录每个进程运行信息,我们只需要调用响应的接口,从操作系统拿到这些信息就可以判断程序是否运行了。
在Windows中,一般调用程序快照API,来获取某时刻系统正在运行的程序信息,遍历比较进程名,判断程序是否正在运行,判断程序是否运行代码如下:
bool Widget::isProgramRunning(QString program_name)
{
bool ret = false;
HANDLE info_handle = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); //拍摄系统中所有进程的快照
if(info_handle == INVALID_HANDLE_VALUE)
{
printf("CreateToolhelp32Snapshot fail!!\n\n");
return false;
}
PROCESSENTRY32W program_info;
program_info.dwSize = sizeof(PROCESSENTRY32W); //设置结构体大小
int bResult = Process32FirstW(info_handle, &program_info); //获取所有进程中第一个进程的信息
if(!bResult)
{
printf("Process32FirstW fail!!\n\n");
return false;
}
while (bResult)
{
char *pro_name = Wchar2char(program_info.szExeFile);
if(program_name == QString(pro_name))
{
ret = true;
break;
}
//获得下一个进程的进程信息
bResult = Process32Next(info_handle, &program_info);
}
CloseHandle(info_handle);//关闭句柄
return ret;
}
注意API拿到的进程名是宽字节的字符串,需要将其转换为单字节字符串再进行程序名称比较,常用转换函数如下所示:
char *Widget::Wchar2char(const wchar_t *szStr)
{
int nLen = WideCharToMultiByte( CP_ACP, 0, szStr, -1, NULL, 0, NULL, NULL );
if (nLen == 0)
{
return NULL;
}
char* pResult = new char[nLen];
WideCharToMultiByte( CP_ACP, 0, szStr, -1, pResult, nLen, NULL, NULL );
return pResult;
}
如下为QT判断windows中某程序是否在运行的程序示例:
示例代码下载: https://download.csdn.net/download/fangye945a/12467660
在linux(类unix)中判断进程是否在运行,通常通过shell命令就能快速判断,比如(ps | grep usr/bin/wave),如果wave程序正在运行就会有结果输出,否则无结果输出。 在C/C++程序中,我们通常利用system()函数调用shell命令,但其只能执行命令而无法获取执行结果。
若想获取系统调用命令的执行结果,其实只需使用popen函数即可,其功能类似于system与fopen函数的结合,打开程序后,read其执行结果即可。(注意:调用的命令如果结果返回较慢,需要做延时再进行结果读取)。
如下为qnx中判断某程序是否正在运行的示例函数:
int isWaveRunning()
{
FILE* fp = NULL;
int ret = -1;
char buff[64]={0};
char command[]= "pidin | grep usr/bin/wave"; //linux中命令为: ps | grep usr/bin/wave
if((fp = popen(command,"r")) == NULL)
{
printf("popen [%s] fail\n\n",command);
return ret;
}
int rc = fread(buff,1,sizeof(buff),fp);
if(rc > 0)
{
printf("----fread: %s\n",buff);
ret = 0;
}
else
{
printf("----fread no data.\n");
}
pclose(fp);
return ret;
}