Сборка x86: Какой главный пролог и эпилог? - PullRequest
0 голосов
/ 12 ноября 2009

Я следую этому руководству на сборке x86. Каждый пример до сих пор использует то, что автор называет программой «c-driver», скомпилированной с модулем сборки, для некоторой «инициализации». Что-то вроде:

int main(void) {
  int ret = asm_main();
  return ret;
}

А затем функция asm_main пишется нормально, с использованием соглашения о вызове C. Мне интересно, что именно является обязательной инициализацией, генерируемой компилятором C, и может ли она быть выполнена переносимым способом.

Информация: я на Windows XP, 32-битная коробка, использую ассемблер NASM и mingw32-gcc для компоновки.

Ответы [ 3 ]

5 голосов
/ 12 ноября 2009

Инициализация не генерируется компилятором c, она является частью библиотеки c (что облегчает адаптацию для каждой ОС / процессора).

Данный код обычно очень прост в системах Windows / Unixy - обычно выполняет небольшую инициализацию библиотеки (открывает STDIN, STDOUT, STDERR, устанавливает часовой пояс и т. Д.), Настраивает среду, обрабатывает командную строку для передачи в main ; перехватывает возврат из main (), вызывает выход и т. д.

Код запуска в большинстве библиотек c находится в файле с именем crt0.c, crt1.c или чем-то похожим (crt = время выполнения c).

В более примитивных или «голых» системах он также настроит стек и другие регистры и очистит область данных BSS - в этом случае это часто будет в ассемблере (обычно crt0.S).

Вот ссылка на код запуска BSD c - текст ссылки

А код запуска для Mingw для Windows находится здесь в crt1.c - http://mingw.cvs.sourceforge.net/viewvc/mingw/runtime/

0 голосов
/ 13 ноября 2009

Стек, регистры и разделы файла программы (data, rodata, bss и т. Д.) Должны быть инициализированы перед вызовом main (). C runtime library (CRT) обеспечивает эту инициализацию.

CRT также предоставляет пролог и код эпилога, которые выполняются до и после вызова каждой функции. Код пролога и эпилога обновляет указатели стека и фрейма.

0 голосов
/ 13 ноября 2009

Вы можете написать свой основной в сборке, если хотите. Но многие люди хотят поместить отладочные операторы в основную, и они проще в C, чем в asm.

Если вы написали main в asm, вам, возможно, придется иметь дело с main, фактически называемым _main или использующим альтернативное соглашение о вызовах (особенно в Windows), или с другими странными вещами, подобными тем, которые компилятор C обрабатывает для вас автоматически при создании кода для функция с именем «основной». Таким образом, вы тоже не должны этого делать.

...