zoukankan      html  css  js  c++  java
  • fork()函数分析

    1 C语言代码

     1 #include <stdio.h>
     2 #include <unistd.h>
     3 
     4 int main()
     5 {
     6     if(!fork()){while(1)printf(“A”);}
     7     if(!fork()){while(1)printf(“B”);}
     8     wait();
     9     return 0;  
    10 }

    在Linux环境下,运行上述代码,屏幕上会交替显示A与B。

    2 代码解析

    进入fork()函数内部,如下所示。

    main(){
    mov __NR_fork, %eax
    int 0x80
    100: mov %eax, res
    cmpl res,0
    jne 208
    200: printf(“A”)
    jmp 200
    208: ...
    304: wait()
    }

    在实模式下:mov 目的操作数,源操作数

    在保护模式下:mov 源操作数,目的操作数

    而上面的一段代码是在保护模式下。

    如下面代码所示,__NR_fork就是2。

     1 #define __NR_exit                 1
     2 #define __NR_fork                 2
     3 #define __NR_read                 3
     4 #define __NR_write                4
     5 #define __NR_open                 5
     6 #define __NR_close                6
     7 #define __NR_waitpid              7
     8 #define __NR_creat                8
     9 #define __NR_link                 9
    10 #define __NR_unlink              10
    11 #define __NR_execve              11
    12 #define __NR_chdir               12
    13 #define __NR_time                13
    14 #define __NR_mknod               14
    15 #define __NR_chmod               15
    16 #define __NR_lchown              16

    %eax

    8086系列CPU16位寄存器如下所示,加上e表示扩展的意思,既寄存器是32位,前面加一个%是一个规则,就表示是寄存器的意思。

    int 0x80

    这是一个中断,只有通过中断,用户程序才能进入内核。

    进入内核要调用两个关键函数

    set_system_gate(0x80, &system_call);

    set_system_gate把第0x80中断表的表项中中断处理程序入口地址设置为&system_call。并且把那一项IDT表中的DPL设置了为3, 方便用户程序可以去访问这个地址。

    system_call:
        call sys_call_table(, %eax, 4)

    这句汇编语句操作数的含义是间接调用地址在_sys_call_table + %eax * 4 处的函数。

    由于sys_call_table[]指针每项4个字节,因此这里需要给系统调用功能号乘上4。

    然后用所得到的值从表中获取被调用处理函数的地址。

    接着执行sys_fork函数

    sys_fork:
    pushl ...
    call copy_process
    ret

    内核通过调用函数copy_process()创建进程,copy_process()函数主要用来创建子进程的描述符以及与子进程相关数据结构。

    通过执行ret指令,中断返回。

    参考

    int 80h系统调用方法

    https://introspelliam.github.io/2017/08/07/int-80h%E7%B3%BB%E7%BB%9F%E8%B0%83%E7%94%A8%E6%96%B9%E6%B3%95/

    剖析Linux系统调用的执行路径

    https://www.cnblogs.com/ronny/p/7789057.html

  • 相关阅读:
    svn_linux + apache 实现网页访问svn
    SVN_2008R2 搭建流程与规范
    mysql 简称
    论运维之故障排查思路与方法
    mac pro 基本使用
    防火墙之netfailt、iptables详解
    翻转单词顺序列(剑指offer)
    中缀变为后缀
    左旋转字符串(剑指offer)
    和为S的两个数字(剑指offer)
  • 原文地址:https://www.cnblogs.com/QQ2962269558/p/13289264.html
Copyright © 2011-2022 走看看