Кто получает значение, возвращаемое main ()?


34

Я знаю, что в компьютерах значение, возвращаемое main()функцией, получает операционная система. Но что происходит в main()функции микроконтроллера?


7
Я всегда использую void main (), когда использую C для микроконтроллеров PIC. При использовании компиляторов Си для микроконтроллеров это действительно не имеет значения. Потому что нет операционной системы, которая запускает (скажем) "main.c". Если в этом микроконтроллере работает что-то вроде RTOS, то операционная система - это main.c.
Абдулла Кахраман

4
Не совсем дубликат, но, по крайней мере, связанный: electronics.stackexchange.com/q/30830/4950
PetPaulsen

1
Как определяется функция запуска, обычно решать не вам. Среда, которую вы используете, документирует поддерживаемые формы функций запуска. Внедренные реализации C должны поддерживать две формы mainс двумя разными сигнатурами, обе из которых возвращаются int. Если вы используете автономную реализацию C, эта реализация диктует, как вы должны написать функцию запуска. Вы не можете написать voidвозвращающую функцию только потому, что она не возвращает. Поведение не возврат отличается от функции типа , которая влияет на общие соглашения о вызовах.
Каз

Ответы:


42

На микроконтроллере main()не ожидается, что он когда-либо завершится, а поведение, если оно не определено, - это зависит от того, кто написал время выполнения C для микроконтроллера. Я видел системы, которые:

  • Имейте неявный цикл вокруг main(), так что если он выходит, он просто вызывается снова.
  • Имейте простой цикл "прыжок к себе", который выполняется, если main()когда-либо выйдет.
  • Просто выполните остальную часть памяти кода, которая следует за вызовом main(). Это называется "убегать в сорняки".

Я никогда не видел такой, которая вообще что-то делает с возвращаемым значением main(). Если это то, что вас действительно волнует, то вам следует взглянуть - и, возможно, изменить - исходный код библиотеки времени выполнения C вашей системы.


1
Ты подтолкнул меня на это. +1 за синхронность.
Адам Лоуренс

9
Стандарт C определения main()иметь intвозвращаемое значение , очевидно , не был разработан с OS-менее микроконтроллером в виду. Так что это неопределенное поведение, и может произойти все что угодно в зависимости от вашей среды выполнения C, как перечислил Дейв.
ndim

4
C работает на OS менее микроконтроллер может рассматриваться как автономная реализация, а стандарт C не требует даже автономный environent , чтобы иметьmain() , гораздо меньше , определить ее возвращаемое значение. Это зависит от разработчика.
KutuluMike

2
@ndim - мудрить, void main( void )является реализация определяется поведение , не определено поведение .
Андрей

1
@MichaelEdenfield: Действительно. Тем не менее, весь код в C определен в терминах функций, поэтому никогда не представляется возможным иметь совершенно уникальную систему, полностью написанную на C; должен быть хотя бы небольшой кусочек ассемблера (или чего-то еще), который устанавливает минимальную среду для вызова функции Си. Наиболее очевидное имя для этой функции main().
Дэйв Твид

5

Распространенное недоразумение / миф о том, что int mainэто единственная действительная форма, указанная в стандарте. Это неправда.

Стандарт C говорит о двух реализациях: размещенный и автономный. «Реализация» в данном случае означает компилятор. Размещенные компиляторы компилируются для конкретной ОС, а автономные компиляторы компилируются для конкретного приложения с открытым исходным кодом. Встраиваемые системы почти всегда являются автономными системами - даже в случае RTOS.

Отдельно стоящие реализации могут использовать любую форму main(), им даже не нужно иметь функцию с именем main. Чаще всего они используют форму void main (void), поскольку возвращать что-либо бессмысленно.

Важно понимать, что компилятор всегда определяет форму, main()а не программист.

Отдельно стоящие реализации, которые действительно что- то возвращают main(), очень сомнительны. Заставляет задуматься, действительно ли люди, создавшие компилятор, читают стандарт ...

Подробности здесь .


3

Стандарт языка C допускает изменение, определяемое реализацией, void main( void )и это обычная форма во встроенных системах - просто потому, что они не должны возвращаться.

Если вы посмотрите на настройку компилятора, обычно есть фрагмент кода начальной загрузки, вызываемый из вектора сброса, который выполняет некоторую базовую инициализацию (включая, например, копирование значений инициализации в переменные) перед вызовом main ().

Это также (обычно) будет в бесконечном цикле, или, возможно, выполнить сброс, если main()возвращает


0

Это (как упоминалось в других ответах) зависит от вашей цепочки инструментов, но, например, в GCC mainкомпилируется как другие функции, поэтому его возвращаемое значение будет сохраняться в соответствии с соглашениями о вызовах (в ARM я использую право, а не в GCC, оно будет помещено в R0 как раз перед возвращением).

Я полагаю, что это аналогично AVR-GCC, поэтому пользовательский скрипт может использовать это значение после основного возврата.


это скорее не соответствует сути
Крис Страттон

Это подчеркивает, что тот, кто звонит, mainможет получить его возвращаемое значение. Конечно, это игнорируется в 99,9% ситуациях, но ответ предоставляет информацию, кто может получить это возвращаемое значение.
kwesolowski
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.