У цьому розділі я розглядаю частину можливостей кастомізації, які знадобилися мені. Це не повний список того, що пропонує buildroot, але вони цілком робочі і не вимагають втручання у файли самого buildroot.
Використання EXTERNAL-механізму для кастомізації
Але цей метод не дуже зручний, особливо при оновленні будівельногодроту. Для вирішення цієї проблеми є механізм 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
Як видно, загалом структура повторює структуру збудуваннядроту.
Каталог рада містить файли, специфічні для кожної плати в нашому випадку:
- bef_cr_fs_img.sh — скрипт, який виконуватиметься після складання target-файлової системи, але перед пакуванням її в образи. Надалі ми його використовуватимемо
- linux.config - конфігурація ядра
- rootfs_overlay — каталог для накладання поверх target-файлової системи
- users.txt — файл із описом створюваних користувачів
Каталог конфігурації містить defconfig'і наших плат. У нас він лише один.
пакет — каталог із нашими пакетами. Спочатку buildroot містить описи та правила складання обмеженої кількості пакетів. Пізніше ми додамо сюди віконний менеджер icewm та менеджер графічного входу в систему Slim.
Патчі дозволяє зручно зберігати свої патчі для різних пакетів. Докладніше в окремому розділі далі.
Тепер потрібно додати файли опису нашого 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)
Джерело: habr.com