Ответ 1
Слово main
является юридическим именем для любой переменной. Типичным вариантом использования является предоставление функции имени main
компилятору, который компилирует его в файл объекта, который, в свою очередь, связан с crt0.o
, который обеспечивает инициализацию для времени выполнения (распределение стека и т.д.), и перескакивает на метку main
.
В объектных файлах C символы не связаны с прототипами, и компоновщику удается привязать глобальную переменную int main;
к главной программе, к которой нужно подпрыгнуть. Однако эта программа является мусором. Скорее всего, он инициализируется как нули, но вскоре процессор встречает либо случайную инструкцию, которая обращается к памяти за пределами распределенного пространства программ (стек + куча), либо поток команд достигает пределов зарезервированного кодового пространства.
Оба будут вызывать ошибку сегментации. И на самом деле, если система работает с архитектурой с флагами eXecution, программа segfaults с первой попытки перейти на сегмент данных или страницу без разрешения на выполнение.
Дальнейшее чтение для поддержки обсуждения в комментариях: Предотвращение выполнения данных, NX_bit