Head First C 第九章 进程与系统调用 用fork()+exec()运行子进程
问题引入:当你想循环使用exec调用另外一个程序时,发现只调用了一次就结束了。这是因为,exec函数通过运行新程序来替换当前程序,因此,后面的代码都没有运行。
为了达到我们想要的效果,在此引入fork()
系统调用。
实例:RSS订阅功能
int main(int argc, char *argv[]) {
char *feeds[] = {"http://www.cnn.com/rss/celebs.xml",
"http://www.rollingstone.com/rock.xml",
"http://eonline.com/gossip.xml"};
int times = 3;
int i;
char *phrase = argv[1];
for (i = 0; i < times; i++) {
char var[255] = {};
sprintf(var, "RSS_FEED=%s", feeds[i]);
char *vars[] = {var, NULL};
if (execle("/usr/bin/python", "/usr/bin/python", "rssgossip.py", phrase, NULL, vars) == -1) {
fprintf(stderr, "%s\n", strerror(errno));
return 1;
}
}
return 0;
}
在这段代码中,有一个for (i = 0; i < times; i++)
循环,其中包含一个execle("/usr/bin/python", "/usr/bin/python", "rssgossip.py", NULL, vars)
语句,用于调用一个叫作rssgossip.py
的脚本。
我们的本意是想循环调用,但是实际上,这个语句只会运行一次。我们尝试用fork来让它多次运行。
*fork()*的使用
- 使用步骤:
- 复制进程:第一步用fork()系统调用来复制当前进程。进程需要以某种方式区分自己是父进程还是子进程,为此fork()函数向子进程返回0,向父进程返回非零值。
- 如果是子进程,就调用exec()。 现在你有两个独立的进程,子进程在运行rssgossip.py脚本,而原来的父进程可以继续做其他事,完全不受干扰。
- 修改原有的程序代码
主要改动内容为:
1. 创建一个子进程pid_t pid;
2. 使用fork()函数复制当前进程。
3. 监控返回值,如果为0则表示为子进程,则使用execle()
调用脚本取代该进程。
4. 父进程在execle()
后面的代码可以继续执行,即,可以循环创建子进程来获得rss订阅内容。
for (i = 0; i < times; i++) {
char var[255];
sprintf(var, "RSS_FEED=%s", feeds[i]);
char *vars[] = {var, NULL};
pid_t pid;
if ((pid = fork()) < 0) {
fprintf(stderr, "Can't fork process: %s\n", strerror(errno));
return 1;
} else if (pid == 0) {
if (execle("/usr/bin/python", "/usr/bin/python", "./fake_rss.py", phrase, NULL, vars) == -1) {
fprintf(stderr, "Can't run script: %s\n", strerror(errno));
return 1;
}
}
}
示例代码
来源:oschina
链接:https://my.oschina.net/u/2491285/blog/652342