image

Введение


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

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

На просторах интернета почти нет информации о том какая должна быть релизная сборка и как реализовать ее обновление, поэтому разработчик вынужден придумывать «велосипед» или пользоваться собственными наработками, которые далеко не всегда проверены на 100%.

Поскольку я принимаю участие в разработке ПО для различных Linux устройств (моё портфолио можно нагуглить по слову develinux) и дополнительно являюсь автором проекта 11-parts, мне регулярно приходится сталкиваться не только созданием сборок, но и разработкой механизмов обновлений через WEB или USB flash.

В этой статье я хочу поделиться своим опытом и знаниями в соответствующих направлениях.

Требования к сборке


В процессе разработки сборок и обновлений под различные устройства я для себя выделил несколько требований:

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

Эти требования я постараюсь подробнее изложить ниже, а после этого опишу 3 подхода в разбивке образов на разделы и их обновлениях.

Сборка не должна повреждаться при внезапном выключении питания


Кому нужно устройство, которое перестает работать после десятой перезагрузки? Никому! Если взять готовые дистрибутивы (а их очень мало для embedded), то без напильника из коробки они все весьма ненадежные в этом плане. Я очень хорошо запомнил проект, где использовал ubuntu под imx6, файловые системы на карте повреждались, иногда с десятой перезагрузки, иногда с сороковой, зависело от звезд на небе. Проект спасла ФС aufs. Дело в том, что ubuntu не предназначена для readonly, и всегда что-то должна писать. Похожую ситуацию помню в другом проекте, где использовалась yocto на SD карте. Вообще, так к сведению, SD карты это самый безобразный тип накопителя, который выходит из строя быстрее всех, гораздо надежнее emmc и nand. Если используется SD карта, то желательно на нее писать как можно реже во время работы, алгоритмы фонового переноса секторов очень непредсказуемы, я работал с десятками различных SD карт мировых брендов и не нашел ни одной карты, которую мог бы порекомендовать.
Но у SD карт есть несколько преимуществ, они доступны, недороги и удобны в отладке ПО.

К чему это я… А, вот к чему — корневая ФС должна быть readonly, никаких записей в нее быть не должно во время работы. Вы, наверно, задумаетесь: как так? Миллионы Андроид устройств всегда что-то пишут и не выходят из строя. Верно, но это все потому, что большинство устройств с Android, во-первых, имеют аккумулятор, а во-вторых, корневая ФС оформлена в виде ramdisk, а раздел system — readonly.

Если система должна быть надежной, то всякие рюшечки с установкой пакетов в корневую ФС могут многое подпортить. В качестве ФС рекомендую squashfs. Работает быстро, ничего писать не может, экономит место за счет сжатия…

А как же сохранение конфигов, загрузка файлов и т.д. спросите вы?
А вот для этого нужно создавать отдельные разделы RW. Если планируете писать в NAND, то рекомендую проверенный вариант — UBIFS. Если в NOR, то jffs2. Если писать на другой накопитель, то рекомендую ext4, btrfs, ReiserFS, лучшей ФС среди них отметить не могу, т.к. с всеми были различные проблемы.

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

Сборка должна быстро грузиться


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

Загрузчик должен работать безотказно


Загрузчик — это то, без чего не запустится сборка. В последнее время я часто наблюдаю за тем, как производители одноплатников облегчают разработку, выкладывая демо для SD карты с описанием как в нее прописать загрузчик или готовый образ с загрузчиком, который элементарно заливается командой dd. А что если SD карта зависнет? Такое же не редкость. Лично на моей практике карты частенько отваливались. Вот так работаешь за платой несколько часов, пишешь софт, бац и все… начинают сыпаться ошибки в ядре, карта отвалилась. А что, если это устройство, которое должно работать в полях без перезагрузки? И кстати, перезагрузка включая watchdog не всегда оживляют зависшую карту, у карты нет сигнала сброса, это не emmc, конечно же это больше вопрос к схемотехнике платы, если на плате стоит сброс питания карты, то это спасет, но это не везде. На некоторых платах помогает только передергивание питания или карты. Основываясь на своем опыте, я не рекомендую хранить загрузчик на накопителе с основной сборкой, если в процессе работы на накопитель производится запись. Если система на накопитель с загрузчиком ничего не пишет, а такое редко бывает, то пожалуйста. На моем опыте, в режиме readonly файловая система деформировалась только из-за аппаратных ошибок, но не программных.

Загрузчик следует хранить в надежном месте, на надежном накопителе, например в отдельной NOR или EEPROM микросхеме. Ниже пример модуля на базе чипа imx6ull, с SPI NOR для хранения загрузчика.

image

Сборка должна поддерживать обновление


Без обновления никуда… Я участвовал во многих проектах и никогда к сдаче работ не получалось идеального ПО. Всегда обнаруживается ошибка или требуется доработка функционала. Нужно понимать, пока люди пишут ПО, они будут ошибаться, пока люди пользуются устройством, они будут хотеть чуть большего. В 90% случаях, отсутствие продуманной системы обновления может привести как к головной боли производителя, так и к краху всего проекта. Например, разработана система видеонаблюдения для транспорта, система установлена по всей России и вдруг оказывается маркетологи недооценили рынок и не предусмотрели потоковое вещание, да к тому же еще и обнаружилось несколько ошибок в прошитом ПО, плюс потребитель начинает поглядывать в сторону конкурентов, потому что у них как раз есть то чего нет в купленном устройстве… Да, да, на чужом огороде клубника вкуснее и погода лучше (психология).
Что делать в такой ситуации? Если обновление поддерживается, то вариантов решений масса, ошибки можно исправить, потоковое вещание доработать, а функционал подстроить под потребителя, выдать потребителю прошивку с инструкцией и все. Но если оно не поддерживается, то производителя ждут большие приключения с командировками сервисных инженеров вплоть до замены устройств.

Система обновления в устройстве должна быть продумана до мелочей и протестирована на 100%. Одна ошибка в этой части превратит железо в кирпич, поэтому никаких допусков и исключений быть не должно.

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

Обзор подходов в разбивке образов на разделы с учетом дальнейших обновлений


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

Подход №1


image

Самый простой и доступный способ:
На накопитель, например SD карту, кладется образ, который прошивается из u-boot во встроенный накопитель устройства, например NAND flash.
В u-boot для этого нужно подготовить скрипты.
Из плюсов — это самый простой тип обновления, разработка которого займет максимум 1 день.
Недостатки этого подхода в отсутствии визуализации процесса и в очень ограниченных возможностях загрузчика, т.е. никакую сложную логику стандартными средствами не наворотить, если конечно же не придумать свою команду в u-boot (но это уже другой тип обновления, язык C великая сила). Этот способ не предназначен для обновлений через WEB — обеспечить контроль целостности прошиваемого образа проблематично, в ряде случаев размер сборки не должен превышать размера ОЗУ.
Кроме того, в некоторых задачах требуется сохранять настройки при обновлении, а это, при таком подходе, реализовать не просто.

Подход №2


image


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

В подходе используется минимальная сборка (ramdisk размером 8-16Мб) и основная. Ramdisk — это сжатый архив, поэтому сборка на 16Мб физически будет в несколько раз меньше.
Цель минимальной сборки — оценить основную сборку и загрузить ее.
Ramdisk размещается вместе с ядром и скриптами u-boot в FIT image.

Зачем FIT image и что он дает? FIT image — это формат, который поддерживается u-boot. Он обеспечивает целостность всех составляющих (ядро, dts, ramdisk, скрипты). Распаковка FIT image осуществляется в u-boot, причем, если не сойдется контрольная сумма, u-boot откажется его грузить. Это удобно, т.е. не нужно самим заботиться о контроле целостности, не нужно записывать несколько файлов по отдельности или придумывать свои образы, все делает FIT image. Обычно FIT image занимает 7-20Мб, его следует записать на отдельный высоконадежный накопитель, например, в qspi nor flash. Основную сборку можно хранить в более дешевой и ненадежной памяти, например, NAND flash. Поскольку основная работа будет происходить в основной сборке, то именно она повредится первой. В этом случае на помощь придет отдельный накопитель с минимальной rootfs.

Процесс загрузки.

u-boot загружает скрипт, который пытается использовать FIT обновления (FIT2), а затем FIT заводской прошивки (FIT1).

Если FIT2 нет или нарушена его целостность, проверка fit завершится с ошибкой и u-boot загрузит первый FIT (FIT1). Если FIT обновления (FIT2) есть, и он не битый, то грузится его ramdisk который проверяет rootfs обновления (Rootfs2).

Если Rootfs2 битый, то скрипты удалят FIT обновления (FIT2), затем после перезагрузки будет загружен заводской образ состоящий из FIT (FIT1) и Rootfs1.

Процесс обновления.

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

Ход обновления по шагам:

  • проверка образа на совместимость с железом и ПО,
  • проверка целостности образа в файле обновления,
  • копирование Rootfs2 из файла обновления в заранее подготовленный раздел,
  • проверка целостности скопированного образа в разделе,
  • копирование FIT2 в соответствующий раздел,
  • перезагрузка.

Если в процессе произойдет сбой, отсутствие или повреждение FIT2 не испортит систему, т.к. u-boot просто откажется его использовать и загрузит заводской образ. Поэтому в ходе обновления целостность FIT2 не проверяется.

После обновления, новая сборка будет размещена на основном накопителе в виде FIT2 и Rootfs2.

Данный способ стоек к механическим повреждениям накопителя и ошибкам ФС.

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

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

Подход №3


image


Этот тип обновления используется почти во всех проектах 11-parts, поскольку очень неплохо себя зарекомендовал.

Обновление подойдет под любые размеры сборок, для любых типов накопителей. В отличие от предыдущего типа, здесь SPI NOR используется только для u-boot, поэтому имеет меньший размер и меньшую стоимость, 1 Мбайт хватит вполне.

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

В примере используется накопитель SD карта, но может быть и NAND с использованием UBIFS, без разницы. В этом подходе отсутствует проверка Rootfs RO перед загрузкой, если сборка повредится, то система так и не узнает что она повредилась и будет ее грузить по кругу. Здесь предполагается, что данные в разделе RO никаким образом не могут быть изменены, этот подход исключает физическую неисправность накопителя. Если накопитель физически не исправен, то устройство нужно нести в сервис центр, никакого самовосстановления не предусмотрено. Это та цена, которую приходится платить за увеличение скорости разработки, удешевление поддержки и удешевление элементной базы, но она оправдана. Зачем страховаться от того, что почти никогда не произойдет.

Логика загрузки и обновления такая же как в предыдущем подходе.

В случае загрузки вначале u-boot грузит FIT обновления (FIT2), если его нет или нарушена целостность, u-boot грузит первый FIT (FIT1), стартует сборка прошитая на заводе и так до тех пор пока не обновят систему. Когда систему обновят — появится FIT2 и Rootfs2. В этом случае при загрузке устройства первым стартует FIT обновления (FIT2). В скриптах u-boot, которые хранятся в каждом FIT, должно быть прописано какую rootfs монтировать.

Shared partition RW


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

Подведем итог


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

На данный момент я использую только последние два, поскольку они больше всего подходят под требования. Для наглядности, вы можете ознакомиться с примерами устройств, где используются эти типы обновлений (подробности в портфолио 11-parts):

  • повторитель RS485 через 4G/WiFi/LAN,
  • плата управления контроллером промышленного дисплея 4K V-By-One,
  • комплексная система управления климатом ангара,
  • видео контроллер промышленного дисплея 2DisplayPort-LVDS,
  • система контроля линий,
  • VPN шлюз.

Если моя статья окажется полезной и интересной, я готов далее делится опытом и проверенными техническими решениями в области embedded linux на этой площадке.

Всем спасибо.
Горчаков Илья
telegram: develinux

Комментарии (55)


  1. capitannemo
    07.10.2019 20:28

    Вопрос как професиионалу.
    Что для дома и семьи посоветуете на текущий момент — orange pi, banana pi
    raspberry pi или алиэкспресс?


    1. develinux Автор
      07.10.2019 21:31

      Что выбрать, это дело вкуса. Если вы новичок, то советую raspberry. Если профи, то берите смело любой одноплатник под ваши нужды. Лично я на orangepi zero и lichee pi собирал и использовал yocto, все как по маслу собирается и заводится.


      1. Pilat
        07.10.2019 23:01

        Про NanoPI NEO Core2 нет ли мнения?

        И сразу… не дtлаете ли Вы UPS на маленьком аккумуляторе или ионисторе, передавая на GPIO сигнал о потере питания?


        1. develinux Автор
          08.10.2019 09:26

          Nano pi не тестировал, по характеристикам приличное железо.
          Но нет меганадежного накопителя для загрузчика. Загрузчик придется размещать в emmc с основной сборкой, плюс двусторонний монтаж, поэтому на плату пузом не посадишь, только через разъем.
          По поводу UPS, то эта задача для stm32. Лично я этим не занимаюсь, но могу спросить у коллег, сформулируйте задачу в личку, я передам.


        1. NickViz
          08.10.2019 10:25

          вот это не подойдёт? www.crowdsupply.com/silicognition/lifepo4wered-pi-plus
          готовое, для малины. на одно устройство не так дорого.


          1. Pilat
            08.10.2019 20:33

            Это по разным причинам может и подойти. Но продаётся ли оно, не очень ли оно дорогое, может ли использоваться не с RPi — вопросов много. Автор порассуждал о конкурентах, и там много интересного всплывает, так что устройство заслуживает внимания. Но это самоделка, как она будет поставляться неизвестно (скорее всего никак).
            (Так-то можно было бы собрать из двух компонентов — контроллера аккумулятора и повышающего преобразователя, просто собрать проводочками и приклеить к батарейному отсеку, но не будет рапорта о проблемах и будут разные нетривиальные случаи).


    1. lingvo
      07.10.2019 22:35

      RaspberryPi — 2 штуки. Использовать рекомендации автора статьи по поводу Readonly и Ramdisk для сохранности SD карты(полно статей в инете), питание через Powerbank(только следить, чтобы напряжение давал повыше). Так будет работать долго — у меня 4 года трудился.
      Второй Распбери с SD картой прошить образом первого и положить рядом. На всякий случай.


    1. lonelymyp
      07.10.2019 23:05

      У китайских клонов малины есть определённые трудности, то нет нужной версии ОС, или версия есть, но именно в ней нет поддержки чего-то, что было в прошлой версии, то конкретная версия ПО не работает в конкретной версии ОС.
      С малиной немного лучше в этом плане, большее сообщество исправило больше багов.


    1. Foxek
      08.10.2019 15:07

      Про ODROID почему-то все забыли. А Ведь он тоже весьма хорош)


  1. antonvn
    07.10.2019 21:00
    +1

    Какие у вас требования к аппаратной начинке одноплатников? Почему не использовали OpenWrt?


    1. develinux Автор
      07.10.2019 21:52

      Требования к начинке зависят от задачи.
      Мин требования 64Мб DDR2, 256Мб ROM (любого типа), CPU 500MHz.
      Изначально у меня была задача, которая требовала нечто готовое. Я поглядывал в сторону openwrt, понял что это проект для создания роутеров и не более, шаг в сторону, начинаются квесты и приключения.
      Поэтому решил, что проще разработать свой проект, чем тащить пласт неизвестного для меня кода, с неизвестными ошибками и подводными камнями. Все хорошо на словах, его рекламируют, у него большое сообщество, много отличных роутеров на его базе создано, но вот например сколько нужно потратить времени, что бы из него сделать видеодомофон, сколько нужно времени что бы весь его WEB интерфейс переделать под свои задачи да так что бы ничего не ломалось, хороший вопрос.
      Плюс как можно гарантировать стабильность решения не зная его на 100%. Поэтому было принято решение, разработать свой проект в котором перечисленные вопросы отпадут сами собой.


  1. develinux Автор
    07.10.2019 21:58

    .


  1. vdk10
    07.10.2019 21:58
    +1

    Интересно, но плохо читается без примеров.
    Напишите как реализовано всё вышеописанное в Raspberry Pi 3 (Pi 4) и Orange Pi.
    Что-то не нашел в портфолио про 11-parts. Можно ссылку?
    Было бы интересно почитать о:
    — повторителе RS485 через 4G/WiFi/LAN,
    — VPN шлюзе,
    — системе контроля линий(кстати, о каких линиях речь?) и
    — комплексной системаеуправления климатом ангара.


    1. develinux Автор
      07.10.2019 22:01

  1. 0lom5zhdovdv
    07.10.2019 23:23

    Насколько я понял, в RPi 4 пришли к описанному Вами. Ну почти пришли…
    Есть SPI чип на борту с бутлодером, обещают допилить настоящий USB boot, так чтобы SD карта вообще была бы не нужна. А на USB бери да и вешай нормальный SSD, который вместе с набортными конденсаторами и/или алгоритмом записи и гарантировано доживет до записи блока после его стирания (что и является проблемой окирпичивания SD) при срыве питания…


    1. IRT
      08.10.2019 09:24

      USB Boot был еще в Raspberry Pi 3B, 3B+, 3A+, и 2B v1.2. Это как раз в RPi 4 USB boot пока нет. Но обещают добавить в firmware.


    1. bmx666
      09.10.2019 15:23

      Да, в RPi4 есть загрузка с других носителей.
      НО, нигде не афишируется то, что там boot mode одноразовый и к тому же вы сразу лишаетесь 5 нижних пинов слева/справа в зависимости от boot mode.
      По моему мнению: лучшим решением остается сборка U-boot для RPi и выбор загрузки SD/USB уже в нём.
      Также не советую брать SOM RPi3 с eMMC, т.к. после выхода её из строя (а таких случаев уже много было) вы получаете абсолютный «кирпич», спасает только перепайка микросхемы.


  1. evgeny_boger
    07.10.2019 23:52

    Спасибо за статью. Кажется с eMMC всё было бы сильно проще: есть отдельные «аппаратные» бут-партиции, данные сами по себе не портятся, можно перестать всё хранить в raw и работать с файлами. Ну и нормальные eMMC не умирают сами по себе. Почему в новых продуктах продолжаете пользоваться NAND и SD-картами?


    1. develinux Автор
      08.10.2019 10:46

      1. 256Мб NAND дешевле чем 4Gb emmc. Меньше 4G — emmc не производится. Если не
      требуется большой объем, зачем переплачивать.
      2. Архитектура NAND прозрачна.
      Каждый производитель emmc использует свои алгоритмы, которые закрыты, это черный ящик хранящий сюрпризы в отличие от прозрачного NAND.
      NAND имеет кучу минусов, которые можно обойти, в отличие от черного ящика emmc.


      1. Wicron
        09.10.2019 11:24

        Полный бред.
        1. Нет. Смотрите цены на бирже Шеньчженя.
        2. Нет. Разброс параметров Nand как раз существенно влияет на качество выпущенного изделия, блочные устройства стабильнее в этом плане.


        1. develinux Автор
          09.10.2019 12:51

          1. Поскольку компания в которой я работаю, разрабатывает и производит электронику, мне известны цены официальных дистрибьюторов. Иногда в совместных проектах мне приходится самому заниматься поиском более дешевых замен. Дополнительно хочу отметить что чудес не бывает, emmc это NAND с контроллером, еще и большого размера, еще и с большими секторами типа MLC или TLC. Возможно вы нашли emmc дешевле, но это ничего не означает, может это остатки распродают, сегодня они есть, а завтра нет. Плюс еще влияет бренд, если сравнивать два разных бренда, например Micron и china noname, то результат может быть не предсказуемым. Дополнительно если уж сравнивать цены, нужно это делать в рамках одного бренда и NAND в сравнении нужно приводить с MLC или TLC плохого качества, а не дорогой SLC.

          2. Ошибки NAND известны, к ним можно подготовится. С точки зрения блочного доступа, emmc лучше чем NAND, экономится программистское время, не нужно заморачиваться с UBIFS, e2fs и подобными узкоспециализированными ФС, не нужно заботится от карте битых секторов, не нужно устраивать танцы c несовместимостью ECC и т.д. Поэтому ее используют, про ее удобство я не спорю, и еще раз подчеркиваю, emmc удобнее NAND…

          Я не готов в двух словах рассказать как работает emmc, нет времени, да и информации в гугле достаточно. Главное это то что emmc в фоне переносит сектора у которых сработал счетчик числа записей в другое менее зашкварное место. Физические сектора emmc размером например 1Мб, требуют время для переноса, плюс перед переносом требуется очистить сектор назначения. И вот представьте что будет если в этот момент вырубится питание. Я не говорю что emmc нельзя использовать, его весь мир использует. Просто хочу подчеркнуть небольшое преимущество NAND выраженное в простоте и открытости в отличие emmc, если проект имеет сборку размером 60Мб, то NAND это будет лучший выбор.


          1. develinux Автор
            09.10.2019 13:49

            Не e2fs, а f2fs. Сорри, перепутал.


          1. 0lom5zhdovdv
            09.10.2019 17:26

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


  1. Amomum
    08.10.2019 00:21

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


    • Цепляться к одноплатнику по ssh или vnc (или просто клаву/монитор подключать), писать и компилить прямо там. Терпимо, но на одноплатнике приходится держать компилятор, IDE и т.д.
    • Кросс-компиляция (поскольку одноплатники почти поголовно ARM'ы) и удаленная отладка. Писать комфортнее, компилировать может быть больно (поскольку приходится в своей системе держать либы, собранные под ARM); отладка может быть медленной и глючной. Если рабочий ПК под виндой — очень больно, приходится брать виртуалку с линуксом. Опять же, терпимо, рабочее окружение можно при желании затолкать в докер-образ.

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


    Но вот беда — докера под ARM нет :(
    Хотя я вот сейчас погуглил для порядка и увидел, что три месяца назад он вроде как появился. Хм.


    Тем не менее, может быть есть какие-то разумные альтернативы? Или я как-то вообще неправильно подхожу к этому процессу?


    1. ZEN_LS
      08.10.2019 00:32

      QEMU — виртуалка для армов.


      1. Amomum
        08.10.2019 00:33

        Вы не могли бы раскрыть свою мысль чуть более подробно?



        1. virtual9900
          08.10.2019 13:22

          Вероятно, имелась в виду разработка в эмуляторе.


          1. Amomum
            08.10.2019 13:40

            Интересно, насколько это медленно?


            1. slonopotamus
              08.10.2019 14:41

              Зависит от того чего у вас за процы (как в девайсе так и в том кто будет эмулировать).

              По моей инфе 5-летней давности: производительность qemu на 1 ядре Phenom II x6 @3.2GHz плюс-минус равна одному ядру OMAP2420 @400MHz. Только вот у фенома ядер шесть, а у OMAP'а всего одно. Ну и оперативы на десктопной машине может быть в разы больше. Поэтому смысл в эмуляторе очень даже есть.

              С тех пор десктопные процы стали побыстрей. Да и наверняка qemu научилась эффективнее эмулировать.


              1. slonopotamus
                08.10.2019 19:46

                Только не пяти-, а восьмилетней давности. Время летит...


    1. Dima_Sharihin
      08.10.2019 08:00

      поскольку приходится в своей системе держать либы, собранные под ARM

      Yocto Project максимально упрощает этот процесс. Он умеет отдельно собирать SDK для хостовой системы.


      отладка может быть медленной и глючной
      В эмбеддеде часто используют отладчики, работающие по USB 2.0 Full Speed (12MBit/s). Если у вас в железке есть езернет — о каких тормозах для отладки вы говорите?


      1. Amomum
        08.10.2019 12:58

        о каких тормозах для отладки вы говорите?

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


        1. Dima_Sharihin
          08.10.2019 13:09

          Для непосредственно отладки ssh как-то не нужен. На таргете запускается gdbserver с приемом соединений по TCP, на хосте — gdb


          1. Amomum
            08.10.2019 13:11

            Хм. Да, действительно, по ssh скорее всего только деплой делался.
            Тем не менее, на тот момент (года 4 назад) это было достаточно мучительно, окна эклипса так мееееедленно обновлялись, пошаговая отладка так мееееедленно шагала.


    1. develinux Автор
      08.10.2019 11:13

      Докер это отличное и модное решение, которое например ставит крест на костылянии
      в ubuntu с окружением, он требует высокой квалификации, он не прост, в масштабах 10 лет это молодой проект, который набирает обороты.

      Самый простой способ как мне кажется, это VirtualBox+eclipse+sublime+core i7+16Gb RAM

      В наше время любой производитель чипов, делает поддержку в yocto.
      С помощью yocto командой populate_sdk вы можете собрать SDK с компилятором, с правильными завистимостями, библиотеками, toolchain, binutils и т.д.
      Например bitbake core-image-minimal -c populate_sdk
      Далее переходите в папку своих исходников, запускаете скрипт из SDK, который правильно
      натраивает окружение и пути к кросс библиотекам и компилятору. Затем собираете
      без бубна, поскольку все нужные флаги устанавливает скрипт из SDK.
      Полученное под ARM заливаете на девайс и вуяла.

      Дополнительно советую использовать NFS, т.к. экономится много времени на разработку.


      1. Amomum
        08.10.2019 12:59

        Звучит достаточно радужно, надо будет попробовать. Спасибо!


    1. bmx666
      09.10.2019 15:16

      Можете глянуть в сторону Balena OS, там используется docker-контейнер для запуска своего ПО. Но их документация оставляет желать лучшего. Я 2 дня пытался разобраться, как запустить простой HelloWorld на C, слишком перемудренная реализация оказалась.


      1. Amomum
        09.10.2019 15:19

        Выглядит вкусно, жаль, если с документацией все плохо. Спасибо!


    1. fougasse
      09.10.2019 15:33
      +1

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


      1. Amomum
        09.10.2019 15:39

        Билдить на девайсе — дикая дичь.

        Согласен, но люди так делают. Особенно, если речь не про одноплатник на ARM, а про какой-нибудь промышленный комп на х86.


        Ну и просто стартовать с нфс

        А вот это мне в голову не приходило, спасибо.


    1. dvrpd
      09.10.2019 22:32

      Но вот беда — докера под ARM нет :(
      Всегда был. Основное требование для его работы на каком-либо хосте — поддержка ряда опций в ядре хоста, нужных для контейнеризации. От архитектуры устройства это не сильно зависит, пусть там хоть PowerPC будет.


      1. Amomum
        09.10.2019 23:14

        Допускаю. Возможно, просто готового пакета не нашлось (или я плохо искал). Так же, как под 32-битную ubuntu, например.


  1. selivanov_pavel
    08.10.2019 00:59

    ubuntu не предназначена для readonly, и всегда что-то должна писать

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


    /etc/rsyslog.conf
    
    *.* ~
    
    /etc/systemd/journald.conf
    
    [Journal]
    Storage=none

    ФС aufs

    aufs в ядро так и не приняли, сейчас советуют всем переходить на принятую в ядро overlayfs.


    Статья интересная, спасибо.


  1. embden
    08.10.2019 03:06

    А еще можно крутить всё поверх гипервизора со специально обученной машиной в качестве главной вм (dom0 в xen). Нужно обновление? Загружаешь новую виртуальную машину (domU). Такой подход вроде хотят реализовать в lfedge.


  1. ajratr
    08.10.2019 08:20

    Эх, если бы вы ещё так же хорошо написали как всё это делать…


  1. ABATAPA
    08.10.2019 09:39

    Делаю прошивки для некоторого оборудования на основе OpenWRT и (меньше) Buildroot в том числе запускал их на оборудовании, для которого нет прошивок на основе Linux. С OpenWRT вообще всё просто с обновлениями — есть штатный механизм, если что, его можно переписать.


  1. divego
    08.10.2019 11:43

    А что мешает в третьем случае проверить целостность rootfs1 RO? Ну, например, при заливке rootfs1 ro посчитать хэш и сохранить его u-boot enw, тогда можно будет его проверять, и если он битый, то выходить на скрипт u-boot для восстановления. Тогда получится тот же подход, что и в 2 =)


    1. develinux Автор
      08.10.2019 11:44

      Ничто не мешает, просто это повлияет на время загрузки, особенно если сборка около 1Gb. Плюс усложнит логику, хеш обновленного образа нужно будет записывать в окружение u-boot из Linux, или придумывать логику определения того что образ залит новый из u-boot, c подсчетом его нового хэш.
      Если уж речь идет о восстановлении, то зачем u-boot, здесь лучше подойдет ramdisk, а это вариант 2.


      1. divego
        08.10.2019 11:59

        Согласен. А так, как-то получил boot-loop при обновлении. Поэтому теперь мне во все железки очень хочется кнопочку, заведенную на gpio, которая запускает принудительно процесс восстановления при загрузке девайса.


  1. aptem334
    08.10.2019 11:55

    Спасибо за статью, но есть вопрос,

    Загрузчик следует хранить в надежном месте, на надежном накопителе, например в отдельной NOR или EEPROM микросхеме.
    . В малинке же нет этого на плате?


    1. develinux Автор
      08.10.2019 12:04

      За все малинки отвечать не берусь, но в документе Raspberry-Pi-Schematics-R1.0.pdf ее не нашел. Пришлите схему, я посмотрю.
      Поймите меня правильно, я специализируюсь на ПО для разработанных плат компании, в которой работаю, там малинки не используются.


  1. AlexanderDem
    08.10.2019 14:25

    Полностью с вами согласен, загрузка должна быть очень быстрой, я когда Kodi 15.2 под yocto собирал для Raspberry Pi 3B, смог добиться скорости включения от подачи питания до появления kodi Меню за 12 секунд, а вот Kodi 17.6 уже тормозной, быстрее 18 секунд так и не получилось (это при 10 классе microSDHC карты)


  1. vitamin
    08.10.2019 17:17

    Так в убунте ж, если она так нужна, там overlayroot есть из коробки…


  1. AlexanderDem
    09.10.2019 10:44

    Не всегда получается с помощью overlay fs настроить множество слoeв файловой системы, я например на работе вместе с коллегами остановился на следующем варианте: У нас две или три компьютерных стойки и при подаче питания один образ ОS раскидывается через pxe boot на 10 — 15 компьтеров, каждый комп выполняет свою задачу, и есть базовый squashfs образ и далее к нему навешивается через aufs еще два или три образа squashfs в зависимости от функции компьютера (дополнительные образы передаються не на все компы, а только на нужные, что ускоряет время загрузки всей стойки (максимум 2 минуты)) и далее еще навешивается слой верхнего уровня ext4 в виде одного файла, в который уже можно писать (read/write). И я смог подключить это только через AUFS. На мой взгляд офигенная штука, очень гибкая.