Pull to refresh

Comments 230

Да, есть такой метод, с перемещением стека в начало ОЗУ.

Но по сути спасает только от неопределённого поведения при выходе стека за допустимый размер, заменяя его на хардфолт. При разработке хоть какое-то профилирование всё равно нужно.
И, кстати, это только для MSP работает.

PSP — это просто куски памяти где-то в bss.
PSP это не куски памяти, это такой же регистр как и MSP, только с одним исключением — его гарантировано не будут использовать прерывания. А на что каждый из регистров указывает, решать программисту.
De facto это куски памяти в bss. Объявленные обычно просто как массивы в приложении. Особенного положения у стеков процессов нет и не будет просто в силу того, что стеков процессов — обычно несколько больше, чем возможно особенных положений.
Всмысле «только» спасает? Также вам позволяет в микроконтроллере без MPU отловить проблемное место, войти в безопасный режим или вообще перезагрузится с сохранением состояния без ведома пользователея (все зависит от сложности програмы).
Нет у вас никакого безопасного режима, у вас есть BusFault (или вообще сразу HardFault) по неизвестной вам причине. В этот момент вы уже ничего не знаете о том, живо ли там вообще какое-либо состояние.

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

Так что помогает это только в отладчике.
Попадание в любое исключение уже указывает на проблему, что не мешает Вам ввести МК в «безопасный» режим. Этот режим и что это вообще такое, определяется проектом. Вы можете сделать дамп стека, регистров, записать лог… Оставить след в рам памяти. Сделать сброс, в стартапе проверив, не был ли сброс по причине ошибки. То что Вы не знаете как такое делается, не значит что такое невозможно.
Вы можете сделать дамп стека


Какого стека? Того, который только что записался в никуда, вызвав хардфолт?

То что Вы не знаете как такое делается, не значит что такое невозможно.


Ну началось.

Вообще-то с высокой степенью достоверности именно это и значит. Вы даже причину сбоя определить не сможете, так что какое вам счастье со знания, что перезагрузка была вызвана сбоем — сказать трудно.
Что имеет смысл дампить, зависит от причины, которую (еще раз повторюсь) можно определить. Я перечислял возможности, а не указал последовательный список действий.
которую (еще раз повторюсь) можно определить


Нет, нельзя. В рантайм-коде в общем случае нельзя определить причину, по которой система грохнулась в хардфолт.
Для любого ответственного применения безопасный режим обязателен. То есть краны закрыть, все горящее — притушить, окна-двери — разблокировать. Ну в общем сделать так.чтобы если что — поменьше народу погибло. Безопасный режим желательно дублировать на разных слоях аппаратуры. Притяжки к 0 и 1 вне SoC — это первый слой, на случай, если нет питания на плате. Притяжки в STM32Cube — второй слой, но они отрабатывают не сразу после старта. поэтому для быстрых процессов делается третий слой — притяжки при вылете HardFault ему подобным.

В рантайм-коде в общем случае нельзя определить причину
В общем случае нельзя, а в частных — можно. Ту же окраску памяти при помощи 0xDEADBEAF проверить.

Логика тут такая. Получив полный ламп, программист за месяц найдет причину с вероятностью 99.99%. Далее ничего не мешает написать код, который бы выявлял признаки именно этой ситуации. И так — со всеми ситуациями, которых на отлаженной программе — немного.

Ну как пример. 25 лет назад у меня при включении холодильника дважды перезапускался процессор клавиатуры. Сначала первый перезапуск, а следом — второй. Поэтому последовательность инициализации выдавалась в полуторном размере, а BIOS такого не понимал.

Случай был настолько вырожденный (всего одна причина слета), что я просто написал резидента к MS-DOS для исправления влияния холодильника.

Так что в общем случае нельзя, а в частных — делаем вероятностно на известные причины.
Для любого ответственного применения

Притяжки в STM32Cube


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

но они отрабатывают не сразу после старта. поэтому для быстрых процессов делается третий слой — притяжки при вылете HardFault ему подобным


Это, конечно, чушь.

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

Во-вторых, обработчик hard fault вам с этими подтяжками никак не поможет, потому как из него вам таки надо будет перезагрузиться, в результате чего все ваши ножки мгновенно встанут в режим входа, см. выше.

В-третьих, есть всего две вещи, в которых вам может помочь обработчик hard fault, и ни одну из них вы не упомянули. Это либо немедленно перезагрузиться, либо, наоборот, выставить ножки в состояние по умолчанию и навсегда уйти в while (1) — то есть повиснуть до вмешательства оператора.

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

В общем случае нельзя, а в частных — можно. Ту же окраску памяти при помощи 0xDEADBEAF проверить.


Опять чушь.

Во-первых, то, что у вас окраска затёрта, могло случиться по тысяче причин, и переполнение стека — лишь одна из них. Вовремя не остановившийся while легко вытрет вам всю память вообще, пока либо не грохнет вам стек, либо не дойдёт до дырки в адресах. Никак в рантайме определить, что именно случилось, вы не сможете.

Во-вторых, ничем вам это всё равно не поможет. На момент hard fault у вас система в неопределённом состоянии и продолжать работу не может, путь у вас один — перезагрузка.

Логика тут такая. Получив полный ламп, программист за месяц


Вы уверены, что это — про рантайм?

Случай был настолько вырожденный (всего одна причина слета), что я просто написал резидента к MS-DOS для исправления влияния холодильника


Подпёрли дырку костылём то есть.
Вы правда для ответственных применений пользуетесь простынками, сгенерированными кубом?..
А чем они хуже сгенеренных руками в смысле надежности? Поскольку STM32 c ни с пятой, ни с девятой приемкой не бывает, то для ответственных применений не она. А для автовождения комбайна зато — в самый раз. Там вообще вся панель приборов — на бортовом компе, работающем на андроиде.

Во-первых, до того, как у вас инициализировалась периферия и ножки программно переключились в нужные режимы, они находятся в режиме входа, то есть — работают внешние подтяжки.
Если делаете что-то отказоустойчивое, не путайте «должны находиться» с «находятся». Да, должны, но опыт STM32H7 показал, что не всегда RESET сбрасывает все. Ну и errata никто не отменял.

то, что у вас окраска затёрта, могло случиться по тысяче причин, и переполнение стека — лишь одна из них.
И что??? Вам нужна теоретическая надежность в семь девяток? Или реальная помощь персоналу по замене неисправного блока? Если второе, то 80% надежность при диагностике «сдох БП», «сдох процессорный блок», «сдохло УСО» вполне помогает сократить время ремонта.

путь у вас один — перезагрузка.
Путей, вообще-то 4:

  1. Перезагрузка и работа в полном режиме.
  2. Перезагрузка и работа с деградацией функций
  3. Передача управления резервному блоку
  4. Останов до оценки персоналом.


Вы уверены, что это — про рантайм?
Угу. Приходилось. Вплоть до отладки драйверов через лампочки передней панели на больших машинах. Ну и через gdb при hardfault на той же STM32.

Подпёрли дырку костылём то есть.
Менять холодильник или покупать ИБП было сильно дороже. не говоря уж о том, чтобы перепрограммировать процессор серийной клавиатуры. 1993 год, вообще-то был. С деньгами очень негусто было.
А для автовождения комбайна зато — в самый раз.
Вероятность инцидентов с человеческими жертвами в результате плохой работы автопилота серийного комбайна гораздо выше, чем в результате работы большинства девайсов с приемкой — просто потому, что комбайнов больше, и работают они дольше.
А можно сценарий хоть одного инцидента именно из-за автопилота комбайна? А что-то ничего в голову не приходит.

Автопилот комбайна, как и автопилот самолета — это устройство, обеспечивающее ведение по заданной траектории. Водителя оно не заменяет, скоростным режимом не управляет.

На самолетах было всего несколько случаев, когда неверный монтаж автопилота вызвал раскачку. Причиной катастрофы было то, что летчики не поняли, что причина именно в автопилоте. Ибо реальных причин в самолете может быть много. Но хождение комбайна по синусоиде очень легко диагностируется, а сам автопилот отключается движением руля.
Некорректное сравнение автопилотов самолета и комбайна, следовательно, Вы не до конца представляете, как работает автопилот на современном самолете.
ОК, расскажите. Только не путайте автопилот с FMS, FADEC, АБСУ и иными блоками.

Система АБСУ-134 состоит из автопилота АП-134, автомата тяги АТ-5, системы траекторного управления СТУ-134 и аппаратуры ухода на второй круг.

Так что жду рассказа про крутость автопилота.

А я вам в сою очередь расскажу про уровень техники современного самолета. В своё время полез разбираться, что за GPS-приемник работает на A-320/A321.

Когда говорят «GPS-приемник», вы что себе представляете? Маленькую микросхему на плате? Вес GPS-приемника A320 — под 20 килограмм. Компонентная база — 80ых годов.

Характеристики — точность 10 метров 50% времени, остальные 50% — хуже (до 30 метров). Для сравнения современный бытовой приемник 50% времени дает точность до 3х метров, остальные 50% — до 10 метров.

Само собой — только GPS и SBAS, всего-навсего 12 каналов. В современных приемниках меньше 32 каналов не бывает.

Единственное достоинство этого гроба — он не ломается.

Да, его сейчас заменяют. На гроб примерно уровня 2000 года. Там ещё и ГЛОНАСС есть. Но ни GALILEO, ни BEIDOU, ни QZSS…

Ну а теперь ваш рассказ про сложности самолетного автопилота.
Только не путайте автопилот с FMS, FADEC, АБСУ и иными блоками.

Не путаю, у меня на работе под боком сидит один из разработчиков FADEC. Называть явки и пароли не могу по определенным причинам.
Жду рассказа про крутость автопилота.
Смысл рассказывать что-то человеку, который не видит разницы между автопилотом летательного аппарата и наземной самоходной тележки.
И в который раз прошу — приоткройте тайну.

Разница-то у них есть, у комбайна — всего один канал вместо трех у самолета. Но оба устройства — простые.

Ну как минимум простые по сравнению с GPS-приемником или с нашим RTK. Или с тем, что называют автопилотом легковых автомобилей.
По Вашему мнению, автопилот летательного аппарат проще GPS-приемника?!
И ещё раз прошу — расскажите про сложности автопилота.

Первые автопилоты были вообще гидравлические. Там ведь все просто — на каждый канал PID-регулятор. Максимум -ещё фильтр Калмана.

А GPS-приемник — очень сложная штука. Например, сотые герца меряет. Могу рассказать, если хотите. Хотя мы сами приемники не делаем, мы их используем для RTK
А GPS-приемник — очень сложная штука

Раньше люди картами пользовались и GPS-приемники не нужны были.
И не надо мне рассказывать про радиочасть приемника.
Вы постоянно ссылаетесь на GPS-приемники, похоже ничего больше не видели и не о чем больше не знаете. И в разработке ни с чем другим не имели дело.
А что там сложного в радиочасти? Радиочасть там простенькая, все сложности после АЦП идут. Те же сотые герца — в цифровой части выделяются.

похоже ничего больше не видели и не о чем больше не знаете.
Хотите померяться? Ну давайте вначале ваш список. Пока что для затравки скажу, что если у вас в школе были УКНЦ, то вы и полторы моих программы использовали (одну написанную, и одну, переданную мне на поддержку).
Ну давайте вначале ваш список

У Вас доступ к совершенно секретным сведениям и гостайне есть?
Пока что для затравки скажу, что если у вас в школе были УКНЦ, то вы и полторы моих программы использовали (одну написанную, и одну, переданную мне на поддержку).

Программы, написанные мной, использовались в одно время для обучения студентов. Возможно, их еще продолжают использовать. Курс лабораторный-практических занятий по силовой электронике был составлен при моем участии. Вам еще написать, где я руку приложил к учебному процессу? И заметьте в ВУЗе, а не в школе! Нашли чем похвастаться.
Угу. Приходилось. Вплоть до отладки драйверов через лампочки передней панели на больших машинах


А вы вообще замечаете, что с логикой беседы у вас — ну, так себе? Вы каждый раз уверенно отвечаете не на тот вопрос, который вам задавали.

В ответ на вопрос о надёжных способах профилирования памяти — рассказ о мажоритарном троировании, о диагностике в рантайме — рассказ о программисте, месяц ковыряющем дамп памяти, о том, какое отношение этот дамп имеет к диагностике рантайму — уже пошли какие-то лампочки и «gdb при hardfault» (который, очевидно, опять — не диагностика в рантайме).

При этом вы ещё практически в каждом вашем тезисе умудряетесь и откровенной чуши добавить.
Извините, штатный телепат в отпуске. Я не обязан догадываться, что было у вас в голове, когда вы писали свои вопросы.Это пусть ваши школьники гадают на кофейной гуще, какой ответ вы хотели получить.

В ответ на вопрос о надёжных способах профилирования памяти
Пардон, где этот вопрос? Вы не перепутали, кому его задавали? Приучаемся к взрослым методам ведения дискуссии — или признаете, что подобный вопрос мне не задавали или даете пруф.

А вопрос был "Например, чем?". И относился он не к профилированию памяти, а к методам создания надежных систем.

который, очевидно, опять — не диагностика в рантайме
Что вы называете диагностикой в рантайме? Выяснение причин вылета рантайма или диагностики, выполняемые в рантайме? Я писал про первое.

Если речь про второе, то есть богатый опыт, но с ПК, а не с микропроцессорами. Когда-нибудь допишу статью. Система проработала 15 лет без сбоев. Точнее без видимых пользователю сбоев, ибо внутренние сбои устранялись самой системой. Кстати, как раз с дублированием — два одинаковых сервера.

Диагностика строилась на постоянном использовании try-блоков. То есть в каждом методе — try...except… finally. Защита была многослойной — метод-объект-подсистема-тред-сервер. Впрочем, во многих случаях подсистема была эквивалентна треду. Каждый слой старался обработать исключение сам, если не мог — передавал вышестоящему слою. Для исключения долбежки применялись счетчики — 3 раза упали в одном месте — значит неверно восстанавливаемся, надо передать исключение выше.

Теперь о том. что вас больше всего интересует. Сервера работали по схеме мастер-слейв с теплым резервированием. Смена ролей шла двумя путями. Во-первых мастер, столкнувшись с неисправимой на уровне перезапуска тредов проблемой, сообщал слейву «я перезагружаться, побудь мастером», ну и уводил сервер в ребут. Во-вторых, слейв постоянно мониторил, жив ли мастер. Если мастер не подавал признаков жизни слейв брал его роль на себя.

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

Сервера менялись ролями примерно раз в 2-3 месяца — в основном из-за отключения питания во время ППР (планово-предупредительный ремонт стана). Сбои, приводящие к переключению — порядка раз в год.

Так что с прямыми руками — вполне пишется надежная система с дублированием. Увы, 20 лет прошло, забыл я о ней. Ну ОК, спасибо, что напомнили.
Пардон, где этот вопрос? Вы не перепутали, кому его задавали?


Практически везде, начиная с поста, под которым вы пишете ваши комментарии.

Что вы называете диагностикой в рантайме? Выяснение причин вылета рантайма или диагностики, выполняемые в рантайме?


Вы издеваетесь — или у вас русский язык совсем не родной? Диагностикой в рантайме называется диагностика, проводимая в рантайме. Которую тут обсуждали до вас, пока вы не пришли со своими бесконечными рассказами про то, как у вас GPS работает, не имеющими к этой теме никакого отношения вообще.

Остальную вашу простыню не читал.
Практически везде, начиная с поста, под которым вы пишете ваши комментарии.
Ну то есть в этом треде — нигде.

Остальную вашу простыню не читал.
Что явно показывает, что диагностика в рантайме вам неинтересна.

Вы тут в основном пытаетесь доказывать, что если вы чего-то не умете — то и остальные не должны это суметь сделать.

Байка про БРИЗ
На одном совещании в Москве академик долго и убедитльно доказывал, что приемник, принимающий одновременно GPS и ГЛОНАСС сделать невозможно. А потом встал директор Уманского радиозавода и сказал:
Мы этого не знали. Мы дураки. Мы сделали.
И это был первый в мире двухсистемный GNSS-приемник БРИЗ.

Так вот, мы дураки, мы сделали.
То есть даже этот конкретный тред вы до конца промотать не смогли, предпочтя вместо этого очередную байку о том, как вы отлаживали GPS.
Не обращайте внимание на пользователя olartam..., у него что-то «не то»

Он такие комментарии много где оставляет.
Интересно, а если я скажу, что статья — плохо написанное бессмысленное словоблудие, а в голове у автора недопереваренная каша?.. :)
Ну он привык общаться со студентами, поэтому и сам мыслит ближе к уровню полных чайников и учебных проектов.

Ну это примерно как учителя детям во втором классе объясняют, что 3 (коробки) на 4 пирожка — будет 12 пирожков. А если наоборот, это будет 4 (пирожка) на 3 коробки — 12 коробок, то есть неверный ответ.

Взрослые шизеют и воют в LJ, но на уровне второклашек — оно действительно так. Потому что они используют умножение как быструю замену сложения, а у сложения — одна размерность.

Вы можете сколько угодно объяснять учителю, что 12 — это все равно 12, но он все равно не примет ответ, ибо коробки — это не пирожки. А законы умножения -это третий класс, а не второй, потому не катят.

Ну и у olartamonov та же болезнь.
Просто «репорт» отпраляйте администрации.
Этот инфальтильный чувак гадости пишет не стесняясь.
У него явно проблемы со здоровьем.
У меня аналогичная деформация — много воспитывал подростков. Поэтому потерплю.

А администрация ему уже один аккаунт банила, насколько я помню.
Очень люблю читать посвящённую мне мифологию.
Помнится, когда вас забанили, вы писали с ника с ArbeitMachtFrei Вспоминаете такое?
Честно говоря, не очень — хотя бы потому, что если бы у меня был запасной аккаунт, мне не составило бы особой проблемы загнать его карму в приличные +20-30, а не как у вас, кхе-кхе.

Что ещё расскажете?

(до чувака, который ходил и всем рассказывал, что меня уволили из «Компьютерры» за джинсу, вы пока довольно сильно не дотягиваете; не говоря уж про создавшего целиком посвящённый мне сайт)
Ничего страшного, другие увидят. Ваше хамство — оно всегда с вами.
Вам пишут, что ваше поведение токсичное (по вашим комментариям к другим статьям), что вас уже банили здесь за ваш выходки, а вы отвечаете, про какой-то там сайт, который никому не интересен и не известен.
уволили из «Компьютерры» за джинсу


А также выгнали из гестапо за жестокость.

— С уважением,
Генрих Мюллер, группенфюрер
Ну это примерно как учителя детям во втором классе объясняют, что 3 (коробки) на 4 пирожка — будет 12 пирожков. А если наоборот, это будет 4 (пирожка) на 3 коробки — 12 коробок, то есть неверный ответ.

— на самом деле здесь не 4 пирожка, а 4 пирожка на коробку.
Поэтому 3 коробки * 4 пирожка/коробку = 12 коробка*пирожок/коробка = 12 пирожков (коробки сокращаются)
И, соответвенно, ничего не меняется при перестановке множителей
По третьему классу — вы правы. Но во втором умножение — это только замена сложения. Так что будет 3 коробки + 3 коробки + 3 коробки + 3 коробки = 4 * 3 коробки = 12 коробок.

Взрослым странно, но второклашкам так понятнее.

Буква М — методика.
если 4*3 коробки = 12 коробок, значит «4» у нас был безразмерный множитель типа «штуки» — тогда причем там пирожки?
а если 4 пирожков на коробку * 3 коробки = 12 пирожки*коробки/коробки = 12 пирожков (коробки опять сократились)
По-моему, даже второклассникам надо объяснять как оно на самом деле, а не как им понятнее. Особенно если это «понятнее» означает необоснованные требования к расстановке множителей.
По-моему, даже второклассникам надо объяснять как оно на самом деле, а не как им понятнее.
Будьте любезны, дайте ссылку на исследование.

Дети бывают разные. Одни в 11 лет идут в 10ый класс, другие — в 8 в первый.

По личному опыту (работал на продленке с весны 1978ого по весу 1981ого) + обучение пары детей чтению методики, увы, придумываются не зря.

Объясняешь ребенку, что надо сложить Д + А и получить ДА — а ребенок не понимает. Ну не получается у него. Обзываешь себя бездарью, берешь букварь и делаешь строго по букварю. Опаньки — и у ребенка все получается. Шаг влево-вправо от букваря — опять очень сложно.

Так что нужно исследование, показывающее успеваемость при вашем способе преподавания в сравнении со стандартной методикой.

«4» у нас был безразмерный множитель типа «штуки» — тогда причем там пирожки?
Не при чем. Умножение водится вначале как сокращенная запись сложения. Это не полноценное умножение, а понятный второклашкам эрзац.

И лишь когда они выучили таблицу умножения и свыклись с тем, что можно умножать — вводится полноценное умножение.

И дело тут примерно в трети детей, которые без этой связки (умножение — всего лишь быстрое сложение) не могут освоиться с умножением.

При этом в момент ввода умножения процентов 10 детей проверяют сложение «на пальчиках».

Они не тупые. И, в основном, не прирожденные двоечники. Это просто кинестетики. А вы сами — скорее всего дижиталы.

В 1986-1987ом я участвовал в эксперименте. Взяли детей, выброшенных школой за неуспеваемость в ПТУ и учили их математике по методике, придуманной Марком Ивановичем Башмаковым специально для кинестетиков. Смешно сказать, 10ый класс — а мы занимаемся с ними квадратными уравнениями.

А вот дальние итоги были такие — больше половины основного состава закончили институты. Одних программистов пяток оттуда вышел.

Так что методика, при которой треть класса не понимает, что такое умножение, а 10% — так и не могут научиться умножать — заведомо плохая методика.

Ну и последнее. То, как меня учили — это результат Колмогоровской реформы. Если не лень — посмотрите, как вводит умножение Башмаков. Ну и как все остальные, у нас сейчас есть 5-6 программ для начальной школы. Найдете вариант по душе — читайте отзывы и результаты экспериментов.

Своего ребенка — можете обучать как хотите. Но если ребенку трудно — признайте себя (а не ребенка) бездарью и идите ровно по методике.

Мне лично умножение тоже было понятно до того, как его начали проходить в школе. Но я — дижитал, призер Питера по математике, и я по себе других детей не ровняю.
Ах вот откуда вы такие беретесь, у которых 3*4 не равно 4*3. Ясно-понятно.
Мне в комментарии советовали потрогать DebugMon, который, по идее, позволит отделить хардфолт от переполнения стека, но сходу у меня это не заработало и дальше я пока не копал.
Может у вас получится?
DWT — это опциональные системные регистры; они, с одной стороны, определены ARM'ом, а не конкретным производителем, с другой — их наличие и функциональность в конкретном продукте отданы на откуп производителю.

Может не быть вообще, может быть не быть конкретно точек останова — надо смотреть документацию на конкретный контроллер.
Это да, но ваша статья-то про STM32; там эта функциональность вроде как присутствует.
Там целая пачка нюансов.

Во-первых, надо смотреть в конкретной серии процессоров, ибо ARM нам сообщает, что «The DWT unit can include between 0 and 15 comparators» — т.е. само по себе наличие DWT не означает, что он имеет конкретную функциональность. Во-вторых, с DWT также есть засада — он настраивается на конкретный адрес, и если сбоящая функция этот адрес «перешагнёт», то DWT ничего не заметит. В-третьих, DWT асинхронный и он сам не останавливает текущую операцию, т.е. проблема с тем, что ошибку-то мы заметили, а дальше нам остаётся только перезагружаться, потому что система находится уже в неопределённом состоянии, никуда не исчезает.
Вообще-то в некоторых из STM32 есть MPU, и его тоже можно для этого использовать.
К чему этот комментарий? Я знаю о существовании MPU, в статье же указаны микроконтроллеры без него, и даже без него есть варианты того, что можно сделать.

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

Этого мало, надо избавиться от рекурсий, callback-ов.
Еще можно запустить программу под отладчиком и поставить breakpoint в какой-нибудь самой-самой вложенной функции. Там посмотреть либо сам стек целиком, либо хотя бы Stack Pointer.
Чтобы узнать, сколько свободной памяти у нас есть, нужно включить создание Linker Map File и посмотреть сколько занимают глобальные переменные. Неиспользованный остаток можно отдать на стек.
Если ваш микроконтроллер совсем имеет совсем крошечный объем памяти, например какой-нибудь AVR Tiny, не используйте стандартные функции работы со строками sprintf, printf. Они очень неслабо жрут память, т.к. универсальные по своей природе. Напишите свои функции, узко заточенные именно под ваши нужды, например, только под вывод unsigned char.
Абсолютно согласен с вами. Отладчик и MAP-файл позволяют решить эти проблемы. Ну, и конечно же минимизировать вложенные функции, кол-во аргументов сделать поменьше. А динамическая память и рекурсия вообще противопоказаны. Компилятор даже кое-что показывает: linking…
Program Size: data=119.5 xdata=2323 const=303 code=15011
(у меня не ARM, но суть та же).
Где-то в конце статьи должна быть приписка, что если вы делаете не домашний термометр, а автопилот или систему управления АЭС, то надо пользоваться не этим методом, а гальванической развязкой чем-то более продвинутым и, желательно, стандартизованным.
Не знаю( Вы же специалист, а не я. Я серьезно сейчас, если что.
Но мне кажется, что для ответственных применений должно существовать что-то более надежное, хотя, конечно, вы правы в том, что этот метод покрывает подавляющее большинство возможных проблем.
Так и я серьёзно. И Ганссл серьзно.

Инструментов, которые достоверно при статическом анализе кода определят размер нужного стека, вообще нет.

Инструменты, которые позволят в рантайме поймать переполнение надёжнее, чем окраска памяти — есть, но не во всех контроллерах.
На ум сразу приходит статический анализ кода для оценки потребления программой стека, но он если и возможен, то только в рамках чистых функций без side-effect-ов (т.е. не взаимодействующих с внешним миром), иначе проблема сводится к решению (нерешаемой) проблемы останова.
Даже безотносительно внешнего мира — два прерывания от разных таймеров с разным приоритетом для анализатора будут непреодолимой проблемой, потому как потребуют от него знания внутренней архитектуры контроллера, анализа времени выполнения каждого из прерываний и т.п.

Оценка здесь возможна только сверху — из обработчиков с одним приоритетом выбираем самый жирный, далее складываем полученное для разных приоритетов и добавляем к каждой из веток кода.

Ну и молимся, чтобы приоритет прерываний в рантайме не менялся.

P.S. И ещё анализаторы при построении структуры программы могут обламываться на вызове функций через указатели.
Например стандартизованными методиками IEC61508, сертифицированными тестами, проверяющими состояние буферной области стека, грамотно определенными безопасным состоянием системы и границами применимости.
Как вариант — четыре процессора, каждая пара сравнивает результаты после каждого такта (аппаратно), при сбое — управление переходит на вторую пару.

Второй вариант — написание двух прошивок разными командами разработчиков, при отказе одной прошивки работает вторая.

Третий вариант — троирование с мажоритарной логикой.

Четвертый вариант — вторая прошивка с сильно упрощенным алгоритмом.

Надеюсь сами вспомните, где какой вариант применяется?
Я серьёзно надеюсь, что вы не пишете софт для АЭС и автопилотов.

двух прошивок разными командами разработчиков, при отказе одной прошивки работает вторая


И как именно вы определите, какая из двух прошивок ошиблась?

Третий вариант — троирование с мажоритарной логикой


Не хочу вас расстраивать, но компьютер — вполне себе детерминированная система. Три экземпляра с одним и тем же кодом внутри и одними и теми же сигналами на входе при наличии в этом коде ошибки свалятся совершенно синхронно.

Четвертый вариант — вторая прошивка с сильно упрощенным алгоритмом


У вас правда в голове нет никаких идей, почему в системах с мажоритарной логикой не используются два дублирующихся экземпляра?..
Я серьёзно надеюсь, что вы не пишете софт для АЭС и автопилотов.
Для автопилотов как раз пишем. Но автопилот комбайна — очень простая штука. Мелкое дополнение к сложной сиcтеме RTK-навигации.

И как именно вы определите, какая из двух прошивок ошиблась?
Если не путаю, это на Апполоне было сделано. Америкацы тупые, да?

Три экземпляра с одним и тем же кодом внутри и одними и теми же сигналами на входе при наличии в этом коде ошибки свалятся совершенно синхронно.
А это уже русские, Аргон-16. За четверть века эксплуатации на космических кораблях “Союз”, транспортных кораблях “Прогресс”, орбитальных станциях “Салют”, “Алмаз”, “Мир”, “Меч-К” не было отмечено ни одного отказа комплекса в составе системы управления. Русские тупые, да? Не знали, что вся беда в ошибка и защищались от ТЗЧ и иных аппаратных сбоев.

Не хочу вас расстраивать, но компьютер — вполне себе детерминированная система.
Да ну??? А доказать можете? Ну скажем на год поставить 10 незащищенных от ТЗЧ систем. Сколько из них сбойнут? Почитайте лучше про вероятность сбоя. И на Земле и в космосе. Потому 9ая приемка — 9ой приемкой, а защищаться от сбоев лучше дополнительно.

Четвертый вариант — вторая прошивка с сильно упрощенным алгоритмом
Для полноты картины — это системы управления газом всех современных автомобилей.

почему в системах с мажоритарной логикой не используются два дублирующихся экземпляра?..
Потому что используются. Например двухголовый simatic S7–400H это отказоустойчивая система, а двухголовый simatic S7-400F — отказобезопасная. Логика отказобезопасной простая — или два процессора совпали, или все выходы — в безопасное состояние. Если нужно и то и то — четырехголовый S7-400FH.

Впрочем, с вашей точки зрения, небось немцы тоже тупые.

Для полноты картины — это системы управления газом всех современных автомобилей.

На современных автомобилях возможно и так, в чем я крайне не уверен. Но на ряде инжекторных автомобилях — это работает не так. При выходе из строя ЭБУ машина глохнет, даже на ходу. А вот при выходе одного из датчиков двигателя, кроме датчика коленвала, ЭБУ переходит на упрощенный алгоритм управления двигателем. При выходе из строя датчика коленвала ЭБУ останавливает работу двигателя.
При выходе из строя ЭБУ машина глохнет, даже на ходу.
А почему глохнет, а не ускоряется до предела? Какое же устройство при любом выходе из строя притягивает выход к нулю? В комментарии на хабре мне писали, что как раз второй процессор.

Cама стратегия работы DBW — это вообще космос! Там два микропроцессора и каждый непрерывно проверяет достоверность работы другого и правильность расчета положения — при этом каждый при определении проблемы, может независимо от другого, снять питание выходных каскадов драйвера привода заслонки.

Собственно зову в тред emmibox. При всех наших с ним спорах он действительно разбирается в чип-тюнинге авто.

Ну а я умываю руки.Максимум, что я могу — это спросить у коллеги из одного их производителей автоэлектроники (включая ЭБУ), так это в их решении или не так. Но я контактирую с разработчиками бортового компа, фактически — замены приборной панели, тонкости ЭБУ он может не знать.

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

Вы представляете, что такое заглохнуть на ходу?


Если вы поняли, что у вас что то пошло не так — заглохнуть на ходу самый оптимальный вариант! (на самом деле дроссель становится в limp-home позицию и можно куда то ехать с черепашьей скоростью)… И он значительно лучше, чем скажем неконтролируемо разогнаться до максимальной скорости и впечататься в столб.

Резервирования там нет никакого… Там есть 100%-й контроль корректности работы в условиях абсолютного недоверия как ПО так и железу, для одновременно двух микроконтроллеров. С идеей основанной на том, что любой вдруг возникший ранее не известный дефект не может одинаково воспроизвестись в двух фундаментально разных микропроцессорных архитектурах, созданных на разных заводах, по разным технологиям, разными производителями… (хотя в последних версиях 2й микроконтроллер упростили и заменили на asic только контролирующую работу первого).
Резервирования там нет никакого…

Про горячее резервирование в автомобильных ЭБУ речи не шло.
Если вы поняли, что у вас что то пошло не так — заглохнуть на ходу самый оптимальный вариант!.. И он значительно лучше, чем скажем неконтролируемо разогнаться до максимальной скорости и впечататься в столб.

С этим не поспоришь.
на самом деле дроссель становится в limp-home позицию и можно куда то ехать с черепашьей скоростью

Все зависит от датчиков двигателя, вышедших из строя.

Приведите пример автомобильно ЭБУ, в котором применяются:
1. два микроконтроллера (для резервирования);
2. два микроконтроллера с разной архитектурой.
Про резервирование речь не шла! Что касаемо двух с разной архитектурой то это, например вся линейка линейка ME7.
Основной МК — С167 с внешней памятью или ST10 с флеш.
МК монитора — 68HС05. (в массе) масочный ST10-С167 (в редких исполнениях).

(впрочем если про резервирование — первые АБС это 2 масочных 80с51 с арбитражем)
Ну у нас в спутниковом судовом приемоиндикаторе с функцией выдачи курса и судовом спутниковом устройстве дистанционной подачи курса (компасе) — горячее резервирование по навигационным координатам.

Сделал после рассказов одного штурмана о том, как они шли проливом маточкин шар на гирокомпасе потому, что снежно-ледовым зарядом им перебило 2 антенных кабеля из трех. Маточкин шар шириной 600 метров в узкой части, фарватер — и того меньше. А точность координат от гирокомпаса — фиговая. Самолетный имеет право к концу полета уходить на милю, судовой небось ещё хуже.

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

Дурацкий вопрос — а 4 тормоза на 4х колесах за горячий резерв не считаем? А посылку двух сигналов от дух половинок педали — это не горячий резерв? А датчик скорости на каждом колесе за горячий резерв не покатит? А дублирование передачи от АБС в ECM — это не горячий резерв?

Пардон, у меня на кухне в люстре 6 лампочек. Это тоже не горячий резерв? :-)
Дурацкий вопрос — а 4 тормоза на 4х колесах за горячий резерв не считаем?
Нет, не считаем, потому что одним или тремя тормозами нельзя тормозить. И двумя правыми тоже нельзя. И двумя передними не всегда можно.
Что значит нельзя???? Если у вас отказал один тормоз, то что, вся машина тормозить откажется? АБС затем и служит, чтобы выборочно отключать (или снижать усилие вплоть до нулевого) на тормозах отдельных колес.

Так что вполне себе горячий резерв. Лучше отремонтироваться, но если тормоза сломались на скорости 160 км в час — то уж лучше так, чем никак.
Если без АБС, то нельзя. Машина не откажется тормозить, она просто сделает это не по прямой и убьет вас в процессе с высокой вероятностью.
А если с АБС, то она при отказе одного тормоза отключит второй, чтобы тормозное усилие не было несимметричным и смены траектории не произошло.
Вы хотите сказать, что если отказали два тормоза с одной стороны, то машина вообще тормозить не будет? А можно пруф для обще эрудиции?
Вы в курсе как устроена тормозная система, хотя бы легкового автомобиля?
Нет.

Ответ на вопрос будет?
Ещё раз прошу, ответьте на вопрос.

Вы хотите сказать, что если отказали два тормоза с одной стороны, то машина вообще тормозить не будет? А можно пруф для общей эрудиции?
Если отказали два тормоза с одной стороны, и вы нажмете на педаль тормоза, машина на большой скорости уедет в случае отказа правых тормозов налево, а в случае отказа левых тормозов — направо. Называть это «торможением» я бы не стал, несмотря на то, что в итоге скорость машины скорее всего уменьшится до нуля.
А ещё я видел последствия заклинивания тормоза на одном колесе. Вам такого увидеть не желаю.
То есть все-таки тормозить будет. Плохо, криво, но будет.
Я не знаю на какой забористой травке Вы сидите, но стоит прекратит ее принимать, перед написанием комментарием.
Изучите устройство тормозной системы, хотя бы легкового автомобиля. Чтобы впредь не позориться перед другими людьми в разговорах и дискуссиях.
Нет, это не «плохо, криво, но будет», а «вместо штатной работы мы получим плохо предсказуемое и опасное для жизни поведение».
Это примерно как ваш любимый комбайн, внезапно получив вместо поля под Ростовом координаты посреди Тихого океана, попытается поехать обратно в Ростов. Плохо, криво, но поедет же.
При наличие ABS автомобиль поведет себя иначе.
Похоже Вы еще не в курсе, что такое горячий резерв. Раз привели такие примеры.
Пардон, у меня на кухне в люстре 6 лампочек. Это тоже не горячий резерв?

Нет, и еще раз нет.

Дурацкий вопрос — а 4 тормоза на 4х колесах за горячий резерв не считаем? А посылку двух сигналов от дух половинок педали — это не горячий резерв?

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

Изучите мат. часть про надежность и резервирование систем.
Нет, и еще раз нет.
А какой же тогда? Холодный? Теплый??

Если хватает освещения от 4 лампочек из 6 — две это резерв. Не надо думать, что горячий резерв не должен использоваться в работе.
Не надо думать, что горячий резерв не должен использоваться в работе.

Сами поняли, что написали?!

От Ваших ответов полнейший «лицо+ладонь».
Жду от вас новых определений горячего резерва.

P.S. Горячий резерв потому и горячий, что он всегда включен. А уж холостой ход или рабочий — не важно. Резерв, находящийся в stand by — теплый.
У Вас запасные лампы автоматом включаются в работу при выходе из строя основных?!
Автоматом включатся — это холодный резерв. Теплый — включены вполнакала.
Подведем итог: лампы на кухне в люстре — это не горячий, не теплый и не холодный резерв. А два дополнительных источника света с ручным управлением.
Это резерв, если освещенности от 4х ламп хватает. И это горячий резерв, ибо «находится в таком же режиме, как и основой».

Да, случай вырожденный, но кое-что резервируется именно так. Например аккумуляторные ячейки. Для нагрузки хватает 6, ставим 8 и имеем две в резерве — на случай отказа. У самолетах на стойках шасси по 4 колеса — это тоже резерв, на случай порванной покрышки.

P.S.
А два дополнительных источника света с ручным управлением.
Это вы условия не поняли. 6 ламп в одной люстре запитаны параллельно.
Небольшой ликбез о видах резервирования.

Нагруженный резерв («горячий резерв») — резервный элемент, который находится в таком же режиме, как и основой.

Облегченный резерв («теплый резерв») — резервный элемент, находящийся в менее нагруженном состоянии (например, «спящем»), чем основной.

Ненагруженный резерв («холодный резерв») — резервный элемент, находящийся в ненагруженном режиме до начала его использования вместо основного элемента.
Нагруженный резерв («горячий резерв») — резервный элемент, который находится в таком же режиме, как и основой.
Согласен. Ну и что значит «в таком же режиме» для электрической лампочки? Ась?

Отключения лампочка работает в таком же режиме, как и включенная?!

Не-а. У меня все 6 лампочек включены. 4 основных и 2 резервных.

А резерв они потому, что освещенности от 4х лампочек хватает. Так что пока перегорели 1-2 — можно не заменять.

После этого комментария вспомнился советский фильм под названием "Сережа", конкретно вспомнилось высказывание Серёжи в моменте с дядей Петей и конфетой.

Разжевать на уровне детского сада?

Нагруженный резерв («горячий резерв») — резервный элемент, который находится в таком же режиме, как и основой.

Основной режим лампочки — включена и горит. Значит режим горячего резерва такой же. То есть резервная лампочка тоже включена и тоже горит.

Был бы диммер — был ты теплый резерв. Как на котельных и насосных — два котла (насоса) пашут не на полную мощность, один отключился — второй запускаем на полную.

А раз диммера нет — режим горячий. Просто избыточное освещение от дух лампочек. На той же насосной можно и его устроить — только избыток давления надо будет сбрасывать. Не удивлюсь, если на той же Северстали и такое было или есть. У них там мегаватные электродвигатели вхолостую работали для поднятия косинуса фи.

P.S Я согласен, что случай тривиальный.
А при чем тут изменение косинуса фи и надёжность?!

Что такое различные типы резерва, я знаю не по наслышке. Ни один нормальный человек не будет включать 6 ламп, если ему хватает яркости от 4. И Ваш пример про лампы некорректный, так как у Вас изменяться свойства системы, уменьшится яркость.
А какая нормальная девушка разрешит выкручивать лишнюю лампу из люстры?

А при чем тут изменение косинуса фи и надёжность?!
При том, что Северсталь в свое время деньги не экономила. От слова совсем. А уж тем более — на надежности. Если нужен в насосной горячий резерв — значит будет горячий. И плевать, что избыток давления стравливается.

Из поразившего — у них между корпусами стальные переходы. Отпаливаемые. Неутепленные — стенки просто из стали. Сколько стоит их протопить в -20 — не знаю, но зимой в них тепло.
А Вы в курсе что из себя преставляют корректоры косинуса фи?! Вы снова влезли не в свою область знания и ушли от темы.

Сначала изучите мат. часто, а потом лезьте с комментариями, уважающий себя инженер не будет писать о том, в чем не разбирается от слова совсем.

И что Вы мне этим хотели доказать?! Свою неправоту про лампочки на кухне?
Если не путаю, это на Апполоне было сделано. Америкацы тупые, да?


Вы на вопрос ответьте, пожалуйста. Сами. Без ссылок на американцев.

Да ну??? А доказать можете? Ну скажем на год поставить 10 незащищенных от ТЗЧ систем.


У меня всё сильнее ощущение, что вы беседуете с радио, очень громко играющим у вас в голове. К теме защиты от переполнения стека в результате ошибки софта вот эта ваша фраза какое вообще отношение имеет?

Про комбайны — печально, конечно. С такой кашей в голове и ещё что-то проектировать…
Вы на вопрос ответьте, пожалуйста. Сами. Без ссылок на американцев.
Да ноль проблем, я не понимаю, какие у вас трудности.

Чем плох watchdog? Тем что он спасает только от зацикливания. А от отсутствия решения (или неверного решения) не спасает. Да, можно выкручиваться, но мы сильно ограничены временем watchdog. которое обычно секунды.

Из того, что обсуждалось. Два блока, инерциальной и спутниковй навигации. При отсутствии достоверного решения от одного блока в течение N секунд другой блок ресетит отказавший.

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

Качество решения (обычно в виде СКО) в навигации всегда считается вместе с решением. Например — по остаткам псведодальностей и псевдофазы. Или по дрожанию решения. Так что закомплексировать два RTK-приемника или RTK c PPP — это запросто можно.

Ну а задачи бортового компьтера космического корабля — близки к навигационным.

К теме защиты от переполнения стека в результате ошибки софта вот эта ваша фраза какое вообще отношение имеет?
А задача защиты от переполнения не является самостоятельной задачей. Реальная задача — обеспечить наработку на отказ.

И рассмотрение системы как 100% детерменированной — это неверный подход. есть шумы ошифровки, есть ошибки на портах и шинах передачи (и перпосылки), есть нестабильности тактовых генераторов.

99.999% детерменированности обычно есть. Но сбои, изредка приводящие к переполнению стека надо рассматривать как недетерменированные. Получили сбой по порту, запустили перепосылку — стека поели больше. Пришла импульсная помеха — получили пачку лишних прерываний — опять стека поели больше.

Из того, что ловили 30 лет назад. Исходная причина — незащищенный стек между двумя инструкциями ассемблера. При приходе таймерного прерывания (50 герц) портилась память в стеке.

Исходная частота ошибки — примерно раз в трое суток. Вначале мучались математики, потом прикладники, потом системщики. В итоге исключением кусков программы удалось довести частоту сбоя до 1 раз в 10 минут, после чего уже нашли чтением кода. Увы, заслуга не моя, а моего шефа.

Но факт есть факт — пока ошибку искали как детерминированную — её не могли найти. Как только стали искать как недетерменированную — нашли.

Возвращаясь к теме. Симптомы, указывающие на редкое переполнение стека, нельзя рассматривать отдельно от шансов сбоев от ЭМИ, ТЗЧ и так далее. Если есть нужное оборудование — можно даже начать исследование с них. То есть увеличить частоту сбоев предельным тепловым режимом, максимальными помехами, ухудшенным качеством питания. Вполне может быть, что этим вы редчайшее событие превратите в редкое.
Аналогично можно действовать и в случае двух функционально идентичных блоков. При отсутствии решения на чужом блоке или его низком качестве и наличии решения у нас — отключаем или перезапускаем чужой блок.


Вы продолжаете нести многословную чушь.

Что такое «отсутствие решения»? Блок 1 и блок 2 одновременно выдают координаты вашего комбайна, причём разные.

У какого из блоков «отсутствует решение»?

А задача защиты от переполнения не является самостоятельной задачей. Реальная задача — обеспечить наработку на отказ.


Ваша проблема в том, что сначала вы начинаете нести отсебятину, причём щедро приправленную чушью, в ответ на вполне конкретный и узкий вопрос, а потом — оправдываться, что на самом деле вопрос был и не такой уж конкретный и не такой уж узкий.

В то время как вопрос был именно таким, каким он был. Конкретным и узким.

Симптомы, указывающие на редкое переполнение стека, нельзя рассматривать отдельно от шансов сбоев от ЭМИ, ТЗЧ и так далее


Бред. Можно и нужно, потому что котлеты — отдельно, а мухи — отдельно.
Что такое «отсутствие решения»? Блок 1 и блок 2 одновременно выдают координаты вашего комбайна, причём разные.

У какого из блоков «отсутствует решение»?
Так выдается же не только решение, но и его СКО, полученное из остатков. То есть нашли координаты, просчитали теоретически расстояние до спутников, вычли измерения — получили остатки. И эти остатки могу отличаться в десятки раз.

В реальности у нас 3 антенны и 3 приемника и проверяемся по вычисленному из решений расстоянию между приемниками. Если между приемниками 1 и 2 расстояние в норме, а между 3 и 1 и между 3 и 2 — не в норме, то надо перезапустить решение на приемнике 3.

На самом деле мы считаемся на одном и том же SoC, но логика у нас ровно такая.

А измерения без оценки СКО — это какой-то школьный уровень. Ну не стоит так делать в профессиональной аппаратуре.

на самом деле вопрос был и не такой уж конкретный и не такой уж узкий.
Это правда. При переносе вопросов на личный опыт получается не конкретно и не узко.

Нехватки стека я видел. Но они или срабатывают сразу или носят не детерменированнный характер. То есть может проработать сутки, а может свалиться через 10 минут. Потому что условием ошибки является редкая и не детерменированная ситуация в данных.
Так выдается же не только решение, но и его СКО, полученное из остатков


В реальности у нас 3 антенны и 3 приемника


Мне нравится, как вы сначала делаете обобщение вида «при отказе одной прошивки работает вторая», а на вопрос, как вы определяете, какая конкретно прошивка отказала, мгновенно сводите всё к тому, что у вас и не две, и не прошивки, а вообще всё по-другому.

Вы не могли бы громкость играющего у вас в голове радио всё же немного уменьшить — а то не очень понятно, стоит ли вообще с вами дискутировать, если вы в любой момент тему беседы меняете произвольным образом?

Но они или срабатывают сразу или носят не детерменированнный характер


Опять чушь — ну или банальное незнание и непонимание вами, что такое детерминированная система.

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

Недетерминированное поведение — это поведение, при котором одни и те же входные данные могут приводить к разным результатам.
Недетерминированное поведение — это поведение, при котором одни и те же входные данные могут приводить к разным результатам.
Да, именно так. Один и тот же сигнал, снятый с одной и той же антенны приводит к разным измерениям. Один и тот же пинг, посланный одному и тому же серверу, дает разное время пинга.

Отучайтесь от привычки работать исключительно с ученическими системами. Не детерминированность или неполная детермированность — неотъемлимое свойство сложных систем.

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

В понимаете, что в многонитевой программе переключение между нитями может произойти в произвольный момент? Или веруете, что оно детерменировано?

Вы понимаете. что в младших битах значения от АЦП дробный шум? Или веруете в стабильность любых измерений, не взирая на температурный дрейф и прочие эффекты?

Вы понимаете, что сбои по ком-порту бывают примерно с частой 1E-6 в не детерминированных местах?

Короче, оставьте этот бред для школьников. Да, на уровне «hello world» все детермировано. А на уровне реальных систем — нет.

Поэтому дико бесят недоучки, не принимающие мер к детерминизации. То есть они работают только по реальному сигналу, а потом удивляются — ой, странный сбой, ой, не воспроизводится.

Да, подсистемы. позволяющие записать сигналы, а потом — воспроизвести поведение системы по записанным файлам — не дешевое удовольствие. Зато по файлам, на windows, в однонитевой программе — все детерминировано. И 98% процентов проблем отлаживается именно так.

И первый шаг к надежному коду — признать, что реальный SoC с плывующей частотой кварца, шумящим АЦП, прерываниям и прочими прелестями — слабо детерменирован.

Теперь к первому вопросу.

Мне нравится, как вы сначала делаете обобщение вида «при отказе одной прошивки работает вторая», а на вопрос, как вы определяете, какая конкретно прошивка отказала, мгновенно сводите всё к тому, что у вас и не две, и не прошивки, а вообще всё по-другому.


Давайте вы научитесь правильно задавать вопросы? А то думаете одно, пишете другое, а потом удивляетесь, что вам ответили на тот вопрос, который вы задали, а не на тот, о котором вы думали.

а на вопрос, как вы определяете, какая конкретно прошивка отказала,
Мы определяем? Именно мы?! Я вам рассказал про решение, которое применило НАСА в одном из кораблей. Вроде в Апполоне.

Мы не являемся сотрудниками НАСА. И не отвечаем за решением примененное НАСА более 50 лет назад.

Я могу рассказать про свои системы. Но мы не НАСА, поэтому программирование одного алгоритма двумя независимыми командами разработчиков не применяем. А что применяем — я рассказал.

Или вам нужны фантазии, что бы я сделал на месте НАСА? Это несложно. Принцип ровно тот же — не только считать не только результаты расчетов, но и показатели их достоверности и точности (СКО, КВО, etc). Это все давным давно описано в учебниках. Собственно любая система выше школьного уровня погрешности считает.

Ну и второе -это время решения. Все расчеты — итеративные, сходятся итерации быстро или медленно — зависит от данных и методики расчета. Насколько мне помнится, в те годы сильно боялись зацикливаний. Так что нету решения N секунд — считаем, что у нас отказ. Такой вот взаимный контроль.

Ну может оно сложновато для того школьного уровня, к которому вы привыкли. Ну так реальные системы сильно отличаются от того «hello world», который вы преподаете. Ничего страшного, не век же вам со студентами общаться? Привыкайте к общению со специалистами.
Не детерминированность или неполная детермированность — неотъемлимое свойство сложных систем.


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

Ну или в силу своей вопиющей некомпетентности искренне не различаете случайные физические процессы с недетерминированностью вычислительной системы.

Остальную простыню не читал.
и опять ad hominem.

Как там с гонкой и моментом переключения нитей? Есть там детерменированность или нет?
Да, есть.

(можете не трудиться писать в ответ простыню на три экрана о том, как вы отлаживали GPS)
То-то нынешние вчерашние студенты не умеют с гонками бороться. И как им научиться, если у их преподавателя такая каша в голове?

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

А сказки про детерменированность — оставьте для пятиклашек. Ибо уже шестиклашки могут померять скорость исполнения и убедиться, что детерменированности нет.

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

А уж в системе процессор + периферия детерменированные модели и 60 лет назад никуда не годились.

P.S. Вы попробуйте в программу таймеры вставить и количество циклов за секунду померить. Как думаете, сколько процентов расчетов дадут одинаковые значения?
Господи, какой бесконечный стыд.

Можно где-то с вашим кодом ознакомиться, кстати?
Давайте начнем с малого — вы все-таки предложите сове решение задачи про холодильник и клавиатуру. В рамках бюджетных ограничений, само собой. Ну или признаете, что не может придумать лучшее решение.

Далее условия такие
  1. Вы даете ссылку на свой код, уровнем повыше школьной задачки. Много не прошу — ну скажем 200-300 строк сложного модуля.
  2. В ответ — получаете или найденную мной ошибку или иной способ решения той же задачи (словесно) или признание, что ваш код для меня слишком сложен.
  3. Я вам даю кусочек своего кода (300 строк) и 40 страниц документации к нему.
  4. Вы или находите в коде реальную ошибку или предлагаете свое решение той же задачи (словами) или признаете, что код такого уровня вам не по зубам.



А так… Если в школке на УКНЦ учились, то с мои электронные таблицы учитель вам должен был показывать.
Господи, какой же вы унылый. Вот эти «40 страниц документации» — они мне, например, зачем? Оценить вашу способность нафигачить 40 страниц текста? Спасибо, я по комментариям здесь уже понял.

Вот эта ваша клавиатура несчастная — она здесь зачем и кого вообще должна волновать? Ну залепили вы какую-то дырку четверть века назад дерьмом с палками, вам кажется, что вы это очень изящно сделали, всем остальным — что в самом факте использования этих материалов нет ничего, чем стоило бы гордиться.

size_t NMEA_CRC(char *Str)
{
   static  char    H[17]   =       "0123456789ABCDEF";
   int i=1;
   int8u   CRC=0;
   char c;
   while   (((c = Str[i]) != 0) && (c != '*'))  {
           CRC     ^=   c;
           i++;
           }
   Str[i++]        =       '*';
   Str[i++]        =       H[CRC>>4];
   Str[i++]        =       H[CRC&15];
   Str[i++]        =       13;
   Str[i++]        =       10;
   Str[i]          =       0;
   return i;
};


Вот это — ваш личный стиль написания кода, я правильно понимаю?
А три разных способа именования идентификаторов на десять строк кода? А приравнивание int к size_t? А static вместо const? А явное указание размера константного массива?

Такой талант пропадает.
Зачем вы сейчас приплетаете одиночные сбои к разговору про сбой процессора в результате ошибки в программе? Если есть ошибка в программе, то все три копии действительно откажут синхронно и одинаково (там, разумеется, есть нюансы про прерывания, но это сейчас не важно).
Но кстати да, дублирование в реальности довольно часто применяется, хотя мажоритарная логика тут ни при чем, конечно же. Это как с помехоустойчивым кодированием — есть коды, которые ошибки исправляют, а есть коды, которые их только обнаруживают. Вторые дают меньше накладных расходов в штатной эксплуатации, но больше — во время сбоя.
Если есть ошибка в программе, то все три копии действительно откажут синхронно и одинаково (там, разумеется, есть нюансы про прерывания, но это сейчас не важно).
Попробуйте доказать этот тезис.

Ну как пример. Есть чтение ком-порта, при приеме бывают сбои. Подаем информацию с одного датчика на две системы. Вы уверены, что два ком-порта на разных SoC дадут сбой синхроннно?

Ошибки на главном ходу алгоритма вычищаются быстро. А ошибки на редко используемых ветках намного больше завязаны на не детерменированные события.

Можете сделать эксперимент. Берете два GPS-приемника, сажаете их на общую антенну и общее питание. Корпус — общий или одинаковый, чтобы температурный режим не влиял.

Какие шансы, что два приемника в таком режиме (режим называется нуль-база) дадут одинаковые измерения псевдодальности и псевдофазы? НУЛЕВЫЕ. Всегда будет шум измерений. У хороших приемников — поменьше, у плохих — побольше. Но он есть всегда.

И дело не только в тепловом шуме. Бывают слипы, бывают систематики. Даже тактовые генераторы прилично расходятся. Один дает коррекцию на 1/16 мкс раз в 15 секунд, другой- на каждой секунде. Что будет в измерениях? Систематика там будет.

Так что сказок про детерменированность — не надо. Детерменированность у нас (высокоточная навигация) — редкий подарок.
Ну как пример. Есть чтение ком-порта, при приеме бывают сбои. Подаем информацию с одного датчика на две системы. Вы уверены, что два ком-порта на разных SoC дадут сбой синхроннно?


Вы вообще пробовали прочитать вопрос, который вам задали, и ваш ответ на него?

Или вы искренне считаете, что какая-либо корреляция между вопросом и ответом совершенно не обязательна — и в дискуссии можно просто на все исходные тезисы спокойно забить, на ходу придумав новый пример?

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

В то время как у любых нормальных разработчиков решение проблемы начинается с её максимальной декомпозиции и дальнейшего поштучного исключения кандидатов на причину, то вы действуете ровно наоборот — яростно замешиваете в одну кучу все возможные причины, а потом, вместо поиска и устранения единственной истинной причины, пытаетесь подпереть получившееся костылём, который вроде бы в данном месте не даёт получившейся конструкции обрушиться.
То есть вы не поняли, что вопрос "Зачем вы приплетаете" риторический и хотите получить на него ответ????!

Ну ОК, отвечу. Да затем, что исправление «одиночных сбоев» занимает 90% времени. Затем что хотя каждая отдельная ситуация редкая, хоть какая-нибудь из них происходит часто. Затем, что учет редких ситуаций дает нам точность в 4 раза лучше конкурентов (при том же приемнике).

Никогда не видели, как дешевый навигатор показывает, что вы едете сквозь дома? Это вот как раз и есть — отсутствие учета редких ситуаций.

Иногда даже понятно, каких именно.
Включите навигатор в 2:30 в ночь с субботы на воскресенье — есть шансы, что в 3:00 решение улетит метров на 100 от реального расположения. Как минимум на одной модели мы такое видели. Исправляется оно через 6-7 минут. Кстати, это один из немногих хорошо детерменированных ляпов.


Так вот, достали недоросли, думающие, что GPS хорошо детерменирован. Ой, у меня в коде сбой, что случилось? А непонятно, что случилось. Если сырые данные не записаны и решались по живому сигналу — могло быть все, что угодно.

Приходится переучивать, объяснять про то, что на живом сигнале регрессионное тестирование невозможно, что отлаживаться надо на записанных файлах…

Так что байки про «детерменированность» — оставьте для школьничков. А студентов нужно приучать к отладке по записанным файлам.

Впрочем, из вашего примера про то, как вы «исправляли» клавиатуру, в принципе дальнейший ход ваших мыслей вполне понятен.
А слабо продемонстрировать как бы вы решали эту проблему? Я её решил за вечер и за 0 денег. Ну вы так не сумеете, поэтому пусть будет 3 дня на исправление, а цена — ваш дневной заработок в 1993 году. Если ещё в школу ходили — ну пусть та сумма, что мама на завтраки вам давала. Сумеете решить?

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

На уровне детского садика — поиски причины и устранение последствий — это разные процессы. Только детсадовцы думают, что найти причину и её устранить -это одно и тоже.

И только на уровне школы устраняет ошибку тот, кто её допустил. А в реальной жизни ошибки компонентов обходятся. Вы думаете мы мало ошибок в GPS-приемниках нашли? Да уж за несколько сотен перевалило. Сегодня вон парочку нашел, позавчера ещё одну (в другом приемние). Но послать багрепорт производителю — это одно, а обойти ошибку — совсем другое. Если ждать исправления всех ошибок, то прибор будет готов через 10 лет (и никому не нужен). Поэтому всегда стараемся обойти ошибки сами.

Так вот, отучите вашего телепата фантазировать. Не писал я ничего о том, как искались причины проблемы. Это вы сами выдумали и сами своей выдумке возмутились. Так что лечите вашего телепата от излишних фантазий.
Господи, какой невероятный стыд вы несёте.

Да никакие вы проблемы не решаете и решать не умеете — вы умеете подпирать дырки костылями, маскируя эти уродливые конструкции гигантскими нагромождениями слов, которые с вашей точки зрения, видимо, имеют отношение к решению проблем.
ad hominem.

Я правильно понимаю, что продемонстрировать своё решение проблемы с указанными инженерными ограничениями вы просто не в силах?
Зачем?

Чтобы вы в ответ накатали не две, а уже три страницы баек, не относящихся вообще никак к обсуждаемой теме, а лишь призванных продемонстрировать, что вы необычайно круты в отладке GPS?
Значит просто не можете.

Вы все верно написали про анализ причин. Вот только нахождение причин и исправление проблемы — разные процессы.

И предложить исправление проблемы в рамках заданного бюджета вы просто не смогли. Не инженер вы, обычный кабинетный теоретик.

По теории — там нужно исправлять несоответствие советских ГОСТов 60х годов на помехи, создаваемые холодильником в цепях питания с иностранными стандартами на БП компьютеров. Надеюсь, сами понимаете, что это нереально.

А все прочие способы — не проходят по бюджету. 1993 год — голодное время. Я тогда думал, что мне лучше — пирожок купить или на автобусе домой подъехать. Ну а вы небось ещё в школу ходили.

Так что одна покупка паяльника — уже превышала бюджет (напоминаю, это всего лишь суточная зарплата).

Ну и что вы можете сделать без паяльника? Даже программатор для клавиатуры не спаяете. Не говоря уж о фильтрах.

Именно этим и отличается хороший инженер от кабинетного теоретика — умением решать подручными средствами.

Вы думаете, я не в курсе, что дело в конкретном сочетании холодильника, БП и клавиатуры? В курсе, это проверялось. Вот только менять что-то из трех (самый прямой путь) — это вне бюджета.

Могли бы думать как инженер — придумали бы ещё один дешевый способ. Я его пробовал, он немного помог. Но, боюсь, что вам инженерной грамотности не хватит до него догадаться.
Так а с кодом-то вашим где-то можно ознакомиться?
Ух ты какой попрошайка.

Молодой человек, решите для начала предложенную вам задачу. Будьте уж так любезны, выполните свое домашнее задание.

А то критиковать — любой дурак может, зато самостоятельное решение — большинству дураков не под силу.

Не пора ли вам признать, что вы только критиковать можете, а решить простейшую инженерную задачу вы не способны?
Если вы не заметили, мы уже тут ознакомились.

Совершенно удивительное творение, вы когда это писали, точно были в сознании?
Именно этим и отличается хороший инженер от кабинетного теоретика — умением решать подручными средствами.
Нет, умение подпирать дырки костылями из говна и палок не относится к важным умениям хорошего инженера.
А теперь попробуйте этот тезис доказать.

С моей точки зрения — это очень важное умение. Да, лучше обойтись без костылей. Но если надо быстро и дешево- нужно уметь применить костыль.

Вот завязнет у вас машина в ненаселенке, что будете делать? Вызвать трактор за 100 км или звонить тому, кто умеет вытаскивать подручными костылями?

А если сломается, то что? Вызвать самолет, чтобы фирменную детальку сбросил?

Не умеете использовать костыли — держитесь в черте мегаполиса. В ненаселенке вам делать нечего. Даже в мелких городах и деревнях вам жить будет очень тяжко.
Уметь использовать костыли должен тот, кто эксплуатирует систему — чтобы дотянуть до сервиса с фирменными запчастями. Создание системы из костылей как постоянных решений — порочная практика, не имеющая ничего общего с хорошей работой инженера-разработчика.
Хороший разработчик предусмотрит замену тем блокам, выход которых вероятен раньше всего по той или иной причине. И, следовательно, в комплект поставки заложит ЗИП.
Хороший разработчик предусмотрит регламентные работы, которые выявит блоки, выход из строя которых наступит в ближайшее время.
Хороший разработчик не будет предлагать делать костыли, этим занимаются плохие разработчики.
Ну и сколько фирменных запчастей вы могли купить в любой день в 1993 году? Мое решение продержалось, пока не нашлись деньги на новую клавиатуру. Увы, 93ий год — это задержки зарплаты, да и денег еле-еле на еду хватало.

Поехали дальше. 1994 год, Pentium FDIV bug. С ужасом обнаруживаете, что тот баг вашего кода касается.

Ваши действия? Напишите в документации, что на пнях с багом программа не работает? Или обойдете баг костылем?
или используете компилятор с опцией Pentium Safe FDIV?

Будут ли покупать вашу программу, если она не работает на чисти компов? Или купят программу у конкурента. Да, с небольшим костылем, зато работоспособную?

Что вы делаете, увидев errata на SoC? Ждете 5 лет, пока производитель исправит? Или обходите чужие баги своими костылями?

Поехали дальше. Вот есть у вас массив записей измерений за 10 лет. Используется для регресссионного тестирования и многих других вещей. Вы его выкинете? Или будете использовать, несмотря на то, что для его дешифровки нужны костыли?

Создание системы из костылей как постоянных решений — порочная практика,
Эта практика называется совместимость. Вы будете утверждать, что совместимость это плохо?

Ещё пара примеров хороших костылей. Первый — очистка спектроскопа кошкой., а второй — известная байка про фломастеры и карандаши в космосе.

А теперь итоги. Костыль — весьма не плох. Плохо увеличение собственного технического долга, независимо от того, вызвано ли оно костылем или нет.

Так что в той ситуации, когда костыль не увеличивает ваш технический долг — можно его использвоать. А уж ежели костыль уменьшает чужой технический долг — его использовать нужно.

Интересно, что зачастую технический долг увеличивается не костылями, а универсальными решениями. Из-за их универсальности они иногда плохо отлажены и сбоят. А костыль — всегда прост, сбоить в нем обычно нечему.

Ну вопрос напоследок. Ваше отношение к Git for Windows? Считаете ли вы, что он «не имеет ничего общего с хорошей работой инженера-разработчика»? Или наоборот?
Поехали дальше. 1994 год, Pentium FDIV bug. С ужасом обнаруживаете, что тот баг вашего кода касается.

Ваши действия? Напишите в документации, что на пнях с багом программа не работает? Или обойдете баг костылем?
или используете компилятор с опцией Pentium Safe FDIV?

С чего Вы решили, что баг в аппаратной части (как делают большинство недоразработчиков программного обеспечения), а не в Вашем ПО и не все предусмотрели в коде.
Выясню причину и выпушу полноценный патч. А не закрою костылем баг в ПО, чтобы костыль потом стал боком.

Что вы делаете, увидев errata на SoC? Ждете 5 лет, пока производитель исправит? Или обходите чужие баги своими костылями?

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

Поехали дальше. Вот есть у вас массив записей измерений за 10 лет. Используется для регресссионного тестирования и многих других вещей. Вы его выкинете? Или будете использовать, несмотря на то, что для его дешифровки нужны костыли?

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

Это несовместимость. Это закрывание дыр. И это снова говорит об очень низкой квалификации разработчика.
Костыль — весьма не плох.

Костыль — всегда плохо. Костылять могут только оооочень низкого уровня разрабы.
Применения костыля возможно только для проверки гипотезы неработоспособности программы самим разработчиком. А дальше выпускается полноценный патч или новая версия ПО.
Ваше отношение к Git for Windows?

Я использую Git for Linux. Использование Git for Windows, не говорит о хорошем уровне разработчика.
Считаете ли вы, что он «не имеет ничего общего с хорошей работой инженера-разработчика»

И объясните мне, как использования Git может говорить о хорошем уроне разработчика?!
А использование других систем управления версиями говорит о невысоком уровне разработчика?!
Вы, видимо, кроме Git ничего не знаете и не использовали. И это снова говорит о низкой квалификации.
Ну так что там с автопилотом? Будет рассказ о его сложности или, как обычно, в кусты?

Чему вы так удивляетесь?
С чего Вы решили, что баг в аппаратной части (как делают большинство недоразработчиков программного обеспечения), а не в Вашем ПО.
Вы что, ни разу бага в процессоре не видели? Может и вы и нормального большого процессора не видели? Не того микропроцессора, что в чипе, а занимающего несколько шкафов. А прошивку настоящую видели? Ту что иголкой и ниткой проводом делается? В ферритовое колечко — единичка, мимо него — нолик, за 3 прошитых провода — отгул. Вот так ПЗУ и шили.



Про баг в микрокоде СМ2М
1986 год. У прикладников программа вылетает с прерыванием «по нереализованной команде». Шеф довольно быстро делает воспроизводимость и отдает мне разбираться. Выясняется, что вылетает при делении мусора на мусор, то бишь ненормализованного на ненормализованнное. Прошу электронщиков поставить микрокод посвежее. Между прочим, микрокод -это две платы. Ну а сам лезу в листинг этого самого микрокода. А там почти открытым тестом «звиняйте, не успели мы нормализацию операндов деления сделать». Проверка на нормализацию есть, а дальше если не прошла — прерывание по нереализованной команде. Ну сменили платы микрокода на новые и все заработало. Дальше уже дело прикладников — мусор на мусор делить тоже не стоит.


Как проверяют баги в микропроцессорах
С чего Вы решили, что баг в аппаратной части
Ну уж про этот баг все СМИ писали. А проверяется его влияние на программу обычным путем. Тестовый пример с аппаратной плавающей точкой и прогон на ПК с разными процессорами (386/486/Pentium/586 (от AMD)). Потом тот же пример с сотфверной плавающей точкой — и опять прогон на всех ПК. Если результаты второго прогона совпали, а первый на некоторых Pentium отличается — значит этот баг нас затронул.


Выясню причину и выпушу полноценный патч.
Остапа понесло, пронесло и унесло.

Патч к чему??? К фотошаблонам для производства процессора? Увы, Pentium FDIV не правился перезаливкой микрокода, надо было менять целиком процессор.

Патч к бинарному коду? Ну это самый худший вариант костыля. Патч к исходникам?

Ну и чем ваш «полноценный патч» отличается от моего костыля? Мой костыль в идеале — это одна опция компилятора — Pentium Safe FDIV. Если такой опции в компиляторе нет — можно сделать два исполняемых модуля, один с аппаратной плавающей точкой, другой с софтверной. Можно при старте пропатчить команды FDIV на вызов процедуры. Короче, варианты есть. Но в любом случае это будет костыль, приделанный к программе сверху.

А ваш «полноценный патч» это что? Замена в исходной коде всех операций деления на вызовы процедуры? А если ошибетесь и одно деление забудете?

Разве не очевидно, что костыль, не влияющий на основной текст программы, в этой ситуации намного универсальней, чем правка прикладного кода?

И в любом случае (и у вас и у меня) — это workaround, то есть костыль. Ибо есть прямой путь — предложить всем заказчикам заменить дефектный процессор. Только прямой путь дорог и ненадежен, а workaround -дешев и очень надежен.

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

код разрабатывается так, чтобы при устранении аппаратной ошибки, он не приводил к падению ее и был легко поддерживаемым и модифицированным.
И… с чего вы решили, что костыль плохо поддерживается или модифицируется? Или что костыль ненадежен? Костыль (hack) обычно стилистически инороден — это верно. Но ничто не мешает писать хороший код в костылях. Более того, обычно костыль (hack) — это отличный код.

Костыль — всегда плохо. Костылять могут только оооочень низкого уровня разрабы.

Да ну???? Ну вот вам пример, когда костыль (hack) явно лучше. Код математика:
uint32_t dwa_v_stepeni = uint32_t(pow(2.,N));

Костыль (hack) от программиста:
uint32_t dwa_v_stepeni = 1UL << N;

Дело не в том, что код математика выполняется медленней. Дело в том, что в мире есть не только ПК. На ПК FPU — 80 бит, там оба кода работают одинаково. А вот на ARM FPU — всего 64 бита. И 2**31 у математика считается неверно — получается на единичку меньше.

Хотя никто не спорит, что замена возведения в степень на сдвиг — это костыль (hack). Он явно хуже читается. И хуже модифицируется, если математик решит заменить 2 на 3. Зато — работает верно и быстро.

Знаете что. Давайте вы дадите свое определение костыля. Потому что их несколько. С одной стороны, это workaround, с другой стороны hack.

И в том и в другом случае костылем называют обходной путь. Решение в лоб, с N**3 — прямое донельзя, но тормозное. Решение с N*Log(N) — костыль. Всякий е быстрые алгоритмы — это костыли (hack), тот же QickSort — явный костыль, он очень плохо читается, плохо модифируется, в отличие от прямой сортировки пузырьком. Вот только большинство использует именно костыльный QickSort. Вы попробуйте сделать устойчивый QuickSort. Получиться? А устойчивую сортировку пузырьком сделать просто.

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

И если нужен костыль — это говорит об уровне квалификации разработчика, который ниже плинтуса.
Увы, нет. Костыли (workaround) нужны потому, что записи делались с приемников, в которых были ошибки. И чтобы дешифровать все старые записи, нам нужно хранить в коде костыли (workaround) на уже устраненные ошибки приемников.

И объясните мне, как использования Git может говорить о хорошем уроне разработчика?!
Скажите пожалуйста, для вас русский язык родной или нет? Если нет — я буду писать попроще. Дело в том, что Git — это костыль, сделанный Линусом из гавна и палок за неделю. Ну а Git for windows — костыль в квадрате, ибо для работы Git в windows пришлось переносить приличную часть linux.

У git есть хорошие части. Но чуть ли не половина git написана на shell script и perl. Ну как минимум в git for windows, который я сейчас рассматриваю.

Это такой UNIXWAY — делать системы из гавна и палок. То есть берем готовы, хорошие кирпичи — утилиты. Добавляем к ним свое гавно на bash, awk, sed. Пара часов — и нужная функциональность есть.

UNIXWAY хорош, когда нам нужен одноразовый костыль. Ну хотя бы редкоиспользуемый. А когда свзяка кучи программ используется сто раз на дню…

Вы себе представляете сколько всего сломается, если изменить вывод df или ls? Мы все привыкли к UNIXWAY, поэтому и не видим, сколько костылей у нас в системе.

Ну а Git for windows — костыль в квадрате, ибо для работы Git в windows пришлось переносить приличную часть linux.

У git есть хорошие части. Но чуть ли не половина git написана на shell script и perl. Ну как минимум в git for windows, который я сейчас рассматриваю.


Скажите, а вы вообще на вашем текущем месте работы точно программистом числитесь? Потому что по уровню высказываний — больше похоже на мальчика, который программистам кофе носит.
Если когда-нибудь окажитесь около компа, загляните в C:\Program Files\Git и посмотрите, какие файлы там текстовые, а какие бинарные. Только не по расширениям, а по содержанию.

Можете сразу в C:\Program Files\Git\mingw32\libexec\git-core залезть. Там основные команды. Чуть ли не половина — на баше. Ну и для самого мякотки — в C:\Program Files\Git\mingw32\libexec\git-core\mergetools, там вообще все на bash.

Умете содержимое файлов смотреть? А то после того, как вы не сумели решить элементарную инженерную задачу, я в ваших способностях очень сомневаюсь.
Я могу и на github.com/git/git заглянуть, и что?

Вы, кстати, как-то замяли тему про запредельно кошмарного качества код за вашим авторством. Ну, там, где const и static перепутаны и три способа именования идентификаторов на десять строк кода.

Он у вас весь такой, или вы только этот кусок в бессознательном состоянии писали?
Ну, там, где const и static перепутаны
Откуда же вы такие беретесь? Не я понимаю, кто умеет — тот работает, кто не умеет — тот учит. Но как можно не знать идиомы, существующей с 60ого года?

Я понимаю, что компилятора у тебя нет. Но мог же подружку попросить откомпилировать. Ну правда же мог?

Вот так выглядит static char[]
73 .LBB3:
45:../FarwLib/crc.cpp **** static char H[17] = "0123456789ABCDEF";
46:../FarwLib/crc.cpp **** int i=1;
47:../FarwLib/crc.cpp **** int8u CRC=0;
74 .loc 1 47 0
75 0002 0023 movs r3, #0
76 .LBE3:
44:../FarwLib/crc.cpp **** static char H[17] = "0123456789ABCDEF";
77 .loc 1 44 0
78 0004 30B5 push {r4, r5, lr}

311 .section .rodata._ZZ8NMEA_CRCE1H,"a",%progbits
312 .set .LANCHOR1,. + 0
313 .type _ZZ8NMEA_CRCE1H, %object
314 .size _ZZ8NMEA_CRCE1H, 17
315 _ZZ8NMEA_CRCE1H:
316 0000 30313233 .ascii "0123456789ABCDEF\000"
316 34353637
316 38394142
316 43444546
316 00


А вот const char[]
78 .LBB3:
45:../FarwLib/crc.cpp **** const char H[17] = "0123456789ABCDEF";
79 .loc 1 45 0
80 0002 1A4B ldr r3, .L13
81 .LBE3:
44:../FarwLib/crc.cpp **** const char H[17] = "0123456789ABCDEF";
82 .loc 1 44 0
83 0004 86B0 sub sp, sp, #24
84 .cfi_def_cfa_offset 40
44:../FarwLib/crc.cpp **** const char H[17] = "0123456789ABCDEF";
85 .loc 1 44 0
86 0006 0246 mov r2, r0
87 .LBB4:
88 .loc 1 45 0
89 0008 01AC add r4, sp, #4
90 000a 03F11006 add r6, r3, #16
91 .LVL4:
92 .L5:
93 000e 1868 ldr r0, [r3] @ unaligned
94 0010 0833 adds r3, r3, #8
95 0012 53F8041C ldr r1, [r3, #-4] @ unaligned
96 0016 2546 mov r5, r4
97 0018 B342 cmp r3, r6
98 001a 03C5 stmia r5!, {r0, r1}
99 001c 2C46 mov r4, r5
100 001e F6D1 bne .L5
101 0020 1B78 ldrb r3, [r3] @ zero_extendqisi2
102 0022 511C adds r1, r2, #1
103 0024 2B70 strb r3, [r5]
104 .LVL5:
46:../FarwLib/crc.cpp **** int i=1;
47:../FarwLib/crc.cpp **** int8u CRC=0;
105 .loc 1 47 0
106 0026 0023 movs r3, #0
107 .LVL6:

336 .section .rodata.str1.1,"aMS",%progbits,1
337 .LC0:
338 0000 30313233 .ascii "0123456789ABCDEF\000"
338 34353637
338 38394142
338 43444546
338 00


Разница видна?

Так вот, это чудо под названием own придумала году в 1959ом-1960м команда Бэкуса (того, что БНФ и фортран).

Синтаксически own — локальная переменная процедуры, но сохраняющая свое значение между вызовами. Семантически — это обычная переменная в памяти, но с инициализацией в момент первого вызова процедуры или блока.

Поскольку у меня-то компилятор есть, делаем тестик:
void test1(char a, char b, char c)
{
   static char stat[4] = {a, b, c, 0};
   const  char cons[4] = {a, b, c, 0};
   printf("stat=%s const=%s\n", stat, cons);
}

void test2(void)
{
   test('1','2','3');
   test('4','5','6');
   test('7','8','9');
}


А вот и результаты:
stat=123 const=123
stat=123 const=456
stat=123 const=789


Теперь понятно, что делает компилятор? const — это локальная переменная, размещается в стеке и инициализируется при каждом вызове. А static — это own, глобальная переменная с локальной видимостью. Она размещается в памяти, а инициализируется (формально) — при первом использовании.

А дальше — крохотная оптимизация. Если инициализатор у static статический, то компилятор и инициализирует статически, как будто это обычный static, написанный вне тела процедуры.

Конечно, очень умный компилятор может и const попытаться инициализировать статически. Ну если стандарт С++ ему не помешает. Честное слово — не смотрел, что там в стандарте.

Домашняя работа, сэр:

  1. Порыться по стандартам, можно ли статически инициализировать const char[].
  2. Проверить новомодные компиляторы, умеют ли они это.

Если интересно, то код от gcc 4.9.3 (стандартный кросс-компилятор для ARM от debian 8), уровень оптимизации -Os

Теперь мысль понятна? Нафига нам медленный const, если есть быстрый static?

Я вообще не понимаю, как можно писать на С++, не прочитавши The C Programming Language(он же K&R). Вот вам цитата оттуда:

Объявление static можно использовать и для внутренних переменных. Как и автоматические переменные, внутренние статические переменные локальны в функциях, но в отличие от автоматических они не возникают только на период работы функции, а существуют постоянно. Это значит, что внутренние статические переменные обеспечивают постоянное сохранение данных внутри функции.


код за вашим авторством.
Где ж там мое авторство? У вас нос заложен, что ли? Не чувствуете, что от кода пахнет фортраном? Это не я писал, и не мой предшественник 15 лет назад, это код начала восьмидесятых, из какой-то документации по NMEA 0183, чуть ли не от самой National Marine Electronics Association.

три способа именования идентификаторов
Угу. Когда человек не умеет программировать и не понимает смысла простейших конструкций — ему очень важно, что как именовано в 10строчной процедуре. Потому что без единственно верного наименования ему код не понять.

Нету у нас джунов вашего уровня. У нас всего один джун и тот соображает в коде лучше вас. Про сеньоров и не говорю. Поэтому на правила именования все болт забили.
Потому что нам нужны не шашечки, а ехать. Другим время занято.

Он у вас весь такой, или вы только этот кусок в бессознательном состоянии писали?
Милок, понюхай ты фортрана полной грудью. Вживую goto и метки видел? А потом пойми, что никому не надо этот код переписывать и заново отлаживать. Дошли у кого-то руки перевести на С — и ладненько. Программеры моего уровня (и выше) и не такое прочтут, а всяким [sensored] все равно ничего не поможет. Сложность там в математике, а не в коде (поэтому «прочтут», а не «поймут»).

Так что понюхай, выдохни и иди читать Кернигана с Ричи. Небось много нового про Си узнаешь.

Ох уж эти недоучки… Элементарных вещей не знают, нифига не умеют, а пытаются учить. В итоге из студентиков — ещё хуже недоучки получаются.

Вы свой костыль править собираетесь?
Господи, какой невероятный стыд.

Но зато понятно, какой треш, угар и содомия ждут пользователей твоих поделок, авторы которых фигачат наколенный код как придётся, потому что ровно в этот момент им вожжа под хвост попала под данным конкретным углом — «нам некогда нормально именовать переменные» (вот уже на этом MISRA C тихо плачет в уголке), «мы просто скопипастили из фортрана» и финальное «кому надо будет — те разберутся».
Какой же, однако, неоптимальный код генерит gcc… Но Вы не поняли что хотел сказать olartamonov. В С++, в отличии от C const внутри определения функции — это не локальная переменная, которую запрещено изменять, это именно константа. Компилятор может располагать её где угодно — зашить в код команды, расположить в области инициализированных статических переменных, или во flash-памяти. Последний вариант часто оптимален для микроконтроллеров, особенно таких как приведенный в примере в статье STM32F030F4P6 с очень малым объёмом ОЗУ. Поэтому ссылка на Кернигана и Ричи в этом случае некорректна — именно здесь C++ и C отличаются коренным образом. А что означает static — думаю объяснять было не нужно, всем понятно.
В С++, в отличии от C const внутри определения функции — это не локальная переменная, которую запрещено изменять, это именно константа


Ну, во-первых, const на неизменяемых константах ставят в первую очередь затем, чтобы дальше по тексту никто их случайно не изменил, а все люди, которые в следующие пять-десять лет будут читать и править этот код, понимали, что это — «справочное значение».

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

Во-вторых, GCC на обычном C переменные с модификатором const также кладёт во флэш, что локальные, что глобальные.
Какой же, однако, неоптимальный код генерит gcc…
Не оптимальный по каким критериям? Нам нужно попадание довольно больших циклов в небольшой кэш кода, поэтому для нас главное компактность. Отсюда и оптимизация в режим -Osи так далее

Компилятор может располагать её где угодно — зашить в код команды, расположить в области инициализированных статических переменных, или во flash-памяти
Будьте добры, выполните домашку за olartamonov:

  1. Дайте пример компилятора, который так делает и его код. Лучше штатный.
  2. Приведите цитату из стандарта, разрешающую компилятору так делать и укажите, когда это появилось.


Ну а соображения такие:

  1. Вполне верю, что может, но не обязан. Зачем использовать костыль в виде const, если прямое указание static отсылает ровно в rodata, то есть во flash.

Как видите — тупо копирует в стек при каждом вызове.
Худший из компиляторов, которые нужно использовать — это bcc для MS-DOS, за ним — gcc 2.95 для МСВС (и lcc для Эльбрус-2К). Специфика — мы делаем проекты на разном странном железе, нужном заказчику.



Поэтому ссылка на Кернигана и Ричи в этом случае некорректна — именно здесь C++ и C отличаются коренным образом.
Гм, где-то было указание, что это С++? В примере сишный код, компилируемый и так и так. У меня в примерах, кстати, компилируется как С++.

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

Единственное, что я могу там подправить — это писать static const. Но компилятор и так видит, что раз массив не изменяется, то это константа и его можно в rodata.

Но чистый const — это для данных условий костыль, ибо если и работает, то далеко не везде.

И главное — не работает на штатном компиляторе. То есть на пришедшем в Debian 8. На Debian 9 и других -посмотрите сами. Но штатный компилятор — это максимально надежный вариант в смысле исправления багов.
где-то было указание, что это С++?
здесь
../FarwLib/crc.cpp **** const char H[17] = "0123456789ABCDEF";

А в С, согласен, не нужно полагаться на оптимизатор, нужно писать static const.
А если я переименую в crc.f это сразу станет фортран? Язык ключами задать можно, расширение — всего лишь умолчание для компилятора и make,

А в С, согласен, не нужно полагаться на оптимизатор, нужно писать static const.

  1. static const — согласен, теоретически вернее на случай мелкого ОЗУ. Вот это я исправил.
  2. На оптимизатор вообще нельзя полагаться. При отладке может потребовать неоптимизированная версия, и она должна влезть в стек. Ну, например, проверить, что при отказе от оптимизации баг пропадает.
  3. Покажите мне, пожалуйста, настолько оптимизированный код. Я очень сомневаюсь, что компилятор может настолько вольно обращаться с массивом. А если у нас большой массив? Тогда получаются совсем разные нужды в ПЗУ/стеке в зависимости от оптимизации.
  4. С чего вы взяли, что у нас всегда будет оптимизатор? Мы всегда готовы, что придет заказ на перенос нашего кода на машинке 90ых, выпущенных тиражом в 200 экземпляров. Как минимум перенос на ядроv linux 2.4 и gcc 2.95.4 занял 4 часа работы.

Более того, мы даже 32битным байтам уже не удивляемся. Надо будет — перенесем и туда. А компилятор там — совсем не gcc.

Ну ниша у нас такая, двойного применения.
Самое забавное, что подобный трэш (программеры моего уровня и не такое прочтут — особенно позабавило — это от человека ни фига не понимающего в программировании встроенных систем), сочетающий в себе чудовищный апломб, совершенно ни на чем не основанный, с высосанными из пальца соображениями насчет размещения объектов, которые и 20 лет назад были не вполне верны а теперь просто полная чушь, подаются под лозунгом построения НАДЕЖНЫХ систем.
Вот только компилятор почему-то на моей стороне. Как думаете, почему? :-)

P.S. Подсказка — а что за 20 лет поменялось? Спутники GPS и ГЛОНАСС орбиты сменили? Стандарт NMEA 80ых годов сильно изменился? Процессоры сменили архитектуры?

Поскольку ничего не поменялось, то мы всегда должны быть готовы к заказу в реализации нашей системы на железе 90ых, выпущенном тиражом 200 экземляров исключительно для военных. И с соответствующим компилятором.

Уже был опыт, когда от нас попросили реализацию на linux 2.4 и gcc 2.95.4. И обошелся перенос туда часа в 4. А это не самое старое, что я могу представить.

Так что хоть 30 лет, хоть 40 — это не важно.
Вы точно понимаете понятие «костыля» в ПО?!

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

Я не вижу смысла продолжать дискуссию с Вами, так как и мне и так стало ясно об Вашем уровне знаний и умений.
Ну так что там с автопилотом? Будет рассказ о его сложности или, как обычно, в кусты?

Вы точно понимаете понятие «костыля» в ПО?!
Раз у вас русский не родной, то сами дайте определение. Для меня это или workaround или hack.

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

Да тем же кодом они пишут, в отличие от технологов. Поверьте, про совместную работу математиков с программистами я намного больше вас знаю. Ну хотя бы потому то последние 10 лет с математиков работаю.

Можете полюбоваться, как математики код пишут. Вы же небось ни меток, ни goto в глаза не видели? А вот и ещё код от математиков. Нравится, да? Чувствуете тяжелый запах FORTRAN-IV?

Костыль чего?
Вы тогда в школу ходили, что ли? А в вики прочесть не судьба?

Git и Mercurial это костыли, созданные из-за отзыва бесплатной лицензии на BitKeeper. Причем Git писался самим Линусом по принципу «быстро и дешево» — 3 апреля 2005 года разработка началась, и уже 7 апреля код Git управлялся неготовой системой.

Ровно потому. что это был наспех слепанный костыль, его назвали GIT, что на английском сленге означает «мерзавец». Впрочем сам Линус сказал, что он назвал мерзавцем в честь себя: I'm an egotistical bastard, so I name all my projects after myself. First Linux, now git.

Не видели man к Git? Там ясно написано: git - the stupid content tracker. Ну и ещё чуток с английской вики. Одна из расшифровок GIT — "goddamn idiotic truckload of sh*t", причем обозвал его так сам Линус.

Просто GIT — это очень хороший костыль. Многими любимый. Используемый миллионами. Но по происхождению и по устройству -это костыль. А уж Git for Windows — костыль в квадрате.

Впрочем, как известно, linux — это вообще терминалка-переросток. Линусу просто не хватило функций в ядре MINIX. По крайне мере в 1994 году знающие его фины рассказывали именно эту историю.

Я не вижу смысла продолжать дискуссию с Вами
Похоже мыс вами одной национальности, если вы не видите смысла, но продолжаете.

Ну так то с самолетным автопилотом? Слились полностью и рассказа не будет? Не люблю я таких, не умеющих отстаивать свою позицию. Детство это. Или уж признайте, что он самолетный автопилот не сложен или докажите его сложность.
> Можете полюбоваться, как математики код пишут. Вы же небось ни меток, ни goto в глаза не видели? А вот и ещё код от математиков. Нравится, да? Чувствуете тяжелый запах FORTRAN-IV?

Намного лучше того, как код пишут (не)настоящие программисты (https://habr.com/ru/post/443030/#comment_19873516 ).
Вы любите метки и goto? А можно посмотреть на ваш код? Хочу увидеть goto в современном С++.
Вопросы любви или ненависти к goto никак не помешают при необходимости использовать cdflib (благо она более-менее протестирована еще во времена Fortran-IV). А вот с решениями «Фарватера» я на одном поле срать не сяду.
Скажите пожалуйста, для вас русский язык родной или нет?

С какой целью интересуетесь?
Git — это костыль

Костыль чего?
Ну и сколько фирменных запчастей вы могли купить в любой день в 1993 году? Мое решение продержалось, пока не нашлись деньги на новую клавиатуру.

Не надо мне рассказывать мне о 90-х. Многие сами ремонтировали, исправляя не исправность, а не костыляли, как Вы. Костыляние говорит об низком уровне инженерной подготовки.
Но если надо быстро и дешево — нужно уметь применить костыль.

Знаю одного руководителя фирмы, который любит цитировать «надо быстро и дешево». Только ни один проект за последнее время, созданный по такому принципу, не взлетел.
И почему же они не взлетели? А потому, что состоят из костылей (говна и палок).
Ну ОК, отвечу. Да затем, что исправление «одиночных сбоев» занимает 90% времени.
Если у вас при проектировании автопилота комбайна 90% времени занимает работа по предотвращению одиночных сбоев от космических частиц, то вы явно что-то делаете не так; даже если применяете самые правильные методы, проверенные еще NASA на «Аполлонах».
Хотел поругаться на слово «проектирование» вместо «Отладка», но потом вспомнил вашу профессию. Ну в общем увы — это совсем не проектирование,

Это только в вашей области отладка — небольшой этап. А в нашей отладка — это превращение того, что иногда работает в то, что работает всегда.

Один из последних примеров. В четверг принимаем с приемника псевдодальность L2CL почти 150 тысяч км (при нормальном приеме L1). Это треть расстояния до Луны, спутники летают примерно на 20 тысячах км.

ТЗЧ? Маловероятно, этот приемник выпускается и с 5ой и с 9ой приемкой, то есть от ТЗЧ более-менее защищен.

Редчайший сбой ком-порта, испортивший биты так, что контрольная сумма сошлась? Маловероятно, можно поверить в такое на фоне массовых сбоев по контрольной сумме, но там примерно раз в 1-2 часа.

Баг в прошивке приемника? Возможно, возможно. Похоже что к частичной псевдодальности (в пределах мс) добавили примерно скорость света, помноженную на полсекунды (вместо обычных 70 мс). Но… это приемник геодезического класса. Если и есть в нем такой баг, то почему-то он проявляется раз в год. Пока что автор приемника баг отрицает.

В итоге что? Чертыхнулись и добавили ещё одну проверку. И да, это первый такой случай за 10 лет работы. Ноль вместо псевдодальности- видел, частичную псевдодальность видел, NaN вместо псевдодальности видел. Такого — не видел.

В тот же четверг — ешё один баг из серии «не бывает», на сней раз у CNES. Ну вроде всем известно, что время течет в одну сторону. Но вот в GPS — это не всегда так. G32 выдал эфемериды с опорным временем на 16 часов, а через 20 минут — на 15:59:44. Посоветовались, решили что у него просто поздно прошла перезакладка эфемерид из ЦУП. А в CNES решили, что правильные эфемериды — это не пришедшие позже, а с более поздним опорным временем. И так решили не только в CNES, но и в НАВИС, да и у меня в коде… Ибо это логично. Логично — но неверно. Если приемник включиться в 16:30, он поймает только эфемериды на 15:59:44. Значит CNES свои поправки должен передавать на более поздние эфемериды, несмотря на их более ранее опорное время.

Вот это вот — за один день.

то вы явно что-то делаете не так
Видимо мы не так выбрали себе область. Да, авторы приемников шизеют от тех багов, что мы им рапортуют. Бьют себя пятками в грудь — нет мол у нас такой баги. А потом «спасибо, исправили».

Лет 5 назад я ещё слышал «да у нас сотни тысяч приемников работают, и никто о таком баге не писал». Угу, сотни тысяч. Но используем для RTK — только мы, да сами разработчики один макет сделали. Теперь уже не слышу. Буква Р — репутация.

Как бы вам так объяснить поближе к вашей области… Видели errata на процессор? Ну не такой уж маленький документ. А теперь представьте, что вся errata пишется на основе того, что мы нашли.

вы явно что-то делаете не так
Да я не спорю. Мы делаем на приемниках за 10-20 баксов то, для чего остальные используют приемники за 30 тысяч баксов и более. Мы используем такие возможности приемников, которые до нас не использовал никто. Мы получаем приемники и прошивки к ним ещё до выпуска их продажу.

По процессорам — примерно такая же история с STM32H7, мы начали с ним работать, когда для него ещё в STM32CUBE багов было порядочно.

Я считаю это нормальным. Хочешь быть первым — значит первым наступаешь на грабли. Не хочешь наступать на грабли — значит используй старую технику и процентов на 20 того, что она может.
Это только в вашей области отладка — небольшой этап.
Нет, в моей области отладка — это не небольшой этап. Более того, ее вадность гораздо выше, потому что производство новой партии чипов несколько дороже, чем смена прошивки микроконтроллера. Но да, отладка — это часть проектирования. Неотъемлемая.

этот приемник выпускается и с 5ой и с 9ой приемкой, то есть от ТЗЧ более-менее защищен.
Нет, не значит. Сама по себе ни пятая, ни девятая приемка никакой защиты от ТЗЧ не предполагают.

Как бы вам так объяснить поближе к вашей области… Видели errata на процессор? Ну не такой уж маленький документ. А теперь представьте, что вся errata пишется на основе того, что мы нашли.
Какое отношение эррата процессора имеет к вашим рассказам про одиночные сбои? Вы реально отвечаете какому-то радио в своей голове, а не на вопросы, которые вам задают.
Про радиационную стойкость это вообще вы начали, она в подавляющем большинстве случаев ни при чем.
Но да, отладка — это часть проектирования. Неотъемлемая.
Никогда не говорите такого программистам. Засмеют. У нас проектирование — это процесс определения функциональных блоков, входящих в устройство. Потом идет программирование — написание алгоритмов, потом кодирование, отладка, тестирование, опытная эксплуатация, опять отладка, опытно-промышленная, опять отладка и уж потом промышленная эксплуатация.

Я так понимаю, что у вас все что до промышленной эксплуатации называется проектирование? я на своем этапе проектирвоания могу лишь заложить методы отладки.Например вписать в требования, что программа выполняется как SoC по реальному сигналу, так и под Windows по файлам с записью сигналов. Ну и запроектировать написание софта для записи сигналов с SoC.

Сама по себе ни пятая, ни девятая приемка никакой защиты от ТЗЧ не предполагают
Гм, а можно пруф? Вы тут специалист, я вам верю, но всегда считал, что 9ая приемка — это радиационностойкая. В любом случае, поскольку космическое применение прописано в свойствах приемника, какая-то радиационная стойкость там есть.

Какое отношение эррата процессора имеет к вашим рассказам про одиночные сбои?
Видимо опять у вас иные термины.

Мы рассматриваем приемник как черный ящик. На входе антенн, на выходе — измерения. Поэтому сбой — для нас случайное событие. Ровно так же рассматривается и процессор -черный ящик с кучей ручек.

С другой стороны, для разработчика приемника или процессора — это белый ящик. Можно подключить имитатор спутникового сигнала и большинство редких ситуаций воспроизвести.

Фактически результат нашей отладки — это такая большая errata на исходную версию прошивки приемника. Часть производитель правит, часть не правит, но мы стараемся обойти всё. Увы, бывает, что уже устраненные проблемы иногда возвращаются.

Так что аналогия с errata процессора полная. Ну разве что в процессоре ситуации попроще, ибо редко зависят от невидимых для пользователя состояний. А вот в GPS-приемнике большинство внутренних состояний невидимо.

Про радиационную стойкость это вообще вы начали, она в подавляющем большинстве случаев ни при чем.
Согласен. Уж очень многое надо исключить, чтобы списать ошибку на случайный сбой или сбой из-за ТЗЧ. Все-таки в 99.99% причины прозаичнее — просто баг в чужой прошивке.

Но работать-то надо невзирая на чужие баги. Потому и 90% времени уходит на отладку.
Никогда не говорите такого программистам. Засмеют.
Нет, нормальные не засмеют. До мышей и терминов докапываются только люди, которым нечего обсудить по сути.
В ЕСКД (ГОСТ 2.103-2013) есть эскизный проект и технический проект. Или программисты не по ЕСКД работают?

Гм, а можно пруф? Вы тут специалист, я вам верю, но всегда считал, что 9ая приемка — это радиационностойкая. В любом случае, поскольку космическое применение прописано в свойствах приемника, какая-то радиационная стойкость там есть.
Почитайте соответствующие ГОСТы. Там все написано.
В американском стандарте Mil-std-883 (он, в отличие от наших ГОСТ, не засекречен) есть следующие вещи, касающиеся радиации:
1017.2 Neutron irradiation
1019.8 Ionizing radiation (total dose) test procedure
1020.1 Dose rate induced latchup test procedure
1021.3 Dose rate upset testing of digital microcircuits
1023.3 Dose rate response of linear microcircuits
Вы видите здесь что-то про ТЗЧ? Вот и я не вижу.
«Какая-то радиационная стойкость» — это хорошее определение требований приемки)

Видимо опять у вас иные термины
Нет, у вас. Более того, вы ими жонглируете так, чтобы прикрыть собственное неумение ими пользоваться. 90% времени на отладку — это нормально. 90% времени на отладку последствий попадания ТЗЧ в автопилот комбайна — ненормально. А вы говорили именно о нем.
Или программисты не по ЕСКД работают?
Угу, угадали. И даже не по ЕСПД.

Почитайте соответствующие ГОСТы. Там все написано.
Ссылочки, если не секретно.

90% времени на отладку последствий попадания ТЗЧ в автопилот комбайна — ненормально. А вы говорили именно о нем.
Ой как странно вы читаете…

исправление «одиночных сбоев» занимает 90% времени
90% времени уходит на отладку.

Где тут про ТЗЧ? Вас смутило понятие «одиночный сбой»? Я вам описал две ситуации. Обоих я не видел ни разу за 10 лет работы, моя начальница — за 25 лет. Это как, массовые ситуации или одиночные? Не, бывает, конечно, что «на 18ый день зимнего похода по приполярному Уралу обнаружили, что забыли дома печку.» Для прояснения, найдя редкую ситуацию, вешаем на неё диагностику, а потом проверяем, отработала ли она.

Так что одиночных ситуаций у нас много. А про ТЗЧ я говорил в контексте троированного Аргон-16, работающего на союзах.

90% времени на отладку — это нормально.
В целом, вы правы. Автопилот комбайна очень простая штука, если сравнивать с RTK и PPP. И отладка у него довольно простая. Силы уходят не на автопилот, а нашу основную работу — высокоточку.
Ссылочки, если не секретно
Я ровно потому дал ссылку на американский стандарт, что российский секретен. Но американский вполне даёт представление о том, что происходит. Сказать, насколько он аналогичен российскому, я тоже не могут потому что российский стандарт секретен.
Так вот, в американском военном стандарте по радстойкости нет ни слова про ТЗЧ. Поэтому, кстати, military-grade чипы нельзя бездумно использовать в космосе.
Так я про 9ую приемку, не про 5ую. Но действительно, я не различаю ТЗЧ и иные варианты радиации. Не моя область.
Вы ни черта не понимаете во многих областях, про который пишите.
Помимо ЕСПД, хорошие программисты используют и другие ГОСТы и стандарты.
По процессорам — примерно такая же история с STM32H7, мы начали с ним работать, когда для него ещё в STM32CUBE багов было порядочно.

А без куба никак? И Вы после этого считаете себя хорошим разработчиком?!
Как бы вам так объяснить поближе к вашей области… Видели errata на процессор? Ну не такой уж маленький документ. А теперь представьте, что вся errata пишется на основе того, что мы нашли

Вы себе льстите. Вы прям как ВДВ-шники: «Никто кроме нас».
Да, для понимания надежности комбайнового автопилота. Прием GPS-сигнала идет на уровне в 100 меньше фонового шума. Поэтому куска мокрого брезента, брошенного на антенны — хватает для вывода системы из строя. Любой системы. Хоть нашей, хоть американской.

Поэтому надежность не так важна. Важнее — достоверность. Те самые 2см отклонения от заданной траектории.

Если картошку сажать ровно в грядки, её вырастает на 30% больше, чем при равномерной посадке. Но требуемая долговременная стабильность — меньше 5 см на орудии. Это, правда, не про комбайны, а про трактора.

Ещё один важный критерий — доступность. Один спутник сломался, второй — на плановом ТО, остальные — разлетелись и низко висят… Вот тут как раз хочется минимум пять девяток.

А надежность… Сезон отработал — можно полгода чиниться. Так что надежность решается путем доступности запасных блоков — ну скажем 1 на 100 комбайнов хватит с запасом.

Вот такая вот специфика.
Поэтому надежность не так важна. Важнее — достоверность

Вот здесь Вы в корне ошибаетесь. Надежность важна всегда и не важно на земле, под землей, в воздухе, на воде или под водой нашло применение разрабатываемое вами устройство. Бывают случаи когда устройство разрабатываемое для стационарных наземных систем, находит свое применение на подводных лодках.
Ну только если это будет летающая подводная лодка. Пары милллиметров воды достаточно, чтобы заглушить прием GPS.

Нет смысла делать супернадежную обработку GPS, когда у нас сам прием GPS блокируется куском мокрого брезента. Есть смысл бороться за точность и долговременную стабильность.

Надежность важна всегда
Расскажите об этом производителям лампочек накаливания. Можно было (и делали) очень надежные лампочки. Только они выходили в разы дороже. Есть спрос на надежные лампочки накаливания по десятерной цене? Увы, нету.

На LED-лампы с ценой х10 от ламп накаливания и сроком службы х10 спрос есть и он растет (даже не говоря о том, что они значительно меньше электричества потребляют).
Ну так это всего лишь 10х срока службы за 10х цену. А сколько будет стоит выпуск столетних лампочек? Угу, углеродная нить не перогорает из-за пусковых токов. Но цена…
Ну только если это будет летающая подводная лодка. Пары милллиметров воды достаточно, чтобы заглушить прием GPS.

Где Вы в моем комментарии видели про GPS под водой?! Не надо читать между строк, то чего нет.

Вы не понимаете, что такое надежность, если привели пример про лампы накаливая.

Вот Вам не больший ликбез из ГОСТ 27.002-2015: «Надежность: Свойство объекта сохранять во времени способность выполнять требуемые функции в заданных режимах и условиях применения, технического обслуживания, хранения и транспортирования.»
Где Вы в моем комментарии видели про GPS под водой?!
Ну вот же: под водой нашло применение разрабатываемое вами устройство. и тут Бывают случаи когда устройство разрабатываемое для стационарных наземных систем, находит свое применение на подводных лодках.

Мы занимаемся высокоточным GPS (точнее GNSS, то есть GPS, ГЛОНАСС, GALILEO и так далее).

Так что подводная лодка нам светит только летающая (в степях Украины, видимо).

А для корабельных систем — другое устройство, тоже RTK, но работающее по иным принципам.

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

Одна из — согласен. Но не далеко не самая главная. Например, нам важнее доступность.

Вам нравится прибор, работающий 20 минут раз в два часа? Не, он вполне надежен. Но с доступностью лет 10 назад у него была беда.

С другой стороны, китайские смартфоны — ненадежны. Но зато дешевы. И имеют высокий спрос. Даже айфоны — ненадежны. Одно купание — и опаньки.

А какой спрос на надежные смартфоны, которые можно уронить на бетонный пол или искупать в ванне? Увы, нишевый.

Так что надежность — не самая важная для потребителя характеристика. Просто одна из. Цена, удобство, доступность, точность, цена владения — важнее. А надежность должна согласоваться с моральным устареванием.

Что толку в надежности Nokia-1610? Кто его купит кроме ретро-энтузиастов? Nokia-3310, не терявший цену лет 15 — редчайшее исключение.

Одно купание — и опаньки.

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

После дешевых китайских многие переходят на более надежный смартфоны. Есть примеры.

ак что надежность — не самая важная для потребителя характеристика.

Для потребителя с низким достатком действительно так. Но когда такой потребитель поймет, что на дешевый и не надежный товар он потратил столько же денег, как и на дорогой. Срок службы купленных дешевых товаров оказался меньше, он задумается о покупке более надежного варианта.
Nokia-3310, не терявший цену лет 15

Потому, что надежен.
Это нарушение инструкции по эксплуатации.
Вы про «запрещается пользоваться лифтом во время землетрясения»? Ну таким способом задрать надежность до небес легко. Только это не к нам, мы такой фигней не занимаемся.

не поливаете работающий телевизор из лейки
Как ни странно, телевизор пережил пролитый ребенком на него чай. И да, я считаю это рядовой ситуацией. Многие дети ставят чашку куда попало. И очень многие — сбивают чашку локтем.

После дешевых китайских многие переходят на более надежный смартфоны.
Ну покажите мне этих многих, ушедших с айфонов на надежные аппараты? Сколько вообще этих надежных частные лица покупают? Тысяча в год наберется? А «более надежный» все равно ненадежен.

огда такой потребитель поймет, что на дешевый и не надежный товар он потратил столько же денег, как и на дорогой.
Никогда. Разница в цене — десятки и сотни раз.

Поищите мобильник с реальным IP68 и посмотрите сколько он стоит.

Мой lanrover XP-7800 стоит в 3 раза дороже аналога без защиты. Но защита там китайская. На самом деле нет там ни IP68, ни защиты от падения на бетонный пол. Увы, проверял. Зато — дорогущие запчасти.

Так что больше меня «надежностью» не заманишь. Лучше каждый год покупать новый мобильник за 3-4 тысячи, чем раз в год тратить 6 тысяч на ремонт «надежного» аппарата.

Возвращаясь к программированию. QNX намного надежней линукса и винды. Ну и как? Много персоналок на QNX вы видели?

P.S. Ну вот вам надежный кнопочный телефон. Купите такой за 40 тысяч?
IP68

И когда пылевлагозащита стали главными показателями надежности?!
QNX намного надежней линукса и винды

Вы бросаетесь из крайности в крайность. Вам напомнить определение надежности или сами найдете?
Встречный вопрос: «Почему на большинстве серверных машин крутиться Linux?»
Встречный вопрос: «Почему на большинстве серверных машин крутиться Linux?»
Угу. Вот и подумайте, почему при наличии надежных QNX и FreeBSD, на серверах крутится менее надежный linux.

Знаю ряд систем, где применена FreeBSD на серверах. Выбор операционной системы у простого обывателя зависит от уровня его, как пользователя или администратора, необходимостью программного обеспечения (не все программное обеспечение разработано для всех ОС). Где необходима надёжность выбор делается из других соображений.
Согласен. Именно так — «где необходима надёжность» — там делаем надежность. Скажем наш корабельный компас легко примет на корпус несколько тонн забортной воды во время шторма. И работать не перестанет — у него дорогущие судовые разъемы.

Но нафига такая надежность для комбайна? Не, там где надо (в антеннах) — там у нас IP68. Не будем мы писать в инструкции «Перед заездом на мойку снять антенны». Все рано не снимут.

Но нафига комбайну судовой корпус и судовые разъемы?

P.S. Один коллега — кандидат в сборную РФ по яхтенному спорту, другой — каперанг (бывший штурман подлодки), гендир — яхтсмен… Ну живет мы в городе, где 20 видов дождя в неделю. Поняли, почему для нас IP68 важный параметр? :-)
Но нафига такая надежность для комбайна?

Вы рассчитываете, что Ваш блок в комбайне будет работать в «тепличных» условиях и в неагрессивных средах?! Вы делаете блок для «лакшери» комбайна?
Пару тонны воды на корпус он не поймает. В -20 комбайны просто не ездят. Даже при нуле — редкость, он просто утопнет на поле. Напряжение питания — стабильное, это не локомотив, с провалами вдвое при запуске дизеля.

Что остается? Что под кожух машины попадает? Ну тепло там, вот и все. Даже пыль к нам не залетает — мы высоковато висим.

Вы делаете блок для «лакшери» комбайна?
По кабине — да, luxuкy. Тепло, тихо, мягко, 270 градусов обзора. И очень высоко над землей. Экспорт в 50 стран, внушает?
По кабине — да, luxuкy. Тепло, тихо, мягко, 270 градусов обзора. И очень высоко над землей. Экспорт в 50 стран, внушает?

Похоже по всему экспортируют устройство разработанное без Вашего участия. Я бы допустил к разработке человека с Вашим поверхностым уровнем знаний.
Ну, вообще то, я по первой профессии тракторист-машинист 3 класса, и в наше время параллельность борозд обеспечивалась выносным щупом-повторителем, а вовсе на системой навигации.
Маркировка стека и есть фактически стандартизованный способ, он используется в различных SDK и RTOS.
Есть ещё автоматизированные инструменты для расчёта дерева вызовов, но они сильно ограничены в применении так как не могут учесть наложение прерываний, о чём автор собственно написал.
Статья явно не для тех, кому квалификация позволяет делать автопилот или систему управления АЭС :)
К сожалению, недостаточная квалификация ещё никого не останавливала от того, чтобы делать что-то, потенциально опасное для жизни. Особенно если нет понимания, что квалификация недостаточная, зато есть горящие глаза и нулевой раунд инвестиций.
Одних горящих глаз явно недостаточно чтобы начать производство и продажи таких дорогих и сложных вещей как автопилоты или САУ для АЭС :)
А тем разработчикам, которые все же дошли до таких сложных и ответственных вещей, но не научились качественному тестированию — им никакие приписки в статьях уже не помогут начать это делать.
С чего вы решили, что автопилот — это сложная штука? Это для автомобиля он сложен. А для самолета или комбайна — довольно прост.
Самолетам не занимаемся, а комбайны прошли этап госиспытаний опытного образца. Впрочем, как и у конкурентов из Ебурга. А западные системы лет 15 есть, просто дорогие слишком.

Кстати, то, что автопилот для самолета был сделан в 1912 году намекает, что ничего сложного там нет. Ну то есть не сложнее PID-регулятора.

Сложное — это управление цементной печью. Там люди диссертации пишут на основе опыта живых операторов. Ну просто потому, что математически она не рассчитывается. Там нечеткая логика и экспертные системы. Ну то есть явно не 1912ого года технологии.

в описанных вами случаев все можно решить более простым способом - использованием компьютера с ОС, вместо мк)

ну серьезно, автопилот это очень ресурсоемкая вещь, мк просто не хватит

как и управление АЭС наверное

Судя по фрагменту кода:
while (start < top) {
*(star++) = STACK_CANARY_WORD;
}
создаётся впечатление, что перед публикацией его не показывали компилятору.
Вам стоить изучить работу с указателями, прежде чем писать такие комментарии.
Почему вы так думаете?
Потому, что этот код прекрасно собирается компилятором и корректно отработает. Раз Вы пишете такой бредовый комментарий, соответственно, Вы не разбираетесь с работой с указателями.
Вы на код из комментария внимательно смотрели? Попробуйте еще раз.
Собираем и изучаем.
Компилятор gcc 6.3.0, стандарт С99.
Исходный код
#include <stdio.h>
#include <stdlib.h>

#define STACK_CANARY_WORD   0xDEADABBA

int main(int argc, char** argv) {
    int test_memory[1024] = {0x00000000};
    int *start = &test_memory[0];
    int *stop = &test_memory[1024];
    int cnt = 0;
    
    
    printf("before start 0x%p\n", start);
    printf("stop 0x%p\n", stop);
    while (start < stop) {
        printf ("[%d]\t0x%08X\n", cnt, *(start++));
        cnt++;
    } 
    printf("after start 0x%p\n", start);
    
    start = &test_memory[0];
    printf("before start 0x%p\n", start);
    while (start < stop) {
        *(start++) = STACK_CANARY_WORD;
    } 
    printf("after start 0x%p\n", start);
    
    start = &test_memory[0];
    printf("before start 0x%p\n", start);
    cnt = 0;
    while (start < stop) {
        printf ("[%d]\t0x%08X\n", cnt, *(start++));
        cnt++;
    }
    printf("after start 0x%p\n", start);
    
    return (EXIT_SUCCESS);
}

.

Глазастые, до опечатки докопались, так как к сути статьи докопаться не смогли. Сразу пословица русская вспоминается: «В чужом глазу соломину видит, а в своём — бревна не замечает».
Глазастые evgus, emmibox, dmitryrf, для начала статьи писать начните, а потом посмотрим на их идеальность и отсутствие опечаток.
«Критиковать автора легко, но трудно его оценить» (Люк де Клапье Вовенарг)
Вы теперь в «сперва добейся», что-ли решили поиграть? Да не обижайтесь, не заметили — бывает…
Попробовал этот способ, и обнаружил интересное поведение.
Заполнение памяти я добавил прямо в startup, который использую из CMSIS.
изменения в startup
Reset_Handler:
ldr sp, =_estack /* set stack pointer */

ldr r0, =_ebss
ldr r1, =_estack
ldr r2, =0x6B6B6B6B
Clear_Heap:
str r2, [r0, #0]
add r0, #4
cmp r0, r1
bne Clear_Heap



В самом коде, функция func которая должна отъесть от стека 200 байт, и _write, это чтобы вывод printf через SWO работал.
main.c
#include "stm32f4xx.h"
#include <stdio.h>
#include "rcc.h"

uint32_t stack_size=0;
extern uint32_t _ebss;
extern uint32_t _estack;

int _write(int file, char *ptr, int len){
	while(len--) ITM_SendChar(*ptr++);	
	return 0;
}

uint32_t check_stack_size(void) {
    uint32_t *addr = (uint32_t *)&_ebss;

    while ((addr < &_estack) && (*addr == 0x6B6B6B6B)) addr++;
    return ((unsigned)&_estack - (unsigned)addr);
}

void func(void){
	volatile uint8_t data[200];

	data[10]=0xDD;
	data[199]=data[10];
	return;
}

int main(void){

	stack_size=check_stack_size();
	func();
	stack_size=check_stack_size();

	printf("Stack size %ld\n",stack_size);
	stack_size=check_stack_size();

	while(1){
	};
}


Собираю с -O0, значение stack_size смотрю под отладчиком.
Первый вызов функции — stack_size=40, второй вызов — stack_size=208. Как и должно быть.
А вот вызов после printf возвращает 130912. Очевидно, что даже прожорливый printf столько не съест.
Стал смотреть память, и оказалось, что действительно, после вызова printf память за bss изменена. Но не вся, а только небольшой кусок. И со стороны стека, еще кусок.
Насколько я понял, несмотря на то, что я не использую динамическое выделение памяти и _Min_Heap_Size у меня стоит 0, линкер располагает секцию _user_heap_stack за bss. Секция размером _Min_Heap_Size + _Min_Stack_Size. Ну так по крайней мере в моем случае.
Посмотреть это можно в map файле.
И printf видимо использует динамическое выделение памяти.
Я не нашел, как в main.c получить значение переменных _Min_Heap_Size и _Min_Stack_Size из .ld, поэтому просто добавил свое значение размера стека к объявлению переменной:
uint32_t *addr = (uint32_t *)&_ebss + 0x400;

В таком варианте заработало правильно, после вызова printf стек вырос на 352 байта.

И еще небольшое добавление по поводу стека. В некоторых МК STM32 есть CCMRAM. Это область памяти, с которой не может работать DMA, но может ядро МК. Для F407 например, указанный объем RAM в 192кб это 128кб RAM и 64кб CCMRAM. CCMRAM это отдельная секция и если явно не указать, что там надо разместить переменную, то она просто не используется. Так вот, в нее можно положить стек, освободив RAM.
Насколько я понял, несмотря на то, что я не использую динамическое выделение памяти и _Min_Heap_Size у меня стоит 0, линкер располагает секцию _user_heap_stack


Да, printf/scanf/etc. могут, в зависимости от конкретной реализации, использовать или не использовать кучу, равно как и куча, в зависимости от конкретной реализации, можно быть сделана по-разному.

Например, newlib, собранный по умолчанию, и newlib, собранный со specs=nano.specs, имеют радикально разные футпринты printf, а во FreeRTOS сразу пять реализаций кучи разной функциональности.

Все равно, они едят память как не в себя и лучше заменять все самописными. По крайней мере, на f0.
И компиляторы keil и gcc компилируют сильно по-разному

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

Знать что делаешь надо в любом случае, а не только с malloc. Сам malloc не приводит к дефрагментации, причина дефрагментации — free. Использовать malloc очень удобно на стадии инициализации, и достаточно безопасно, так как легко проверяется тестами. А вот в runtime злоупотреблять malloc действительно не стоит.
Просто взять побольше не получится, нужно все равно как-то проанализировать потребности программы. Хоть через раскрашивание стека, хоть любым другим способом из этой статьи или из комментов к ней.
С большим — а насколько большим? 20 Кб? 40? Мегабайт? Если никак не профилировать и не оценивать потребление стека, то как узнать, сколько вам хватит? Или сразу Малину ставить предложите?
Я не против профилирования. Но если памяти хватает уже в притирку, и есть опасения, что стек достанет данные, то лучше брать МК с запасом на случай расширения объема программы в следующих версиях. У меня уже возникла ситуация с нехваткой памяти. Пришлось вместо STM32F030C8T6 с 8кБ взять STM32F030CCT6 с 32кБ, по распиновке совместимый.
Это закупщики не сказали своё фи и паяльщики, которые привыкли TSSOP20 паять, значит это f030f4p6 и tqfp48, значит это f103cbt6.
Ставьте уж сразу STM32H7 с мегабайтом.
Ну, где-то на партии от 10 тыс. штук жизнь этого чувака и правда оказывается дешевле, чем разница в стоимости между двумя контроллерами…
Дешево же Вы оценили его жизнь — на партии 10 тыс. штук разница между STM32F030F4 и STM32F070F6P6 — $1480, между STM32F407VET6 и STM32F427VGT6 — $11890 (цены взяты с сайта ST). Такая разница оправдывает трудозатраты на оптимизацию, но уже даже замену программиста на более квалифицированного — сама по себе как правило нет.
После определения фактически используемого объёма стека окрашиванием полезно поставить на наибольшую глубину стека точку останова по обращению к ячейке памяти. Это позволит увидеть, в какой ветке программы стек используется максимально. Это нужно потому, что в случае, если программа попадает в эту ветку редко, совпадение времени нахождения в ней, и всех возможных прерываний может случаться очень редко, и за время тестирования может не случиться ни разу. Поэтому в случае, если останов на этой точке останова произошел не в прерывании, или не в том прерывании, которое использует максимальное количество стека, или если возможны вложенные прерывания — к полученному размеру стека нужно добавить соответствующий его размер, используемый в прерываниях. Также возможен случай, когда у функции, в которой наблюдается максимальное использование стека, есть совсем редкий вариант исполнения, который использует ещё больше стека — определив эту функцию его не сложно выявить простым анализом, и зарезервировать под него дополнительный объём стека. Вариант «просто добавить 10%» срабатывает не всегда, фактически 10% нужно резервировать просто на всякий случай, уже после резервирования под максимально возможную вложенность прерываний.
А вообще — описан довольно экстремальный случай, хотя такое и случается. На практике, если после реализации всего функционала остаётся менее 30 % любого ресурса — памяти программ, данных, или вычислительной мощности — нужно в следующей ревизии устройства менять контроллер. Потому что это позволит немного доработать функционал и устранить баги и недоделки, выявленные уже в эксплуатации, обновлением прошивки. В этом случае половину неиспользуемой памяти в релизной версии можно отдать под стек, а в отладочной выделить под стек объём, близкий к минимальному — тогда все связанные с переполнением стека проблемы выявятся ещё на этапе отладки.
Из своего опыта могу сказать, что важно не забывать о проверке стека, когда лезешь в какой-нибудь старый проект.
Обычно просят, добавь нам вот такой функционал. Ну добавляешь. И совсем забываешь, что программа то теперь требует чуть больше памяти и может упасть в самый неожиданный момент в тех местах, которые работали и протестированы на 10 раз.
А ведь был в PDP-11/45 аппаратный контроль стека и прерывание по желтой и красной границе — кому это помешало, никогда не поверю, что реализация этой функции очень затратна по аппаратуре. Конечно, проблему с пересечением стеков задач это не решало, но общий объем контролировать позволяло.
Определим цвет краски — конкретное значение неважно, ниже я просто настучал двумя пальцами левой руки. Главное — не выбирать 0 и FF:

Почему? Чем плохи это значения?
Вы считаете что вероятность встретить их в стеке больше вероятности встретить там 0х01, к примеру?
char buffer[1000] = { 0 };

Вот вам и вероятность встретить 0. На каждом шагу.
То есть это локальный массив, который Вы не собираетесь использовать в процедуре?
Или нулевые массивы, после использования, у Вас обычно остаются нулевыми?

Не кажется ли Вам, что этот пример сильно притянут за уши?
Кто вам сказал, для начала, что очередная проверка стека в многозадачной системе обязательно состоится после того, как вы этот массив не только используете, но ещё и используете до конца?..
Sign up to leave a comment.

Articles