不同进程的相同内存地址
Same memory address for different processes
我只是想不通为什么这段代码会这样工作(而不是我期望的):
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>
#include <sys/types.h>
int main()
{
int buffer;
int* address;
address=&buffer;
if(fork()==0)
{
*address=27;
printf("Address %ld stores %d\n",(long)address,*address);
exit(0);
}
wait(NULL);
printf("Address %ld stores %d\n",(long)(&buffer),buffer);
return 0;
}
为什么系统存储不同的变量,即使它们指向相同的内存地址?
注意:我从来没有真正期望过这段代码能工作,否则所有的管道和东西都没有任何意义;我只是想了解这里发生了什么。
这不是真正的 C 问题,而是关于(现代)操作系统的行为。
简而言之:现代 OS 上的用户space 程序在一些私有 虚拟 地址 space 中运行。访问内存时,虚拟地址被转换为物理地址。实际内存和虚拟地址space之间的映射是由操作系统设置的——内存被分成页,一个页可以"mapped"到一个进程的地址space。
fork()
通常只是将相同的内存映射到它创建的第二个进程,但是一旦写入此内存,就会复制页面并映射副本 ("copy on write")。用户 space 程序永远不会看到其他用户 space 程序私有的内存。
我相信您可以通过搜索此答案中给出的关键词轻松找到更多详细信息。
From wikipedia:fork 操作为 child 创建了一个单独的地址 space。 child 进程拥有 parent 进程所有内存段的精确副本。
所以基本上您创建了一个新进程,其中包含原始进程内存的不同 COPY。
您在复制进程的内存中更改了一些内容,它是相同的,但只是一个副本,并希望在原始进程中看到它。
通常,进程不直接共享内存。
我只是想不通为什么这段代码会这样工作(而不是我期望的):
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>
#include <sys/types.h>
int main()
{
int buffer;
int* address;
address=&buffer;
if(fork()==0)
{
*address=27;
printf("Address %ld stores %d\n",(long)address,*address);
exit(0);
}
wait(NULL);
printf("Address %ld stores %d\n",(long)(&buffer),buffer);
return 0;
}
为什么系统存储不同的变量,即使它们指向相同的内存地址?
注意:我从来没有真正期望过这段代码能工作,否则所有的管道和东西都没有任何意义;我只是想了解这里发生了什么。
这不是真正的 C 问题,而是关于(现代)操作系统的行为。
简而言之:现代 OS 上的用户space 程序在一些私有 虚拟 地址 space 中运行。访问内存时,虚拟地址被转换为物理地址。实际内存和虚拟地址space之间的映射是由操作系统设置的——内存被分成页,一个页可以"mapped"到一个进程的地址space。
fork()
通常只是将相同的内存映射到它创建的第二个进程,但是一旦写入此内存,就会复制页面并映射副本 ("copy on write")。用户 space 程序永远不会看到其他用户 space 程序私有的内存。
我相信您可以通过搜索此答案中给出的关键词轻松找到更多详细信息。
From wikipedia:fork 操作为 child 创建了一个单独的地址 space。 child 进程拥有 parent 进程所有内存段的精确副本。
所以基本上您创建了一个新进程,其中包含原始进程内存的不同 COPY。 您在复制进程的内存中更改了一些内容,它是相同的,但只是一个副本,并希望在原始进程中看到它。 通常,进程不直接共享内存。