进程操作

来源:互联网 发布:csgom4a1皮肤知乎 编辑:程序博客网 时间:2024/06/06 05:48

1、创建一个进程

#include<unistd.h>

pid_t fork(void);

返回值:
1、对于父进程,fork()函数返回新创建的子进程的ID

2、对于子进程,fork()函数返回0。由于系统0号进程是否内核进程,所以子进程的进程号不可能是0.

3、如果出错,fork()函数返回-1。

例:

#include<stdio.h>#include<stdlib.h>#include<unistd.h>int main(void){     pid_t pid;     pid = fork();     if(pid<0){           printf("fail to fork\n");           exit(1);     }else if (pid == 0){   printf("child id:%u\n",getpid());     }else{           printf("parent id:%u\n",pid);     }     return 0;}

2、父子进程的共享资源
子进程完全复制了父进程的地址空间的内容,包括堆栈段和数据段,子进程并没有复制代码段,而是和父进程共用代码段。

例:

#include<stdio.h>#include<stdlib.h>#include<unistd.h>int global;int main(void){    pid_t pid;    int stack = 1;    int *heap;    heap = (int *)malloc(sizeof(int));    *heap = 2;    pid = fork();    if(pid<0){         printf("fail to fork\n");         exit(1);    }else if (pid == 0){         global++;         stack++; (*help)++; printf("child data:%d,stack:%d,heap:%d\n",global,stack,*heap);    }else{         printf("parent data:%d,stack:%d,heap:%d\n",global,stack,*heap);    }    return 0;}gcc test.c -o test./testchild data:1,stack:2,heap:3parent data:0,stack:1,heap:2

资源                        父子进程是否相同            备注
进程ID                      否                            父子进程是两个独立的进程,调度机会均等
实际用户ID               是
实际组ID                   是
有效用户ID               是
有效组ID                  是
附加组ID                  是
进程组ID                  是
父进程ID                  否                            父进程的进程是其他进程,而子进程的父进程是父进程
会话ID                      是
设置用户ID标志        是
设置组ID标志           是
当前工作目录           是
根目录                      是
文件权限屏蔽字       是
信号的屏蔽              是
打开文件的描述符   是
数据段                     是
代码段                     是
堆栈                         是
.bass段                    是
连接的共享存储段    是
存储映射                  是
资源限制                  是
tms_utime                否                     子进程的tms_utime被清0
tms_stime                否                     子进程的tms_stime被清0
tms_cutime              否                     子进程的tms_cutime被清0
tms_ustime              否                     子进程的tms_ustime被清0
fork函数的返回值    否                      父进程返回子进程的进程ID,而子进程返回0
设置的文件锁          否                      文件锁不会被继承
未处理的闹钟信号   否                      子进程清除未处理的闹钟信号
未决信号集              否                     子进程清除未处理的未决信号

2、创建一个共享空间的子进程

创建一个共用父进程地址空间的子进程

#include<unistd.h>

pid_t vfork();

vfork()函数和fork()函数的区别有以下两点

1、vfork()函数产生的子进程和父进程完全共享地址空间,包括代码段、数据段和堆栈段,子进程对这些共享资源所做的修改可以影响进程。由此可知,vfork()函数与其他说是产生了一个进程,不如说是产生了一个线程。
2、vfork()函数产生的子进程一定比父进程先运行,也就是说父进程调用了vfork()函数后,会等待子进程运行后再运行。

例:

#include<stdio.h>#include<stdlib.h>#include<unistd.h>int global;int main(void){pid_t pid;int stack = i;int *heap;heap = (int *)malloc(sizeof(int));*heap = 2;pid = vfork();if(pid<0){printf("fail to fork\n");exit(1);}else if (pid == 0) {global++;stack++;(*help)++;printf("child data:%d,stack:%d,heap:%d\n",global,stack,*heap);printf("child terminates\n");exit(0);}else {        //sleep(2);printf("parent data:%d,stack:%d,heap:%d\n",global,stack,*heap);printf("parent terminates\n");return 0;       }}gcc test.c -o test./testchild data:1,stack:2,heap:3child terminatesparent data:1,stack:2,heap:3parent terminates
3、退出进程
#include<stdlib.h>

void exit(int status);

这个退出函数会深入内核注销掉的内核数据结构,并且释放进程的资源。

例:

#include<stdlib.h>int main(void){       exit(4);}gcc -exit.c -o exit$./exit$echo $?4

c程序中的return 语句会被编译器翻译为调用exit()函数
return 1  会被编译器翻译为调用exit(1)函数
4、设置进程所有者

a、改变一个进程的实际用户ID和有效用户ID

      #include<unistd.h>

      int setuid(uid_t uid);

      参数:改变后的新用户ID

      返回:成功返回0,失败返回-1

      只有两种用户可以修改进程的实际用户ID和有效用户ID
      1、根用户,根用户可以将进程的实际用户ID 和有效用户ID更改。

      2、其他用户,且该用户的用户ID等于进程和实际用户ID或者保存的用户ID

b、只修改有效用户ID函数

      #include<unistd.h>

      int seteuid(uid_t uid);

      参数:修改ID

      返回:成功返回0,失败返回-1.

c、修改实际组ID和有效组ID的函数

      #include<unistd.h>
      int setgid(gid_t gid)
     int setegid(gid_t gid)




0 0
原创粉丝点击