[转]【C/C++】Linux下使用system()函数一定要谨慎
|
1
2
|
#include <stdlib.h>int system(const char *command); |
system() executes a command specified in command by calling /bin/sh -c command, and returns after the command has been completed. During execution of the command, SIGCHLD will be blocked, and SIGINT and SIGQUIT will be ignored.
int system(const char * cmdstring)
{
pid_t pid;
int status; if(cmdstring == NULL)
{
return (1); //如果cmdstring为空,返回非零值,一般为1
} if((pid = fork())<0)
{
status = -1; //fork失败,返回-1
}
else if(pid == 0)
{
execl("/bin/sh", "sh", "-c", cmdstring, (char *)0);
_exit(127); // exec执行失败返回127,注意exec只在失败时才返回现在的进程,成功的话现在的进程就不存在啦~~
}
else //父进程
{
while(waitpid(pid, &status, 0) < 0)
{
if(errno != EINTR)
{
status = -1; //如果waitpid被信号中断,则返回-1
break;
}
}
} return status; //如果waitpid成功,则返回子进程的返回状态
}
int status;
if(NULL == cmdstring) //如果cmdstring为空趁早闪退吧,尽管system()函数也能处理空指针
{
return XXX;
}
status = system(cmdstring);
if(status < 0)
{
printf("cmd: %s\t error: %s", cmdstring, strerror(errno)); // 这里务必要把errno信息输出或记入Log
return XXX;
} if(WIFEXITED(status))
{
printf("normal termination, exit status = %d\n", WEXITSTATUS(status)); //取得cmdstring执行结果
}
else if(WIFSIGNALED(status))
{
printf("abnormal termination,signal number =%d\n", WTERMSIG(status)); //如果cmdstring被信号中断,取得信号值
}
else if(WIFSTOPPED(status))
{
printf("process stopped, signal number =%d\n", WSTOPSIG(status)); //如果cmdstring被信号暂停执行,取得信号值
}
到于取得子进程返回值的相关介绍可以参考另一篇文章:http://my.oschina.net/renhc/blog/35116
system()函数用起来很容易出错,返回值太多,而且返回值很容易跟command的返回值混淆。这里推荐使用popen()函数替代,关于popen()函数的简单使用也可以通过上面的链接查看。
popen()函数较于system()函数的优势在于使用简单,popen()函数只返回两个值:
成功返回子进程的status,使用WIFEXITED相关宏就可以取得command的返回结果;
失败返回-1,我们可以使用perro()函数或strerror()函数得到有用的错误信息。
这篇文章只涉及了system()函数的简单使用,还没有谈及SIGCHLD、SIGINT和SIGQUIT对system()函数的影响,事实上,之所以今天写这篇文章,是因为项目中因有人使用了system()函数而造成了很严重的事故。现像是system()函数执行时会产生一个错误:“No child processes”。
关于这个错误的分析,感兴趣的朋友可以看一下:http://my.oschina.net/renhc/blog/54582
高手的分析 上面有高手的博客
[转]【C/C++】Linux下使用system()函数一定要谨慎的更多相关文章
- 【C/C++】Linux下使用system()函数一定要谨慎
[C/C++]Linux下使用system()函数一定要谨慎 http://my.oschina.net/renhc/blog/53580 曾经的曾经,被system()函数折磨过,之所以这样,是因为 ...
- Linux下使用system()函数一定要谨慎
转载自:http://my.oschina.net/renhc/blog/53580 linux尽量避免使用system. 曾经的曾经,被system()函数折磨过,之所以这样,是因为对syste ...
- (转)Linux下使用system()函数一定要谨慎
转:http://my.oschina.net/renhc/blog/53580 曾经的曾经,被system()函数折磨过,之所以这样,是因为对system()函数了解不够深入.只是简单的知道用这个函 ...
- 关于linux中的system函数
Linux下使用system()函数一定要谨慎 https://blog.csdn.net/senen_wakk/article/details/51496322 system()正确应用 https ...
- linux下代替system的基于管道的popen和pclose函数
linux下使用system需要谨慎,那么代替它的方法是什么呢? 标准I/O函数库提供了popen函数,它启动另外一个进程去执行一个shell命令行. 这里我们称调用popen的进程为父进程,由pop ...
- 【转】在嵌入式Linux和PC机Linux下使用popen函数时,程序运行结果有差异。
下面程序演示了在嵌入式Linux和PC机Linux下使用popen函数时,程序的运行结果是有差异的. 两个程序 atest.c 和 btest.c,atest 检查是否有 btest 进程运行,如果没 ...
- Linux下利用ioctl函数获取网卡信息
linux下的ioctl函数原型如下: #include <sys/ioctl.h> int ioctl(int handle, int cmd, [int *argc, int argv ...
- Linux下系统时间函数、DST等相关问题总结(转)
Linux下系统时间函数.DST等相关问题总结 下面这个结构体存储了跟时区相关的位移量(offset)以及是否存在DST等信息,根据所在的时区信息,很容易找到系统时间与UTC时间之间的时区偏移,另外根 ...
- 【转】Linux下(C/C++)使用system()函数一定要谨慎
转自:http://my.oschina.net/renhc/blog/53580 曾经的曾经,被system()函数折磨过,之所以这样,是因为对system()函数了解不够深入.只是简单的知道用 ...
随机推荐
- Java MyBatis 插入数据库返回主键--insertSelective这样就不用每次到数据库里面查询了
insertSelective---Java MyBatis 插入数据库返回主键--insertSelective这样就不用每次到数据库里面查询了 https://www.cnblogs.com/xi ...
- 使用Mybatis进行连表查询、left join---https://blog.csdn.net/jinzhencs/article/details/51980518
使用Mybatis进行连表查询.left join https://blog.csdn.net/jinzhencs/article/details/51980518
- CodeForcesGym 100753E Change of Scenery
Change of Scenery Time Limit: 10000ms Memory Limit: 262144KB This problem will be judged on CodeForc ...
- HDU 4598 Difference
Difference Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65535/65535 K (Java/Others)Total ...
- SGU 485 Arrays
485. Arrays Time limit per test: 1.75 second(s)Memory limit: 262144 kilobytes input: standardoutput: ...
- cc2540 cc2541 开发板资料更新日志
经过多次PCB打样和全面调试.已经完毕了cc2540 cc2541的开发板的批量贴片.硬件告一段落, 接下来是全面完好软件方面的工作.眼下已经针对没有开发经验的用户编写完毕0基础基础实验代码和教程.接 ...
- iOS中的成员变量,实例变量,属性变量
在ios第一版中: 我们为输出口同时声明了属性和底层实例变量,那时,属性是oc语言的一个新的机制,并且要求你必须声明与之对应的实例变量,例如: 注意:(这个是以前的用法) @interface MyV ...
- Hibernate——三种状态的理解
在Hibernate中有三种状态,对这三种状态的深入的理解,能够更好的理解Hibernate的执行机制. 在整个Hibernate中这三种状态是能够进行转换的. 1.Transient Object( ...
- MyBatis逆向工程生成的Example类的方法总结
很早之前就在项目开发中多次使用MyBatis逆向工程生成的Example类,但一直没有对其下的方法做一个简单的总结,现总结如下:一.mapper接口中的方法解析mapper接口中的部分常用方法及功能如 ...
- Bitmap通过getWidth和getHeight获取尺寸不符
在使用BitmapFactory载入图片时,常会出现这样的情况,返回的图片尺寸与实际尺寸不符.这是因为我们把图片资源放到res/drawable文件路径下时,选择的文件不同所致.不同的目录会有不同的缩 ...