Почему адрес переменной дочернего процесса и родительского процесса одинаков
вот мой код
int main()
{
pid_t pid;
int y = 3;
if ( (pid = fork()) <0 )
return -1;;
if( pid == 0 ) /* child */
{
printf(" before: %d %pn", y, &y );
y *= 10;
printf("after: %d %pn", y, &y );
}
else /* father */
{
sleep(1);
printf("father: %d %pn" , y , &y );
}
return 0;
}
вывод программы выглядит следующим образом:
before: 3 ffbff440
after: 30 ffbff440
father: 3 ffbff440
мой вопрос в том, почему адрес переменной дочернего и родительского одинаков, но значение отличается?
2 ответов
потому что это виртуальный адрес, а не физический.
каждый процесс получает свое собственное адресное пространство (например, 32-разрядная система может позволить каждому процессу иметь свое собственное адресное пространство с полным диапазоном 4G).
это блок управления памятью, который будет сопоставлять виртуальные адреса с физическими (и обрабатывать такие вещи, как ошибки страниц, если замененные страницы должны быть выкуплены из вторичного хранилища).
следующая диаграмма может помочь, каждый раздел, представляющий блок памяти 4K:
Process A Physical Memory Process B
+-------+ +-------------+ +-------+
0K | |----> 0K | (shared) | <----| | 0K
+-------+ +-------------+ +-------+
4K | |--+ 4K | | <----| | 4K
+-------+ | +-------------+ +-------+
8K | | +-> 8K | | | | 8K
+-------+ +-------------+ +-------+
| : : : : : : : |
| +-------------+ |
| 128K | | <--------+
| +-------------+
+--------> 132K | |
+-------------+
вы можете видеть на этой диаграмме разъединение между адресами виртуальной памяти и адресами физической памяти (и возможность для процессов совместно использовать блоки памяти). Адреса слева и справа-это виртуальные адреса, которые видят процессы.
адреса в центральном блоке являются фактическими физическими адресами, где данные "действительно" есть, и MMU обрабатывает отображение.
для более глубокого объяснения fork
(и exec
), вы также можете посмотреть ответ.
адрес "такой же", как у каждого процесса есть собственное виртуальное адресное пространство, и переменная обычно загружается в одно и то же место. Обратите внимание, что это не физический адрес в памяти. Также обратите внимание, что существуют схемы, которые преднамеренно рандомизируют местоположение, в котором загружается процесс, чтобы затруднить атаку/взлом процесса. В таком случае адрес будет другим.