在Yocto构建的linux上安装后脚本

Igo*_*gor 3 openembedded angstrom-linux yocto imx6

我需要在Yocto构建的目标操作系统上运行脚本.

此脚本需要作为安装的一部分运行,因此必须只运行一次(在整个OS安装之后或首次启动时).它不能在主机系统上运行,因为它取决于仅存在于目标上的硬件IO.

另一个小的约束是rootfs是以只读方式挂载的,但我想这可以通过将脚本重新挂载为rw并在执行后再次重新安装为r或沿着这些行的某些内容来避免.

任何帮助表示赞赏.

Igo*_*gor 11

我最终做了shibley写的.这是一个详细的方法:

创建一个新图层

将所需的图层放在其他图层的任何位置.我的stuff目录位于构建目录旁边.

制作以下文件/目录:

meta_mylayer
??? conf
?   ??? layer.conf
??? recipes-core
    ??? mylayer-initscript
        ??? initscript.bb
        ??? files
            ??? initscript.service
            ??? initscript.sh
Run Code Online (Sandbox Code Playgroud)

meta_mylayer 是新图层的名称.

让我们定义图层conf/layer.conf并告诉它在哪里搜索食谱:

BBPATH .= ":${LAYERDIR}"
BBFILES += "${LAYERDIR}/recipes-*/*/*.bb ${LAYERDIR}/recipes-*/*/*.bbappend"
BBFILE_COLLECTIONS += "meta-mylayer"
BBFILE_PATTERN_meta-mylayer := "^${LAYERDIR}/"
BBFILE_PRIORITY_meta-mylayer = "99"
Run Code Online (Sandbox Code Playgroud)

配方由.bb文件的名称定义.该图层只有一个名为initscript的配方.

initscript.bb包含配方信息.以下配方将添加我们的initscript服务并将实际的安装脚本initscript.sh放入/usr/sbin/

SUMMARY = "Initial boot script"
DESCRIPTION = "Script to do any first boot init, started as a systemd service which removes itself once finished"
LICENSE = "CLOSED"
PR = "r3"

SRC_URI =  " \
    file://initscript.sh \
    file://initscript.service \
"

do_compile () {
}

do_install () {
    install -d ${D}/${sbindir}
    install -m 0755 ${WORKDIR}/initscript.sh ${D}/${sbindir}

    install -d ${D}${systemd_unitdir}/system/
    install -m 0644 ${WORKDIR}/initscript.service ${D}${systemd_unitdir}/system
}

NATIVE_SYSTEMD_SUPPORT = "1"
SYSTEMD_PACKAGES = "${PN}"
SYSTEMD_SERVICE_${PN} = "initscript.service"

inherit allarch systemd
Run Code Online (Sandbox Code Playgroud)

install -d将创建指定路径所需的任何目录,同时install -m 0644将复制具有644权限的指定文件.${D}是目标目录,默认情况下是${WORKDIR}/image

创建systemd服务定义

我不会详细介绍systemd的工作原理,而是粘贴服务定义:

[Unit]
Description=start initscript upon first boot

[Service]
Type=simple
ExecStart=/bin/sh -c 'sleep 5 ; /usr/sbin/initscript.sh'
Run Code Online (Sandbox Code Playgroud)

请注意脚本位置/usr/sbin/- 它将被do_install上面函数的最后一行复制.

最后,我们的initscript.sh脚本本身:

#!/bin/sh

logger "starting initscript"

# do some work here. Mount rootfs as rw if needed.

logger "initscript work done"

#job done, remove it from systemd services
systemctl disable initscript.service

logger "initscript disabled"
Run Code Online (Sandbox Code Playgroud)

注册图层

我们需要注册我们的新图层,以便bitbake知道它在那里.编辑build/conf/bblayers.conf文件并将以下行添加到BASELAYERS变量中:

  ${TOPDIR}/../stuff/meta-mylayer \
Run Code Online (Sandbox Code Playgroud)

现在bitbake识别我们的图层,我们需要将我们的配方添加到图像中.编辑build/conf/local.conf并将initscript配方添加到IMAGE_INSTALL_append变量中.这是在python旁边添加时的样子.

IMAGE_INSTALL_append = " python initscript"
Run Code Online (Sandbox Code Playgroud)

运行构建

像往常一样运行构建.例如:

bitbake angstrom-lxde-image
Run Code Online (Sandbox Code Playgroud)

在您第一次安装构建和引导后,您initscript.sh将被执行.