From aed413df1ee31aad6f67eca405ed01d82d628fc7 Mon Sep 17 00:00:00 2001 From: Gatis Paeglis Date: Tue, 10 Nov 2015 14:52:38 +0100 Subject: ostree: patch upstream project - This allows updating files on the boot partition. - Merges ostree's uEnv.txt with system's uEnv.txt - Adds support for convenience symlinks in top level of the /boot directory. This does not affect the atomic property of an update. Change-Id: Ie654e22d6e26aaa0c1395d226ed967765b0c764b Reviewed-by: Samuli Piippo --- recipes/ostree/ostree.bb | 8 +- ...llow-updating-files-on-the-boot-partition.patch | 92 ++++++++++++++++++ ...-require-boot-uEnv.txt-for-u-boot-support.patch | 62 ------------ ...-boot-Merge-ostree-s-and-systems-uEnv.txt.patch | 99 ++++++++++++++++++++ ...0003-Allow-updating-files-in-root-of-boot.patch | 104 +++++++++++++++++++++ 5 files changed, 301 insertions(+), 64 deletions(-) create mode 100644 recipes/ostree/ostree/0001-Allow-updating-files-on-the-boot-partition.patch delete mode 100644 recipes/ostree/ostree/0001-Don-t-require-boot-uEnv.txt-for-u-boot-support.patch create mode 100644 recipes/ostree/ostree/0002-u-boot-Merge-ostree-s-and-systems-uEnv.txt.patch create mode 100644 recipes/ostree/ostree/0003-Allow-updating-files-in-root-of-boot.patch diff --git a/recipes/ostree/ostree.bb b/recipes/ostree/ostree.bb index ab17671..c4a6f69 100644 --- a/recipes/ostree/ostree.bb +++ b/recipes/ostree/ostree.bb @@ -28,10 +28,14 @@ LIC_FILES_CHKSUM = "file://COPYING;md5=5f30f0716dfdd0d91eb439ebec522ec2" inherit autotools pkgconfig SRC_URI = " \ - git://github.com/GNOME/ostree.git;tag=v2015.9 \ - file://0001-Don-t-require-boot-uEnv.txt-for-u-boot-support.patch \ + git://github.com/GNOME/ostree.git \ + file://0001-Allow-updating-files-on-the-boot-partition.patch \ + file://0002-u-boot-Merge-ostree-s-and-systems-uEnv.txt.patch \ + file://0003-Allow-updating-files-in-root-of-boot.patch \ " +SRCREV = "efdb4d8f443768e59529c299290bee8b1f8f93c3" + S = "${WORKDIR}/git" DEPENDS = "glib-2.0 e2fsprogs gpgme attr libsoup-2.4 libgsystem libassuan xz" diff --git a/recipes/ostree/ostree/0001-Allow-updating-files-on-the-boot-partition.patch b/recipes/ostree/ostree/0001-Allow-updating-files-on-the-boot-partition.patch new file mode 100644 index 0000000..0905cc1 --- /dev/null +++ b/recipes/ostree/ostree/0001-Allow-updating-files-on-the-boot-partition.patch @@ -0,0 +1,92 @@ +From bbb7a8ce89e3e13672c63fd4f1f19988fdf40014 Mon Sep 17 00:00:00 2001 +From: Gatis Paeglis +Date: Thu, 5 Nov 2015 17:37:54 +0100 +Subject: [PATCH 1/2] Allow updating files on the boot partition + +Until now OSTree copied only vmlinuz and initramfs +binaries to the boot partition. This patch adds support +for copying other files from the /boot directory of the +tree. + +How this works: + +Ignore subdirectories, only files in root of the boot +directory are copied. There is overhead of copying files +to boot partition, therefore the amount of files in the +boot/ should be kept to the minimum and subdirectories +shouldn't really be necessary. + +Files on the boot partition are updated only with major +releases, when kernel/initramfs bootcsum changes. Files +that require frequent updates should not be stored here. +--- + src/libostree/ostree-sysroot-deploy.c | 53 +++++++++++++++++++++++++++++++++++ + 1 file changed, 53 insertions(+) + +diff --git a/src/libostree/ostree-sysroot-deploy.c b/src/libostree/ostree-sysroot-deploy.c +index f7afe3d..4d6534d 100644 +--- a/src/libostree/ostree-sysroot-deploy.c ++++ b/src/libostree/ostree-sysroot-deploy.c +@@ -1340,6 +1340,59 @@ install_deployment_kernel (OstreeSysroot *sysroot, + } + } + ++ { ++ /* Copy other files that are stored in the boot directory. Lets keep this simple: ++ * ++ * - Ignore subdirectories, only files in root of the boot directory are copied. There is ++ * overhead of copying files to boot partition, therefore the amount of files in the boot/ ++ * should be kept to the minimum and subdirectories shouldn't really be necessary. ++ * - Files on the boot partition are updated only with major releases, when kernel/initramfs ++ * bootcsum changes. Files that require frequent updates should not be stored here. ++ */ ++ g_autoptr(GFileEnumerator) dir_enum = NULL; ++ g_autoptr(GFile) deployments_bootdir = g_file_get_child (deployment_dir, "boot"); ++ dir_enum = g_file_enumerate_children (deployments_bootdir, OSTREE_GIO_FAST_QUERYINFO, ++ G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, ++ NULL, error); ++ while (TRUE) ++ { ++ GFileInfo *file_info = NULL; ++ g_autoptr(GFile) source_file = NULL; ++ g_autoptr(GFile) dest_file = NULL; ++ g_autoptr(GFile) symlink_target = NULL; ++ GFileType type; ++ const char *name; ++ ++ if (!gs_file_enumerator_iterate (dir_enum, &file_info, NULL, cancellable, error)) ++ goto out; ++ if (file_info == NULL) ++ break; ++ ++ type = g_file_info_get_file_type (file_info); ++ name = g_file_info_get_name (file_info); ++ if (type == G_FILE_TYPE_DIRECTORY) ++ continue; ++ if (type == G_FILE_TYPE_SYMBOLIC_LINK) ++ { ++ symlink_target = g_file_get_child (bootcsumdir, g_file_info_get_symlink_target(file_info)); ++ if (!g_file_query_exists (symlink_target, NULL)) ++ continue; ++ } ++ if (g_str_has_prefix (name, "vmlinuz-") || g_str_has_prefix (name, "initramfs-")) ++ continue; ++ ++ dest_file = g_file_get_child (bootcsumdir, name); ++ if (!g_file_query_exists (dest_file, NULL)) ++ { ++ source_file = g_file_enumerator_get_child (dir_enum, file_info); ++ if (!gs_file_linkcopy_sync_data (source_file, dest_file, ++ G_FILE_COPY_OVERWRITE | G_FILE_COPY_NOFOLLOW_SYMLINKS | G_FILE_COPY_ALL_METADATA, ++ cancellable, error)) ++ goto out; ++ } ++ } ++ } ++ + if (fstatat (deployment_dfd, "usr/lib/os-release", &stbuf, 0) != 0) + { + if (errno != ENOENT) +-- +2.1.4 + diff --git a/recipes/ostree/ostree/0001-Don-t-require-boot-uEnv.txt-for-u-boot-support.patch b/recipes/ostree/ostree/0001-Don-t-require-boot-uEnv.txt-for-u-boot-support.patch deleted file mode 100644 index 8e1be94..0000000 --- a/recipes/ostree/ostree/0001-Don-t-require-boot-uEnv.txt-for-u-boot-support.patch +++ /dev/null @@ -1,62 +0,0 @@ -From ca0a0261be6397d5acb7a4fa2a492c5b554fb1fe Mon Sep 17 00:00:00 2001 -From: Gatis Paeglis -Date: Tue, 6 Oct 2015 23:43:25 +0200 -Subject: [PATCH] Don't require /boot/uEnv.txt for u-boot support - -The current code checks if /boot/uEnv.txt is a symlink to -decice if sysroot requires u-boot support. Why this is bad: - -There are 2 ways to provide a custom env to u-boot from user space: - -1) A compiled binary that is sourced from u-boot. -2) A text file (usually /uEnv.txt) that is imported into env from u-boot. - -The current OSTree u-boot integration code was designed with the 1st -case in mind. - -Many bootscripts provided by an embedded device vendors expect -to find uEnv.txt in the top level directory, it is often hardcoded -when building u-boot and is difficult to change later on. Or in other -cases it is stored in read-only memory so changing it would require -re-flushing boot loader with a new env. So the issue here is that -OSTree's and vendor uEnv.txt want to exist on the same path and OSTree -would throw away any changes added to /uEnv.txt by user on the next -upgrade/deploy. - -This patch "hides" away the OSTree's env file loader/uEnv.txt from users -who are used to edditing uEnv.txt at the top level directory. Now to add -OSTree support on such boards you can simply add a custom logic in uEnv.txt -that loads ostree env from /loader/uEnv.txt - -This change is backward compatible with the previous ostree releases and -solves the issue described in: - -https://bugzilla.gnome.org/show_bug.cgi?id=755787 ---- - src/libostree/ostree-bootloader-uboot.c | 4 ++-- - 1 file changed, 2 insertions(+), 2 deletions(-) - -diff --git a/src/libostree/ostree-bootloader-uboot.c b/src/libostree/ostree-bootloader-uboot.c -index 4c0218f..f67e9bd 100644 ---- a/src/libostree/ostree-bootloader-uboot.c -+++ b/src/libostree/ostree-bootloader-uboot.c -@@ -52,7 +52,7 @@ _ostree_bootloader_uboot_query (OstreeBootloader *bootloader, - { - OstreeBootloaderUboot *self = OSTREE_BOOTLOADER_UBOOT (bootloader); - -- *out_is_active = g_file_query_file_type (self->config_path, G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL) == G_FILE_TYPE_SYMBOLIC_LINK; -+ *out_is_active = g_file_query_file_type (self->config_path, G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL) == G_FILE_TYPE_REGULAR; - return TRUE; - } - -@@ -177,6 +177,6 @@ _ostree_bootloader_uboot_new (OstreeSysroot *sysroot) - { - OstreeBootloaderUboot *self = g_object_new (OSTREE_TYPE_BOOTLOADER_UBOOT, NULL); - self->sysroot = g_object_ref (sysroot); -- self->config_path = g_file_resolve_relative_path (self->sysroot->path, "boot/uEnv.txt"); -+ self->config_path = g_file_resolve_relative_path (self->sysroot->path, "boot/loader/uEnv.txt"); - return self; - } --- -2.1.4 - diff --git a/recipes/ostree/ostree/0002-u-boot-Merge-ostree-s-and-systems-uEnv.txt.patch b/recipes/ostree/ostree/0002-u-boot-Merge-ostree-s-and-systems-uEnv.txt.patch new file mode 100644 index 0000000..08855de --- /dev/null +++ b/recipes/ostree/ostree/0002-u-boot-Merge-ostree-s-and-systems-uEnv.txt.patch @@ -0,0 +1,99 @@ +From 5ee49772b001b9757d6cb21fcc587d5ddc66cdb7 Mon Sep 17 00:00:00 2001 +From: Gatis Paeglis +Date: Thu, 5 Nov 2015 17:39:16 +0100 +Subject: [PATCH 2/2] u-boot: Merge ostree's and systems uEnv.txt + +This allows for simpler u-boot scripts and is +a proper fix for: + +https://bugzilla.gnome.org/show_bug.cgi?id=755787 +--- + src/libostree/ostree-bootloader-uboot.c | 42 ++++++++++++++++++++++++++++++--- + 1 file changed, 39 insertions(+), 3 deletions(-) + +diff --git a/src/libostree/ostree-bootloader-uboot.c b/src/libostree/ostree-bootloader-uboot.c +index f67e9bd..be1a40d 100644 +--- a/src/libostree/ostree-bootloader-uboot.c ++++ b/src/libostree/ostree-bootloader-uboot.c +@@ -29,6 +29,10 @@ + #include "otutil.h" + + #include ++#include ++#include ++#include ++#include + + struct _OstreeBootloaderUboot + { +@@ -69,13 +73,17 @@ create_config_from_boot_loader_entries (OstreeBootloaderUboot *self, + GCancellable *cancellable, + GError **error) + { ++ gboolean ret = FALSE; + g_autoptr(GPtrArray) boot_loader_configs = NULL; + OstreeBootconfigParser *config; + const char *val; ++ g_autofree char *boot_path = NULL; ++ g_autoptr(GFile) uenv_file = NULL; ++ char uenv_path[2048]; + + if (!_ostree_sysroot_read_boot_loader_configs (self->sysroot, bootversion, &boot_loader_configs, + cancellable, error)) +- return FALSE; ++ goto out; + + /* U-Boot doesn't support a menu so just pick the first one since the list is ordered */ + config = boot_loader_configs->pdata[0]; +@@ -85,10 +93,13 @@ create_config_from_boot_loader_entries (OstreeBootloaderUboot *self, + { + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, + "No \"linux\" key in bootloader config"); +- return FALSE; ++ goto out; + } + g_ptr_array_add (new_lines, g_strdup_printf ("kernel_image=%s", val)); + ++ boot_path = strndup (val, strlen (val) - strlen ("/vmlinuz")); ++ g_ptr_array_add (new_lines, g_strdup_printf ("bootdir=%s", boot_path)); ++ + val = ostree_bootconfig_parser_get (config, "initrd"); + if (val) + g_ptr_array_add (new_lines, g_strdup_printf ("ramdisk_image=%s", val)); +@@ -97,7 +108,32 @@ create_config_from_boot_loader_entries (OstreeBootloaderUboot *self, + if (val) + g_ptr_array_add (new_lines, g_strdup_printf ("bootargs=%s", val)); + +- return TRUE; ++ /* Merge with user's uEnv.txt if it exists */ ++ snprintf (uenv_path, sizeof(uenv_path), "boot/%s/uEnv.txt", boot_path); ++ uenv_file = g_file_get_child (self->sysroot->path, uenv_path); ++ if (g_file_query_exists (uenv_file, cancellable)) ++ { ++ g_autoptr(GInputStream) instream = NULL; ++ g_autoptr(GDataInputStream) datastream = NULL; ++ gsize len; ++ ++ instream = (GInputStream*)g_file_read (uenv_file, cancellable, error); ++ if (!instream) ++ goto out; ++ ++ datastream = g_data_input_stream_new (instream); ++ while (TRUE) ++ { ++ val = g_data_input_stream_read_line (datastream, &len, cancellable, error); ++ if (!val) ++ break; ++ g_ptr_array_add (new_lines, (char *)val); ++ } ++ } ++ ++ ret = TRUE; ++out: ++ return ret; + } + + static gboolean +-- +2.1.4 + diff --git a/recipes/ostree/ostree/0003-Allow-updating-files-in-root-of-boot.patch b/recipes/ostree/ostree/0003-Allow-updating-files-in-root-of-boot.patch new file mode 100644 index 0000000..d93da22 --- /dev/null +++ b/recipes/ostree/ostree/0003-Allow-updating-files-in-root-of-boot.patch @@ -0,0 +1,104 @@ +From f5a1391e64d4b17ed05fb47f23d5d35affb9f1fd Mon Sep 17 00:00:00 2001 +From: Gatis Paeglis +Date: Thu, 5 Nov 2015 14:58:56 +0100 +Subject: [PATCH] Allow updating files in root of /boot + +It is common for u-boot based systems to search +top level directory of the boot partiton for +additional files that are required for booting. +It can be difficult to change this search logic +if it is hardcoded somewhere low in the stack or +in u-boot env that is in read-only memory. To +allow updating these files you need to add a +symlink in your ostree sysroot: + +cd sysroot/boot +ln -s loader/my-special-file my-special-file + +The bellow code will make sure that loader/my-special-file +points to the correct target file version. + +This does not break the atomic property of update. +--- + src/libostree/ostree-bootloader-uboot.c | 65 +++++++++++++++++++++++++++++++++ + 1 file changed, 65 insertions(+) + +diff --git a/src/libostree/ostree-bootloader-uboot.c b/src/libostree/ostree-bootloader-uboot.c +index be1a40d..779c302 100644 +--- a/src/libostree/ostree-bootloader-uboot.c ++++ b/src/libostree/ostree-bootloader-uboot.c +@@ -131,6 +131,71 @@ create_config_from_boot_loader_entries (OstreeBootloaderUboot *self, + } + } + ++ { ++ /* It is common for u-boot based systems to search top level directory of the boot ++ * partiton for additional files that are required for booting. It can be difficult ++ * to change this search logic if it is hardcoded somewhere low in the stack or in ++ * u-boot env that is in read-only memory. To allow updating these files you need to ++ * add a symlink in your ostree sysroot: ++ * ++ * cd sysroot/boot ++ * ln -s loader/my-special-file my-special-file ++ * ++ * The bellow code will make sure that loader/my-special-file points to the correct ++ * target file version. ++ * ++ */ ++ g_autoptr(GFile) child = NULL; ++ int loader_fd; ++ g_autoptr(GFileEnumerator) dir_enum = NULL; ++ g_autoptr(GFile) real_boot = NULL; ++ g_autofree char *loader_path = NULL; ++ char buf[2048]; ++ ++ child = ot_gfile_resolve_path_printf (self->sysroot->path, "boot/loader.%d/", bootversion); ++ loader_path = g_file_get_path(child); ++ loader_fd = open (loader_path, O_RDONLY); ++ if (loader_fd == -1) { ++ perror("open"); ++ goto out; ++ } ++ ++ child = g_file_get_child (self->sysroot->path, "boot"); ++ dir_enum = g_file_enumerate_children (child, OSTREE_GIO_FAST_QUERYINFO, ++ G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, ++ NULL, error); ++ ++ while (TRUE) { ++ const char *symlink_target, *name; ++ GFileInfo *file_info = NULL; ++ ++ if (!gs_file_enumerator_iterate (dir_enum, &file_info, NULL, cancellable, error)) { ++ close(loader_fd); ++ goto out; ++ } ++ ++ if (file_info == NULL) ++ break; ++ ++ if (g_file_info_get_is_symlink(file_info)) { ++ symlink_target = g_file_info_get_symlink_target(file_info); ++ if (g_str_has_prefix(symlink_target, "loader/")) { ++ name = g_file_info_get_name(file_info); ++ if (g_strcmp0 (name, "uEnv.txt") == 0) ++ continue; ++ ++ snprintf(buf, sizeof(buf), "%s/%s", loader_path, name); ++ remove(buf); ++ snprintf(buf, sizeof(buf), "..%s/%s", boot_path, name); ++ if (symlinkat(buf, loader_fd, name) == -1) ++ perror("symlinkat"); ++ } ++ } ++ } ++ ++ close(loader_fd); ++ } ++ + ret = TRUE; + out: + return ret; +-- +2.1.4 + -- cgit v1.2.3-54-g00ecf