• 这个模型用来测试并发服务器,是否会产生僵尸进程


    #include <unistd.h>  
    #include <stdio.h>  
    #include<signal.h>
    int main(void)  
    {  signal(SIGCHLD, SIG_IGN);            //一般来说在做并发服务器的时候,都要将这个加上!可以防止因为子进程退出时,父进程没时间处理,而产生僵尸进程!
       int i=0;  
       printf("i son/pa ppid pid  fpid
    ");  
       //ppid指当前进程的父进程pid  
       //pid指当前进程的pid,  
       //fpid指fork返回给当前进程的值  
       for(i=0;i<2;i++){  
           pid_t fpid=fork();  
           if(fpid==0)  
               {printf("%d child  %4d %4d %4d
    ",i,getppid(),getpid(),fpid); 
                while(1); }
           else {
               printf("%d parent %4d %4d %4d
    ",i,getppid(),getpid(),fpid);}  
       }  
       return 0;  
    }
    无论有没有signal(SIGCHLD, SIG_IGN); 这句,产生的两个子进程,输出没有变化
    [root@linux Desktop]# gcc a.c
    [root@linux Desktop]# ./a.out
    i son/pa ppid pid  fpid
    0 parent 4643 6269 6270
    0 child  6269 6270    0
    1 child  6269 6271    0
    1 parent 4643 6269 6271
    [root@linux Desktop]# ./a.out
    i son/pa ppid pid  fpid
    0 parent 4643 6422 6423
    1 parent 4643 6422 6424
    [root@linux Desktop]# 1 child     1 6424    0
    0 child     1 6423    0
    //从上面的输出结果可以看出产生的两个子进程都是父进程产生的,分别为6270(i=0)和6271(i=1)两个子进程,按道理来说第二次循环中子进程还可以创建一个子进程,这样就符合规律了,本应该创建3个子进程,但是为啥创建了两个子进程是因为第一次循环时即(i=0)父进程创建的子进程6270陷入了无限循环之中,所以没发在第二次循环中再次创建子进程!这样就可以理解了,为啥只创建一个子进程了!
    [root@linux Desktop]# ps --ppid 1     1号进程为init进程,父进程死亡,子进程被init进程接管
     6270 pts/6    00:00:18 a.out     //部分截图
     6271 pts/6    00:00:18 a.out
     6423 pts/6    00:00:00 a.out
     6424 pts/6    00:00:00 a.out
    
    
    
    
    
    #include <unistd.h>  
    #include <stdio.h>  
    #include<signal.h>
    int main(void)  
    {  signal(SIGCHLD, SIG_IGN);//把这行代码注释掉,仍然没有啥变化
       int i=0;  
       printf("i son/pa ppid pid  fpid
    ");  
       //ppid指当前进程的父进程pid  
       //pid指当前进程的pid,  
       //fpid指fork返回给当前进程的值  
       for(i=0;i<2;i++){  
           pid_t fpid=fork();  
           if(fpid==0)  
               {printf("%d child  %4d %4d %4d
    ",i,getppid(),getpid(),fpid); 
                while(1); }
        
           else {
               printf("%d parent %4d %4d %4d
    ",i,getppid(),getpid(),fpid);}  
       }  
       while(1);    //这句是必须的不然服务器程序会执行完后会退出程序!这样就不能接到客户端的请求了!
       return 0;  
    }  
    [root@linux Desktop]# gcc a.c
    [root@linux Desktop]# ./a.out
    i son/pa ppid pid  fpid
    0 parent 2667 2725 2726
    1 parent 2667 2725 2727
    0 child  2725 2726    0
    1 child  2725 2727    0   //注意这儿阻塞住了,可以用ctrl+c输出没有变化
    
    [root@linux Desktop]# ps aux | grep -w 'Z'
    root      2709  2.0  0.0   4336   792 pts/2    S+   18:58   0:00 grep -w Z  //注意没有僵尸进程产生 
    [root@linux Desktop]# 
    [root@linux Desktop]# ps aux | grep -w 'Z'
    root      2738  0.0  0.0   4336   820 pts/2    S+   18:58   0:00 grep -w Z   
    [root@linux Desktop]# 
    
    
    [root@linux Desktop]# ps --ppid 1
      PID TTY          TIME CMD
      516 ?        00:00:00 udevd
     1467 ?        00:00:00 vmware-vmblock-
     1487 ?        00:00:01 vmtoolsd
     1617 ?        00:00:00 auditd
     1635 ?        00:00:00 portreserve
     1642 ?        00:00:00 rsyslogd
     1695 ?        00:00:01 dbus-daemon
     1706 ?        00:00:00 NetworkManager
     1709 ?        00:00:00 modem-manager
     1717 ?        00:00:00 wpa_supplicant
     1721 ?        00:00:00 avahi-daemon
     1732 ?        00:00:00 cupsd
     1757 ?        00:00:00 acpid
     1766 ?        00:00:00 hald
     1835 ?        00:00:00 sshd
     1873 ?        00:00:00 tpvmlp
     1945 ?        00:00:00 mysqld_safe
     2107 ?        00:00:00 abrtd
     2115 ?        00:00:00 abrt-dump-oops
     2123 ?        00:00:01 crond
     2134 ?        00:00:00 atd
     2149 ?        00:00:00 rhsmcertd
     2166 ?        00:00:00 gdm-binary
     2171 tty2     00:00:00 mingetty
     2175 tty3     00:00:00 mingetty
     2177 tty4     00:00:00 mingetty
     2179 tty5     00:00:00 mingetty
     2184 tty6     00:00:00 mingetty
     2217 ?        00:00:00 console-kit-dae
     2290 ?        00:00:00 dbus-launch
     2296 ?        00:00:00 devkit-power-da
     2338 ?        00:00:00 polkitd
     2349 ?        00:00:00 rtkit-daemon
     2367 ?        00:00:00 gnome-keyring-d
     2384 ?        00:00:00 dbus-launch
     2385 ?        00:00:00 dbus-daemon
     2399 ?        00:00:00 gconfd-2
     2403 ?        00:00:03 gnome-settings-
     2409 ?        00:00:00 seahorse-daemon
     2411 ?        00:00:00 gvfsd
     2420 ?        00:00:00 gvfs-fuse-daemo
     2439 ?        00:00:00 bonobo-activati
     2447 ?        00:00:00 trashapplet
     2448 ?        00:00:01 wnck-applet
     2450 ?        00:00:00 gvfs-gdu-volume
     2454 ?        00:00:00 udisks-daemon
     2456 ?        00:00:02 vmtoolsd
     2469 ?        00:00:00 pulseaudio
     2484 ?        00:00:00 gvfs-gphoto2-vo
     2487 ?        00:00:00 gvfs-afc-volume
     2502 ?        00:00:00 gdm-user-switch
     2503 ?        00:00:00 clock-applet
     2504 ?        00:00:00 notification-ar
     2505 ?        00:00:00 gnote
     2510 ?        00:00:00 gvfsd-trash
     2513 ?        00:00:00 restorecond
     2522 ?        00:00:00 gnome-screensav
     2536 ?        00:00:00 packagekitd
     2540 ?        00:00:01 notification-da
     2617 ?        00:00:00 gvfsd-burn
     2631 ?        00:00:00 gvfsd-metadata
     2652 ?        00:00:02 gedit
     2665 ?        00:00:03 gnome-terminal
    [root@linux Desktop]# 
  • 相关阅读:
    vb.net EXCEL进程问题
    VB.NET 中使用正则表达式
    改变鼠标状态
    举证信息表,语言不是VB.NET 是VBA的
    初学查询时的一些东西
    删除关联错误
    对于 using ESRI.ArcGIS.Carto; 的引用。是否缺少 using 指令或程序集引用
    AxMapControl 引用问题
    堆排序:大顶堆,小顶堆
    abs()函数,fabs函数(),max()函数的区别
  • 原文地址:https://www.cnblogs.com/leijiangtao/p/4078270.html
Copyright © 2020-2023  润新知