linux - clone() 系统调用是否最终依赖于 fork 功能?

标签 linux clone fork

对于我正在上的类(class),我一直在直接使用 Linux 中的 clone() 系统调用做一些工作。我很好奇它实际上是如何工作的,并开始进行一些挖掘。令我困惑的是,它似乎依赖于一些与 fork() 功能相同的基础(它们调用相同的 do_fork() 函数,尽管参数不同)。一方面,这对我来说很有意义,因为线程实际上只是一个轻量级进程,但我一直认为线程的创建方式与进程的创建方式之间存在一些显着差异。我深入研究了 do_fork() 和随后的 copy_process() (do_fork() 调用)的实现,但我还没有能够说服自己我明白发生了什么。

所以,对于那里的大师们,我是不是漏掉了什么,或者这实际上是如何工作的?是否有标志基本上告诉操作系统要复制多少以及开始执行新任务的指令(我认为答案必须是,但我只是不确定他们是如何翻译的)?

下面是我正在查看的代码,也许您可​​以解释传递的参数如何控制创建轻量级或重量级进程。

asmlinkage int sys_fork(struct pt_regs *regs){
  #ifdef CONFIG_MMU
      return do_fork(SIGCHLD, regs->ARM_sp, regs, 0, NULL, NULL);
  #else
    /* can not support in nommu mode */
    return(-EINVAL);
  #endif
}


asmlinkage int sys_clone(unsigned long clone_flags, unsigned long newsp,
             int __user *parent_tidptr, int tls_val,
             int __user *child_tidptr, struct pt_regs *regs)
{
    if (!newsp)
        newsp = regs->ARM_sp;

    return do_fork(clone_flags, newsp, regs, 0, parent_tidptr, child_tidptr);
}

谢谢!

最佳答案

实际上,在概念层面上,Linux 内核对进程或线程一无所知,它只知道“任务”。

Linux 任务可以是进程、线程或介于两者之间的东西。 (顺便说一下,这意味着 vfork() 创建的奇怪 child 非常适合 Linux“任务”范式)。

现在,任务可以共享一些东西,请参阅 clone(2) 联机帮助页中的所有 CLONE_* 标志。 (并非所有这些标志都可以描述为共享,一些指定了更复杂的行为)。

或者新任务可以选择拥有各自资源的副本。从 2.6.16 开始,他们可以在启动后这样做,参见 unshare(2)。

例如,vfork() 和 fork() 调用之间的唯一区别是 vfork() 设置了 CLONE_VM 和 CLONE_VFORK。 CLONE_VM 使其共享其父进程的内存(与线程共享内存的方式相同),而 CLONE_VFORK 使父进程阻塞,直到子进程释放其内存映射(通过调用 execve() 或 _exit())。

请注意,Linux 并不是唯一以这种方式概括进程和线程的操作系统。计划 9 有 rfork()。

关于linux - clone() 系统调用是否最终依赖于 fork 功能?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4157164/

相关文章:

linux - Bash 限制父脚本命令行参数传递给子脚本参数

子进程可以更改父进程共享的静态变量吗?

linux - Openwrt linux 设备列表

linux - 移动 linux 目录,除非它已经存在

linux - 如何在 Linux 中创建不可读的文件

c - 每个 fork 进程的不同输入/输出流

c++ - 流程处理的封装会产生问题

git - 在拇指驱动器上克隆 git 存储库

Java:当您只能访问接口(interface)时复制对象

azure - 没有从 azure devops 克隆 Visual Studio 的选项吗?