首页 文章

使用fork时如何映射内存?

提问于
浏览
5

我是“fork()”的新手,我随处读到,当调用fork()时,启动当前(调用)进程的精确副本 . 现在,当我运行以下代码时,应该有两个不同的进程,有两个不同的分配给其变量和函数的内存位置 .

#include<stdio.h>
int i=10;
int pid;
 int main(){
  if((pid=fork())==0){
    i++;//somewhere I read that separate memory space for child is created when write is needed
    printf("parent address= %p\n",&i);// this should return the address from parent's memory space
  }else{
    i++;
    i++;
    printf("child address= %p\n",&i);// this should return the address of child's memory space 
  }
  wait(0);
  return(0);
 }
Why The output looks like:: 
child address::804a01c 
parent address::804a01c

为什么父母和孩子的地址都是一样的?

3 回答

  • 8

    将两个不同的存储位置分配给它们的变量和功能 .

    不; Linux实现了virtual memory,这意味着每个进程都有自己的完整地址空间 . 因此,在 fork 之后,两个进程都会查看其内存中对象副本的相同地址 .

    (顺便说一句:VM还会导致代码在物理内存中的进程之间共享,并且所有数据都只是copied-on-write . )

  • 2

    地址是进程本地的 . 804a01c 在一个进程中与另一个进程中的 804a01c 不同 .

  • 2

    由于virtual memory:两个地址空间看起来都与各个进程相同 . 存储的物理内存是不同的 . 然而,实际上,通过内存优化(由大多数内核实现)使相应的不同虚拟页面映射到相同的物理页面,直到其中一个进程写入该内存页面,此时页面被物理复制 . 到另一个物理地址(并为该进程重新映射虚拟页面) .

    还有许多其他复杂情况:最受认可的是 fork() 的返回值在进程之间有所不同,尽管这通常是寄存器值的差异,而不是内存 . 但是,打开文件和其他一些资源可以标记为不可继承,因此可能存在其他差异 - 次要但有时很有用 .

相关问题