栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 系统运维 > 运维 > Linux

Linux系统API与库函数-3.进程控制

Linux 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Linux系统API与库函数-3.进程控制

3. 进程控制 3.1 环境变量 3.1.1 获取环境变量getenv()

帮助手册:man 3 getenv
包含头文件:

`#include

函数原型:
char *getenv(const char *name);

参数说明
name环境变量
return成功:环境变量的值
失败:NULL
3.1.2 修改或添加环境变量setenv()

帮助手册:man 3 setenv
包含头文件:

`#include

函数原型:
int unsetenv(const char *name);

参数说明
name环境变量名
value变量值
overwrite当环境变量存在时
0:不重写
非0:重写
return成功:0
失败:-1,并设置errno
3.1.3 删除环境变量unsetenv()

帮助手册:man 3 unsetenv
包含头文件:

`#include

函数原型:
char *getenv(const char *name);

参数说明
name环境变量名
return成功:0
失败:-1,并设置errno
3.2创建子进程fork()

帮助手册:man 2 fork
包含头文件:

#include #include

函数原型:
pid_t fork(void);

刚fork()后:

父子进程相同处:
– 全局变量,data, text, 栈,堆,环境变量,用户ID,宿主目录,进程工作目录,信号处理方式…父子进程不相同处:
– 进程ID, fork返回值,父进程ID, 进程运行时间,闹钟(定时器),未决信号集

注:父子进程间数据读时共享,写时复制,父子进程不共享全局变量

参数说明
return成功:子进程:0;父进程:子进程PID
失败:-1,并设置errno
3.3 获得当前进程PIDgetpid()

帮助手册:man 2 getpid
包含头文件:

#include #include

函数原型:
pid_t getpid(void)

参数说明
return返回当前进程的PID
3.4 获得父进程PIDgetppid()

帮助手册:man 2 getppid
包含头文件:

#include #include

函数原型:
pid_t getppid(void)

参数说明
return返回父进程的PID

示例:

#include 
#include 

int main(int argc, char* argv[])
{
	printf("Begin...n");
	pid_t pid = fork();
	if(pid < 0)
	{
		perror("fork error:");
		return -1;
	}
	if(pid == 0)
		printf("This is child process, PID = %d, PPID = %dn", getpid(), getppid());
	if(pid > 0)
		printf("This is parent process, pid = %d, PID = %d, PPID = %dn", pid, getpid(), getppid());
	printf("End...n");
	return 0;
}
3.5 执行一个文件 3.5.1 execl()

帮助手册:man 2 execl
包含头文件:

#include

函数原型:
int execl(const char *pathname, const char *arg, ... );

参数说明
pathname可执行文件路径
arg参数(注:arg[0]需要用可执行文件占位,最后需要用NULL标识)
return成功:不返回
失败:-1,并设置errno
3.5.2 execlp()

帮助手册:man 2 execlp
包含头文件:

#include

函数原型:
int execlp(const char *file, const char *arg, ... );

函数说明:

执行程序时,使用PATH环境变量,执行的程序可以不用加路径

参数说明
file可执行文件路径
arg参数(注:arg[0]需要用可执行文件占位,最后需要用NULL标识)
return成功:不返回
失败:-1,并设置errno

注:execl()和execlp()会将原来的代码断进行替换

#include 
#include 

int main(int argc, char* argv[])
{
	execlp("ls", "ls", "-l", NULL);
	perror("execlp error:");
	return 0;
}
3.6 等待子进程中断或结束

孤儿进程:父进程运行结束,子进程被init进程领养。僵尸进程:子进程运行结束,父进程没有回收子进程资源(PCB)

孤儿进程示例:

#include 
#include 
#include 

int main(int argc, char* argv[])
{
	pid_t pid = fork();
	if(pid == 0)
	{
		while(1)
		{
			printf("child process...ppid=%dn", getppid());
			sleep(1);
		}
	}
	if(pid > 0)
	{
		sleep(3);
		printf("The parent process is finished...n");
	}
	return 0;
}

僵尸进程示例:

#include 
#include 
#include 

int main(int argc, char* argv[])
{
	pid_t pid = fork();
	if(pid == 0)
	{
		sleep(1);
		printf("The child process is finished...n");
	}
	if(pid > 0)
	{
		while(1)
		{
			printf("parent process...n");
			sleep(1);
		}

	}
	return 0;
}
3.6.1wait()

帮助手册:man 2 wait
包含头文件:

#include #include

函数原型:
pid_t wait(int *wstatus);

函数说明:

wait()会暂时停止目前进程的执行,直到有信号来到或子进程结束。如果在调用wait()时子进程已经结束,则wait()会立即返回子进程结束状态值,并回收子进程的PCB。子进程的结束状态值会由参数wstatus返回,而子进程的进程识别码也会一块返回。如果不在意结束状态值,则参数wstatus可以设为NULL。子进程的结束状态值参考waitpid()。

参数说明
wstatus传出参数(子进程的死亡原因)
return成功:子进程PID
失败:-1,并设置errno

子进程的死亡原因:

示例:

#include 
#include 
#include 
#include 

int main(int argc, char* argv[])
{
	pid_t pid = fork();
	if(pid == 0)
	{
		sleep(2);
		printf("The child process is finished...n");
	}
	if(pid > 0)
	{
		printf("wait...n");
		pid_t wpid = wait(NULL);
		printf("The child process was dead. wpid = %d, pid = %dn", wpid, pid);
		while(1) sleep(1);
	}
	return 0;
}
3.6.2 waitpid()

帮助手册:man 2 waitpid
包含头文件:

#include #include

函数原型:
pid_t waitpid(pid_t pid, int *wstatus, int options);

参数说明
pidpid<-1:等待进程组识别码为pid绝对值的任何子进程
pid=-1:等待任何子进程,相当于wait()
pid=0:等待进程组识别码与目前进程相同的任何子进程
pid>0:等待任何子进程识别码为pid的子进程
optionsNULL:与wait()相同,一会阻塞
WNOHANG:如果没有子进程存在立即返回
WUNTRACED:如果子进程进入暂停状态立马返回,但结束状态不予理会
WCONTINUED:如果通过SIGCONT恢复了停止的子进程,也返回
return成功:子进程PID(如果设置了WNOHANG,如果没有子进程退出返回0)
失败:-1,并设置errno

如果wstatus不为NULL,wait()和waitpid()将状态信息存储在*wstatus中。可以使用以下宏检查此整数:

说明
WIFEXITED(wstatus)如果子进程正常退出放回真
WEXITSTATUS(wstatus)返回子进程的退出状态(注:WIFEXITED返回真可以使用)
WIFSIGNALED(wstatus)如果子进程被一个信号杀死返回真
WTERMSIG(wstatus)返回杀死子进程的信号(注:WIFSIGNALED返回真可以使用)
WCOREDUMP(wstatus)如果子进程核转储返回真(注:WIFSIGNALED返回真可以使用)
WIFSTOPPED(wstatus)如果子进程处于暂停状态返回真(注:WIFSIGNALED返回真可以使用)
WSTOPSIG(wstatus)返回引发子进程暂停的信号代码(注:WIFSIGNALED返回真可以使用)
WIFConTINUED(wstatus)如果子进程回复继续运行返回真

示例:

#include 
#include 
#include 
#include 

int main(int argc, char* argv[])
{
	pid_t pid = fork();
	if(pid == 0)
	{
		printf("tChild dead.n");
		sleep(2);
		return 1;
	}
	if(pid > 0)
	{
		printf("wait for child die!n");
		int status;
		pid_t wpid = wait(NULL);
		printf("wait ok, wpid = %d, pid = %dn", wpid, 		pid);
		if(WIFEXITED(status))
		{
			printf("child exit with %dn", 	WEXITSTATUS(status));
		}
		if(WIFSIGNALED(status))
		{
			printf("child killed by %dn", WTERMSIG(status));
		}
		while(1)
		{
			sleep(1);
		}
	}
	return 0;
}
#include 
#include 
#include 
#include 

int main(int argc, char* argv[])
{
    pid_t pid = fork();
    if(pid == 0)
    {
        printf("tChild dead. pid = %dn", getpid());
        sleep(2);
        return 1;
    }
    if(pid > 0)
    {
        printf("wait for child die!n");
        int ret;
        while((ret = waitpid(-1, NULL, WNOHANG)) == 0);
        printf("ret = %dn", ret);
        while(1)
        {
            sleep(1);
        }
    }
    return 0;
}
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/733957.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号