进程-fork函数


1.进程

【1】进程的定义:
    进行中的程序 
    程序的一次执行过程 (内存 + CPU)
    程序的实例    

【2】
 程序  ----加载到内存----> 进程 
 静态                      动态
 硬盘                      内存 
内存 空间 ---- 掉电丢失
    
【3】进程概念 
  (用来描述 程序动态执行的过程,方便操作系统管理的)
     
【4】应用场景:
   实现并发 
   同一时刻 同时发生 


2. 进程 的组成
   
  【1】 进程怎么来的?
    程序 ---- 加载到内存 ----> 进程 
   
   【2】程序的组成:
     程序 = 代码 + 数据 
     程序 = 代码区 + [栈|堆|全局区|字符串常量区]
   【3】栈
        ------|
         堆   |   
         ------|
     全局区|data/bss       data --- 已经初始化了的全局变量或静态变量 bss ---未初始化
         ------|
      代码段|text

    【4】进程 = 代码|data|bss|堆|栈 + pcb 

      pcb (process control block) 进程控制块 
      PID  process id //进程id号
      对比:
      进程 相当于是 计算机世界中 人 

     pcb
    struct task_struct {
    PID,             //进程标识符
    PPID,            //父进程ID号  parent 
    当前工作路径     //chdir
    umask            //0002
    进程打开的文件列表 //文件IO中有提到
    信号相关设置       //处理异步io, ---段错误
    用户id,组id
    进程资源的上限
      }

3.进程的状态:

PROCESS STATE CODES
       Here are the different values that the s, stat and state output specifiers 
       (header "STAT" or "S") will display to describe the state of a process:

               D    uninterruptible sleep (usually IO) //不可中断的睡眠态
               R    running or runnable (on run queue) // 运行态
               S    interruptible sleep (waiting for an event to complete)//可中断的睡眠态
               T    stopped by job control signal      // 暂停态
               t    stopped by debugger during the tracing
               W    paging (not valid since the 2.6.xx kernel)
               X    dead (should never be seen)
               Z    defunct ("zombie") process, terminated but not reaped by its parent

       For BSD formats and when the stat keyword is used, additional characters may be displayed:

               <    high-priority (not nice to other users)
               N    low-priority (nice to other users)
               L    has pages locked into memory (for real-time and custom IO)
               s    is a session leader
               l    is multi-threaded (using CLONE_THREAD, like NPTL pthreads do)
               +    is in the foreground process group

          R  --- 运行态 
          D  --- 不可中断 睡眠态
          S  --- 可中断 睡眠态 
          T  --- 暂停态 
          Z  --- 僵尸态 

4.

进程管理的命令:
top  //类似Windows的下任务管理器 

ps -eLf | head -1   //可以观察到 PID PPID 
    F S UID        PID  PPID  C PRI  NI ADDR SZ WCHAN  STIME TTY          TIME CMD

ps -eLf | grep a.out  //查看a.out 信息 //可以观察到 PID PPID
ps -aux | grep a.out  //可以查看进程 的状态 
pstree  //进程树  

pstree -sp pid号 //查看指定的进程的关系

kill //给进程发信号 
     kill 信号 程序的pid号    
    eg:
       kill -9 5266
kill -l  //查看可以发送的信号 
 

5.创建子进程 
fork()  

       pid_t fork(void);
       功能:
          创建子进程 (通过复制调用进程)
       参数:
          void 
       返回值:
          成功 
              在父进程中 返回子进程的pid号
              在子进程中 返回0
          失败 
             -1 && errno 被设置
             
     pid号:
          pid 本质上就是一个数值 
          正整数 1 

    

    一次调用,会返回两次。
    子进程先运行和是父进程先进程,顺序不确定。
    变量不共享。
    
    子进程复制父进程的0到3g空间和父进程内核中的PCB,但id号不同。
    
    此时,父子进程各自拥有独立的4g内存空间 (32位的系统)
    
    功能:
          通过该函数可以从当前进程中克隆一个同名新进程。
          克隆的进程称为子进程,原有的进程称为 父进程。
          子进程是父进程的完全拷贝。
          复制之后,
          子进程和父进程 各自拥有自己的 用户空间(进程空间)
          子进程和父进程的执行过程是从fork函数之后执行。
          
          子进程与父进程具有相同的代码逻辑。
          
    返回值:int 类型的数字。
            在父进程中:成功 返回值是子进程的pid号 >0
                        失败 返回-1;
            在子进程中:成功 返回值 0
                        失败 无
            
     注意:
      1.创建好之后,父子进程的运行顺序是不确定 ---全部取决于 操作系统的调度

 

6.kill操作: 
      将父进程杀死 
      init进程(1)   //UNIX环境高级编程(init -- systemd)
       
 init(1)───gnome-terminal-(2554)───bash(3336)───a.out(5934)───a.out(5935)


 init(1)───a.out(5935) 

    子进程 还在 ,父进程不在 ---- 孤儿进程 
                             ---- 此时由init进程 收养 
                             
      结束子进程,父进程还在,但是父进程并没有对子进程"收尸"
       
    特殊:
      孤儿进程 
           子进程 还在,父进程不在
      僵尸进程 
          子进程 结束,父进程还在,且父进程并未"收尸"
         僵尸态进程有危害

 
      练习3:
     fork()&&fork()||fork();    //总共几个进程

32 位 --- 地址总线 数据总线 
          
          
          2^32 = 2^10 * 2^10 * 20 ^10 * 2^2 
                 1k     1M     1G     * 4
                 
                 4G空间       
注意:
   1.父子进程创建好之后,各自拥有独立4G内存空间(32位系统)
   2.他们的数据相互独立,父进程或子进程对数据的修改,不会相互影响,只会对各自造成影响     
 

        
7.应用场合:
        1)一个进程希望复制自己,使父子进程同时执行同的代码段。 --- 子承父业 
           网络服务中会比较多见。(服务器程序,比如,淘宝,接收登录+购物操作)
           
           eg:
           12306 网站:
           (1).登录 
           (2).查询车票
               订购车票
               付款
           12306服务器            
           子进程  
           子1 --- 1 查询,订购,付款 
           子2 --- 2 查询,订购,付款
           
           多任务的并发。
             
        2)一个进程需要执行一个不同的程序。//fork + exec    --- 独立创业 
        bash
         |--bash_child -- ls/cp/a.out

  8.fork出一个子进程。
           子进程与父进程做的完全不同的事情。
           
           exec函数族
          
          eg:
            minishell 
            
            linux@ubuntu:test$ pstree  -sp 3210
             init(1)───gnome-terminal(2579)───bash(2590)───a.out(3210)───a.out(3211)
              
               bash(2590) 
                |
              fork()
              /    \
         bash(2590) bash() + exec()//执行了一个与bash完全不用的程序。
                    //执行了一个新的程序
           

        使用变量测试,验证位于不同的地址空间。
        
        
        bash(7765)───a.out(12807)───a.out(12808)
        
        bash(7765)
          |
        fork
        /   \
bash(7765)  (a.out)bash(7766) //运行了一个 a.out    //exec
 

创建n个进程    :
输入n 创建n个子进程


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值