Зафиксирован ли первый переменный адрес в основной функции? - PullRequest
0 голосов
/ 08 мая 2019

Когда я пытался напечатать адрес первой переменной в основной функции, я обнаружил, что результат всегда один и тот же после запуска несколько раз.Зачем?Это в виртуальной памяти или физической памяти?

#include <stdio.h>

int main()
{
    int a;

    printf("a's address is %p\n", &a);

    return 0;
}

Я ожидаю, что вывод будет отличаться каждый раз, но фактический вывод всегда будет 0028FF3C

Ответы [ 3 ]

5 голосов
/ 08 мая 2019

В некоторых системах ASLR включен и по уважительным причинам.

Например, на моем Linux / Debian / Sid x86-64 ваша программа каждый раз дает разные адреса:

repeat 10 tmp/sange
a's address is 0x7fff2768303c
a's address is 0x7ffc5d26a57c
a's address is 0x7ffcc0a4b2ac
a's address is 0x7ffeec95fd7c
a's address is 0x7ffefd5318dc
a's address is 0x7ffc544497bc
a's address is 0x7fff232f7dac
a's address is 0x7fff9dd3b65c
a's address is 0x7fff9e6858dc
a's address is 0x7ffc2876d4bc

Чтобы узнать больше, прочитайте о неопределенное поведение (например, блог Латтнера ), неопределенное поведение и прочитайте хороший учебник по операционным системам, например, Операционные системы: три легкие пьесы (свободно загружается)

Читайте также о виртуальном адресном пространстве .

3 голосов
/ 08 мая 2019

Нет адрес не является фиксированным.

Ваша ОС должна решить, куда загружена программа и, следовательно, какому адресу назначена переменная.

Если физический адрес является виртуальным, это также зависит от вашей ОС.Он решает, как управлять памятью.

2 голосов
/ 08 мая 2019

В любой обычной многопользовательской операционной системе адреса в вашем процессе будут виртуальными.Это связано с тем, что в обычных многопользовательских операционных системах операционная система использует виртуальные адресные пространства для обеспечения независимости программ друг от друга.

Адресное пространство вашей программы частично устанавливается процессом, называемым загрузчиком., который загружает исходные данные и код вашей программы в память.Простой загрузчик запустит стек новой программы в фиксированном месте - он будет использовать одно и то же начальное местоположение каждый раз, когда загружает программу.Затем, когда ваша программа запускается, a всегда будет по одному адресу.Загрузчики работали таким образом в течение многих лет.

Поскольку злоумышленники иногда могут использовать известные адреса стеков для атаки и подрыва программного обеспечения, некоторые загрузчики теперь используют случайные адреса при загрузке программ.Это называется рандомизацией размещения адресного пространства (ASLR).Когда ваша программа загружается с загрузчиком, использующим ASLR, адрес a будет изменяться от запуска к запуску.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...