将技术做到极致...
分类: LINUX
2014-08-21 15:51:08
前言
在工作中经常遇到:解析linux下某条命令的执行结果。针对该问题,我们往往是通过system()标准C函数执行某条系统命令,然后把命令执行的结果重定向到某个文件中,再对这个文件进行解析。这样处理的方法比较麻烦,每次都要调用一大堆文件操作相关的系统函数。下面我对该问题,我的处理方法进行介绍,仅供参考!!!
系统函数改装
char SpecialChars[]=";|,>`*\"'!#[]()=*^$′{}"; //对一些命令特殊字符进行筛选
/**
获取系统命令执行返回结果
pCmd 要执行的命令串
pResult 命令串返回的结果(如果不关心执行结果传NULL)
nSize 结果缓冲区大小(sizeof(pResult),如果不关心返回结果传任意值)
返回system()执行的返回值
*/
int do_system(const char* pCmd, char* pResult, int nSize)
{
int fd[2];
int ret = -1;
char *p;
if(pCmd==NULL)
return -1;
p=strpbrk(pCmd, SpecialChars);
if(p!=NULL)
return -1;
if(pResult==NULL)
return system(pCmd);
if(pipe(fd)) {
printf("pipe error!\n");
return -1;
}
fflush(stdout);
//hide stdout
int bak_fd = dup(STDOUT_FILENO);
int new_fd = dup2(fd[1], STDOUT_FILENO);
//the output of `pCmd` writes into fd[1]
ret=system(pCmd);
fprintf(stdout, "B"); //write a byte to prevent read() block when `pCmd` block
fflush(stdout);
memset(pResult, 0, nSize);
read(fd[0], pResult, nSize-1);
pResult[strlen(pResult)-1] = 0;
if(strlen(pResult)) {
pResult[strlen(pResult)-1] = 0;
}
//resume stdout
dup2(bak_fd, new_fd);
//close pipe fd
close(fd[0]);
close(fd[1]);
fflush(stdout);
return ret;
}
举例
char cmd[256] = {0},retbuf[1024] = {0};
sprintf(cmd,"ifconfig eth0");
do_system(cmd,retbuf,sizeof(retbuf));
/*返回的retbuf就是命令执行的结果,我们只要解析这个buf就可以了*/
printf("cmd=[%s],retbuf=[%s]\n",cmd,retbuf);