Я ныряю в реверс-инжиниринг, что очень весело.
Однако у меня есть вопрос: почему адреса инструкций, которые я получаю от GDB и Objdump, совпадают?
Разве двоичный файл не должен каждый раз загружаться по разному адресу?
Спасибо. Жюльен
... и каждый процесс получает собственное виртуальное адресное пространство, поэтому фиксированные адреса не создают риска конфликтов адресов.
Да вы оба правы на самом деле, я не думал об адресном пространстве. Спасибо за ответы, ребята.





GDB по умолчанию отключает ASLR. Если у вас set disable-randomization off, то исполняемый файл PIE (Position Indepdent) будет загружаться по случайному адресу, даже если вы run его изнутри GDB.
См. 32-битные абсолютные адреса больше не разрешены в x86-64 Linux? для получения дополнительной информации о PIE.
Исполняемые файлы Position-зависимый загружаются по тому же адресу всегда, и только их адрес стека может быть рандомизирован. Код + данные могут жестко закодировать адреса как 32-битные абсолютные, и они не содержат информации о перемещении для каждого места, где это было сделано. (например, как mov $string, %edi; call puts).
Посмотрите на gcc code-gen для Hello World с / без -fPIEв обозревателе компилятора Godbolt.
.LC0:
.string "Hello World!"
main:
lea rdi, .LC0[rip] # RIP-relative with -fPIE
sub rsp, 8
call puts@PLT
xor eax, eax
add rsp, 8
ret
но с -fno-PIE (по умолчанию в Godbolt, часто не по умолчанию в современных дистрибутивах Linux) вы получаете mov edi, OFFSET FLAT:.LC0, 32-битный абсолютный адрес.
(Остальной код тот же, за исключением того, что он излучает call puts и позволяет компоновщику преобразовать его в call puts@PLT. Используйте -fno-plt, чтобы встроить косвенный call через адрес GOT.)
Традиционно в Unix двоичные файлы загружаются по фиксированным адресам. У вас могут быть двоичные файлы, адрес загрузки которых определяется только во время выполнения, это называется PIE (исполняемый файл, независимый от позиции).