如何在继承 core-image class 的同时将包含子目录的整个目录复制到 Yocto 中的 /boot(即 bootfs)?

How to copy whole directories containing subdirectories to /boot (i.e bootfs) in Yocto while inheriting core-image class?

我有一个目录,它再次包含子目录,这些子目录是用其他配方的一部分构建的,并使用 deploy bb class 移动到 DEPLOY_DIR_IMAGE。所以现在我想把它复制到主映像启动分区。

如果它是单个文件,则将所需的文件名附加到 IMAGE_EFI_BOOT_FILES 变量,然后 yocto 将其复制到 /boot。但同样不适用于包含子目录的目录,请提供样式以包含子目录。谢谢

PS:我试过附加 IMAGE_EFI_BOOT_FILES += “parent_dir/*” 没用。

很明显,IMAGE_EFI_BOOT_FILES 的作用类似于众所周知的 IMAGE_BOOT_FILES 和其他变量,这些变量负责将必要的文件传送到引导分区中。这需要文件而不是目录。

因此,如果您不需要手动指定所有文件,而是想传递目录,我建议您使用 python 方法为您收集文件并将它们附加到变量。

看下面我开发测试的例子:

def get_files(d, dir):
    import os
    dir_path = dir
    if not os.path.exists(os.path.dirname(dir)):
        dir_path = d.getVar(dir)
    return ' '.join(f for f in os.listdir(d.getVar(dir)) if os.path.isfile(f))

IMAGE_EFI_BOOT_FILES += "${@get_files(d, 'DEPLOY_DIR_IMAGE')}"

该方法将测试参数是否为真实路径,然后它将直接检查文件,如果不是,它将假定它是一个 bitbake 变量并获取其内容,因此如果 DEPLOY_DIR_IMAGE 是,例如 /home/user/dir,传递 DEPLOY_DIR_IMAGE/home/usr/dir 将得到相同的结果。

重要

很明显,IMAGE_EFI_BOOT_FILES 用于 .conf 文件,例如 local.conf 或自定义机器配置文件。所以在 .conf 文件中添加 python 函数将不起作用。我建议为它创建一个 class 并在你的 .conf 文件中全局继承它:

  • meta-custom/classes/utils.bbclass

  • local.conf:

INHERIT += "utils"
IMAGE_EFI_BOOT_FILES += "${@get_files(d, 'DEPLOY_DIR_IMAGE')}"

试试这个并在评论中告诉我。

编辑

我刚刚意识到 bitbake 已经在 python 表达式扩展中导入了 os,因此您可以在一行中完成它而无需单独的 python 函数:

PATH = "/path/to/directory/"  or
PATH = "A variable containing the path"
IMAGE_EFI_BOOT_FILES += "${@' '.join('%s' % f for f in os.listdir('${PATH}') if os.path.isfile(f))}"

注意:我正在寻找可以实现上述解决方案的 Yocto built-in,希望分享其他解决功能的方法以造福于社区。

如果您正在使用,请在 bb 文件中添加以下内容或参考 talel-belhadjsalem 答案以使用 utils.bbclass。

def add_directory_bootfs(d, dirname, bootfs_dir):
    file_list = list()
    boot_files_list = list()
    deploy_dir_image = d.getVar('DEPLOY_DIR_IMAGE')
    for (dirpath, dirnames, filenames) in os.walk(os.path.join(deploy_dir_image, dirname)):
        file_list += [os.path.join(dirpath, file) for file in filenames]
    for file in file_list:
        file_rel_path = os.path.relpath(file, os.path.join(deploy_dir_image, dirname))
        boot_file_entry = os.path.join(dirname, file_rel_path) + ';' + os.path.join(bootfs_dir, dirname, file_rel_path)
        boot_files_list.append(boot_file_entry)
    return ' '.join(boot_files_list)

IMAGE_EFI_BOOT_FILES += "${@add_directory_bootfs(d, 'relative_path_to_dir_in_deploy_dir_image', 'EFI/BOOT')}"