В данном разделе я рассматриваю часть возможностей по кастомизации, которые потребовались мне. Это не полный список того, что предлагает buildroot, но они вполне рабочие и не требуют вмешательства в файлы самого buildroot.
Использование EXTERNAL-механизма для кастомизации
В предыдущей статье рассматривался простой пример добавления своей конфигурации, путем добавления defconfig’а платы и нужных файлов непосредственно в каталог Buildroot.
Но этот метод не очень удобен, особенно при обновлении buildroot. Для решения это проблемы есть механизм external tree. Суть его в том, что в отдельном каталоге можно хранить каталоги board,configs,packages и прочие( например, я использую каталог patches для наложения патчей на пакеты, подробнее в отдельном разделе) и buildroot будет сам добавлять их к имеющимися в своем каталоге.
Примечение: можно накладывать сразу несколько external tree, есть пример в руководстве buildroot
Создадим каталог my_tree, находящийся рядом с каталогом buildroot’а и перенесём туда нашу конфигурацию. На выходе должны получить следующую структуру файлов:
[alexey@alexey-pc my_tree]$ tree
.
├── board
│ └── my_x86_board
│ ├── bef_cr_fs_img.sh
│ ├── linux.config
│ ├── rootfs_overlay
│ └── users.txt
├── Config.in
├── configs
│ └── my_x86_board_defconfig
├── external.desc
├── external.mk
├── package
└── patches
6 directories, 7 files
Как видно, в целом структура повторяет структуру buildroot.
Каталог board содержит файлы, специфичные каждой плате в нашем случае:
- bef_cr_fs_img.sh — скрипт, который будет выполняться после сборки target-файловой системы, но перед упаковыванием её в образы. В дальнейшем мы его будем использовать
- linux.config — конфигурация ядра
- rootfs_overlay — каталог для наложения поверх target-файловой системы
- users.txt — файл с описанием создаваемых пользователей
Каталог configs содержит defconfig’и наших плат. У нас он всего один.
Package — каталог с нашими пакетами. Изначально buildroot содержит описания и правила сборки ограниченного числа пакетов. Позже мы добавим сюда оконный менеджер icewm и менеджер графического входа в систему Slim.
Patches — позволяет удобно хранить свои патчи для разных пакетов. Подробнее в отдельном разделе далее.
Теперь нужно добавить файлы описания нашего external-tree. За это отвечают 3 файла: external.desc, Config.in, external.mk.
external.desc содержит собственно описание:
[alexey@alexey-pc my_tree]$ cat external.desc
name: my_tree
desc: My simple external-tree for article
Первая строка — название. В дальнейшем buildroot создать переменную $(BR2_EXTERNAL_MY_TREE_PATH), которую нужно использовать при конфигурировании сборки. Например, путь к файлу с пользователями можно задать следующим путем:
$(BR2_EXTERNAL_my_tree_PATH)/board/my_x86_board/users.txt
Вторая строка — краткое, понятное человеку описание.
Config.in, external.mk — файлы для описания добавляемых пакетов. Если свои пакеты не добавлять, то эти файлы можно оставить пустыми. Пока что мы так и поступим.
Теперь у нас готово наше external-tree, содержащее defconfig нашей платы и нужные ему файлы. Перейдем каталог buildroot, укажем использовать external-tree:
[alexey@alexey-pc buildroot]$ make BR2_EXTERNAL=../my_tree/ my_x86_board_defconfig
#
# configuration written to /home/alexey/dev/article/ramdisk/buildroot/.config
#
[alexey@alexey-pc buildroot]$ make menuconfig
В первой команде мы используем аргумент BR2_EXTERNAL=../my_tree/, указывающий использование external tree.Можно задать одновременно несколько external-tree для использования При этом достаточно сделать это один раз, после чего создается файл output/.br-external.mk, хранящий информацию об используемом external-tree:
[alexey@alexey-pc buildroot]$ cat output/.br-external.mk
#
# Automatically generated file; DO NOT EDIT.
#
BR2_EXTERNAL ?= /home/alexey/dev/article/ramdisk/my_small_linux/my_tree
BR2_EXTERNAL_NAMES =
BR2_EXTERNAL_DIRS =
BR2_EXTERNAL_MKS =
BR2_EXTERNAL_NAMES += my_tree
BR2_EXTERNAL_DIRS += /home/alexey/dev/article/ramdisk/my_small_linux/my_tree
BR2_EXTERNAL_MKS += /home/alexey/dev/article/ramdisk/my_small_linux/my_tree/external.mk
export BR2_EXTERNAL_my_tree_PATH = /home/alexey/dev/article/ramdisk/my_small_linux/my_tree
export BR2_EXTERNAL_my_tree_DESC = My simple external-tree for article
Важно! В этом файле пути будут абсолютными!
В меню появился пункт External options:
В этом подменю будут содержаться наши пакеты из нашего external-tree. Сейчас этот раздел пустой.
Сейчас нам важнее переписать нужные пути на использование external-tree.
Обратите внимание, что в разделе Build options → Location to save buildroot config, будет абсолютный путь к сохраняемому defconfig'у. Формируется он в момент указания импользования extgernal_tree.
Также в разделе System configuration поправим пути. Для таблицы с создаваемыми пользователями:
$(BR2_EXTERNAL_my_tree_PATH)/board/my_x86_board/users.txt
В разделе Kernel поменяем путь к конфигурации ядра:
$(BR2_EXTERNAL_my_tree_PATH)/board/my_x86_board/linux.config
Теперь при сборке будут использоваться наши файлы из нашего external-tree. При переносе в другой каталог, обновлении buildroot у нас будет минимум проблем.
Добавление root fs overlay:
Данный механизм позволяет легко добавлять/заменять файлы в target-файловой системе.
Если файл есть в root fs overlay, но нет в target, то он будет добавлен
Если файл есть в root fs overlay и в target, то он будет заменён.
Сначала зададим путь к root fs overlay dir. Это делается в разделе System configuration → Root filesystem overlay directories:
$(BR2_EXTERNAL_my_tree_PATH)/board/my_x86_board/rootfs_overlay/
Теперь проведем создадим два файла.
[alexey@alexey-pc my_small_linux]$ cat my_tree/board/my_x86_board/rootfs_overlay/etc/hosts
127.0.0.1 localhost
127.0.1.1 my_small_linux
8.8.8.8 google-public-dns-a.google.com.
[alexey@alexey-pc my_small_linux]$ cat my_tree/board/my_x86_board/rootfs_overlay/new_file.txt
This is new file from overlay
Первый файл (my_tree/board/my_x86_board/rootfs_overlay/etc/hosts) заменит файл /etc/hosts в готовой системе. Второй файл (cat my_tree/board/my_x86_board/rootfs_overlay/new_file.txt) добавится.
Собираем и проверяем:
Выполнение скриптов кастомизации на разных этапах сборки системы
Часто нужно выполнить некоторые действия внутри target-файловой системы до того, как как она будет упакована в образы.
Это можно сделать в разделе System configuration:
Первые два скрипта выполняются после сборки target-файловой системы, но до упаковки её в образы. Разница в том, что fakeroot-скрипт выполняется в контексте fakeroot, те имитируется работа от пользователя root.
Последний скрипт выполняется уже после создания образов системы. В нем можно выполнять дополнительные действия, например, скопировать нужные файлы на nfs-сервер или создать образ своей прошивки устройства.
В качестве примера я создам скрипт, который будет писать версию и дату сборки в /etc/.
Сначала укажу путь к этому файлу в моем external-tree:
А теперь сам скрипт:
[alexey@alexey-pc buildroot]$ cat ../my_tree/board/my_x86_board/bef_cr_fs_img.sh
#!/bin/sh
echo "my small linux 1.0 pre alpha" > output/target/etc/mysmalllinux-release
date >> output/target/etc/mysmalllinux-release
После сборки можно увидеть этот файл в системе.
На практике, скрипт может стать большим. Поэтому в реальном проекте я пошел более продвинутым путем:
- Создал каталог (my_tree/board_my_x86_board/inside_fakeroot_scripts), в котором лежат скрипты для выполнения, с порядковыми номерами. Например, 0001-add-my_small_linux-version.sh, 0002-clear-apache-root-dir.sh
- Написал скрипт(my_tree/board_my_x86_board/run_inside_fakeroot.sh), который проходит по этому каталогу и последовательно выполняет скрипты, лежашие в нем
- Указал этот скрипт в настройках платы в разеле System configuration -> Custom scripts to run inside the fakeroot environment ($(BR2_EXTERNAL_my_tree_PATH)/board/my_x86_board/run_inside_fakeroot.sh)
Автор: Boozlachu