- Вопрос или проблема
- Ответ или решение
- Проблема с автоматическим включением служб systemd в Yocto: подробное руководство по решению
- Описание проблемы
- Структура вашего проекта
- Возможные причины проблемы
- 1. Ошибки в декларациях сервисов
- 2. Недостаток параметров в .service файлах
- 3. Автоматическая активация по умолчанию
- 4. Повторное использование переменных
- Что попробовать
- Заключение
Вопрос или проблема
Я использую версию 2.2 (morty) Yocto, и у меня возникли трудности с тем, чтобы несколько моих сервисов запускались при загрузке. Вот моя текущая настройка:
-
Я не хочу, чтобы все сервисы были включены по умолчанию, поэтому я установил
SYSTEMD_AUTO_ENABLE ?= disable
. -
Я установил затрагиваемые сервисы в
${D}${systemd_unitdir}/system/
. Я подтвердил, что сервисы присутствуют при загрузке, но они не включены. -
В моем рецепте, где я устанавливаю конкретный сервис, у меня также есть строка
SYSTEMD_SERVICE_${PN}_<имя_машины> = "<имя_сервиса>.service <другой-сервис>.service"
. У меня есть несколько различных машин, для которых я компилирую, и каждая машина требует разный сервис, поэтому для каждой машины есть строка, как выше, с соответствующим именем сервиса. -
У меня есть другой рецепт, который добавляет другие не связанные сервисы, у которых такая же настройка (установка в то же место, добавление сервиса в
SYSTEMD_SERVICE_${PN}_<имя_машины>
таким же образом). Эти сервисы включаются по ожиданию при первой загрузке.
Я приложил упрощенную версию обоих рецептов ниже. Любая помощь была бы очень appreciated, я в затруднении.
Рецепт, у которого сервисы включены при загрузке:
SRC_URI_machine1 += "file://machine1/etc/udev/rules.d/99-local.rules \
file://machine1/lib/systemd/system/button-off.service \
file://machine1/lib/systemd/system/machine1-startup.service \
file://machine1/etc/machine1/startup \
file://machine1/usr/bin/button_press_off.sh \
file://machine1/usr/bin/execstop.sh \
"
SRC_URI_machine2 += "file://machine2/etc/udev/rules.d/99-local.rules \
file://machine2/lib/systemd/system/button-off.service \
file://machine2/lib/systemd/system/machine2-startup.service \
file://machine2/etc/machine2/startup \
file://machine2/usr/bin/button_press_off.sh \
file://machine2/usr/bin/execstop.sh \
"
FILES_${PN} += "${bindir} ${sysconfdir} ${systemd_unitdir}/system ${base_libdir}"
SYSTEMD_SERVICE_${PN}_machine1 = "
button-off.service \
machine1-startup.service \
"
SYSTEMD_SERVICE_${PN}_machine2 = "
button-off.service \
machine2-startup.service \
"
inherit systemd autotools
do_compile() {
}
do_install_prepend() {
install -d -m 0755 ${D}${systemd_unitdir}/system/
install -d -m 0755 ${D}${sysconfdir}/${MACHINE}/
install -d -m 0755 ${D}${sysconfdir}/udev/rules.d/
install -d -m 0755 ${D}${sysconfdir}/sysctl.d/
install -d -m 0755 ${D}${bindir}/
ln -s /usr/bin/arm-poky-linux-gnueabi-gcc ${D}${bindir}/arm-linux-gnueabihf-gcc
}
do_install_machine1() {
install -m 0755 -D ${WORKDIR}/machine1/usr/bin/*.sh ${D}${bindir}
install -m 0644 -D ${WORKDIR}/machine1/lib/systemd/system/*.service ${D}${systemd_unitdir}/system/
install -m 0744 -D ${WORKDIR}/machine1/etc/machine1/startup ${D}${sysconfdir}/machine1/
install -m 0644 -D ${WORKDIR}/machine1/etc/udev/rules.d/* ${D}${sysconfdir}/udev/rules.d/
}
do_install_machine2() {
install -m 0755 -D ${WORKDIR}/machine2/usr/bin/*.sh ${D}${bindir}
install -m 0644 -D ${WORKDIR}/machine2/lib/systemd/system/*.service ${D}${systemd_unitdir}/system/
install -m 0744 -D ${WORKDIR}/machine2/etc/machine2/startup ${D}${sysconfdir}/machine2/
install -m 0644 -D ${WORKDIR}/machine2/etc/udev/rules.d/* ${D}${sysconfdir}/udev/rules.d/
}
Рецепт, у которого сервисы отключены при загрузке:
SRC_URI_machine1 = "
file://service1.service \
file://machine1-service2.service \
"
SRC_URI_machine2 = "
file://service1.service \
file://machine2-service2.service \
"
S = "${WORKDIR}/git"
inherit systemd
inherit autotools
INSANE_SKIP_${PN} = "ldflags"
FILES_${PN} += "${bindir} ${systemd_unitdir}/system ${D}${prefix}/src/debug/${PN}/${PV}-${PR}/git "
SYSTEMD_SERVICE_${PN}_machine1 = "machine1-service2.service service1.service"
SYSTEMD_SERVICE_${PN}_machine2 = "machine2-service2.service service1.service"
do_install_machine1() {
install -d -m 0755 ${D}${systemd_unitdir}/system/
install -m 0644 -D ${WORKDIR}/machine1-service2.service ${D}${systemd_unitdir}/system/
install -m 0644 -D ${WORKDIR}/service1.service ${D}${systemd_unitdir}/system/
}
do_install_machine2() {
install -d -m 0755 ${D}${systemd_unitdir}/system/
install -m 0644 -D ${WORKDIR}/machine2-service2.service ${D}${systemd_unitdir}/system/
install -m 0644 -D ${WORKDIR}/service1.service ${D}${systemd_unitdir}/system/
}
Вы решили эту проблему? У меня такая же проблема.
Ответ или решение
Проблема с автоматическим включением служб systemd в Yocto: подробное руководство по решению
Описание проблемы
Вы используете версию 2.2 (Morty) Yocto и сталкиваетесь с проблемами, связанными с автоматическим включением ваших сервисов при загрузке. Некоторые из ваших сервисов не включаются при старте системы, несмотря на то, что они установлены в соответствующей директории и доступны. В то же время, другие сервисы с аналогичной конфигурацией работают корректно.
Структура вашего проекта
Вы задали следующие параметры в вашем проекте:
-
Отключение автоматического включения всех сервисов:
SYSTEMD_AUTO_ENABLE ?= disable
-
Установка сервисов в директорию:
Все ваши сервисы были установлены в${D}${systemd_unitdir}/system/
, что подтвердили при загрузке системы, видя, что они присутствуют. -
Объявление служб для разных машин:
Вы используете переменныеSYSTEMD_SERVICE_${PN}_<machine_name>
, где для каждой машины указаны соответствующие службы. -
Код для рецептов:
Были представлены два рецепта, один из которых содержит рабочие сервисы, а другой — неработающие.
Возможные причины проблемы
1. Ошибки в декларациях сервисов
Убедитесь, что файловая структура и пути к вашим .service
файлам корректны. Проверьте, что все зависимости, указанные в .service
файлах, доступны и правильно определены.
2. Недостаток параметров в .service
файлах
Проверьте содержимое ваших .service
файлов. Они должны содержать необходимые параметры для работы, такие как After
, Wants
и WantedBy
. Пример:
[Unit]
Description=My Service
After=network.target
[Service]
ExecStart=/path/to/executable
[Install]
WantedBy=multi-user.target
3. Автоматическая активация по умолчанию
Несмотря на то, что вы указываете отключение по умолчанию (SYSTEMD_AUTO_ENABLE ?= disable
), если вы хотите включить конкретные службы, необходимо добавить следующее в ваши рецепты:
systemd_set_service_inactive = "false"
Это заставит Yocto активировать указанные группы служб даже при выключении автоматического включения.
4. Повторное использование переменных
Проблема может быть связана с многократным использованием переменной SYSTEMD_SERVICE
для разных машин. Убедитесь, что вы не переопределяете переменные, и они правильно сопоставляются с вашей целевой машиной.
Что попробовать
-
Проверьте логи systemd. Используйте команду
systemctl status <service_name>
иjournalctl -xe
для диагностики проблем с вашим сервисом. -
Создайте переопределяющую конфигурацию. Попробуйте создать
.service
файл для переопределения, который будет всегда активировать требуемые службы. -
Полная перезагрузка: Иногда требуется выполнить
bitbake -c clean <recipe>
и затемbitbake <recipe>
, чтобы убедиться, что все изменения применены корректно. -
Информация о зависимости: Убедитесь, что ваши сервисы не зависят от других, которые могут не быть активированы, в результате чего ваши сервисы не запускаются.
-
Включение вручную: Попробуйте вручную активировать службы с помощью команды:
systemctl enable <service_name>
Заключение
Ошибки в автоматическом включении служб systemd в Yocto могут быть вызваны множеством факторов, от неправильной конфигурации до ошибок в зависимости. Следуя представленному выше плану, вы сможете лучше разобраться в вашей проблеме и, возможно, найти решение. Убедитесь, что вы проверяете логи, структурируете ваши .service
файлы правильно и используете корректные переменные для управления состоянием служб.