Merge ~xypron/grub:efivarfs into ~ubuntu-core-dev/grub/+git/ubuntu:ubuntu

Proposed by Heinrich Schuchardt
Status: Superseded
Proposed branch: ~xypron/grub:efivarfs
Merge into: ~ubuntu-core-dev/grub/+git/ubuntu:ubuntu
Diff against target: 132 lines (+118/-0)
2 files modified
debian/patches/efivar-check-that-efivarfs-is-writeable.patch (+117/-0)
debian/patches/series (+1/-0)
Reviewer Review Type Date Requested Status
Ubuntu Core Development Team Pending
Review via email: mp+417181@code.launchpad.net

This proposal has been superseded by a proposal from 2022-03-21.

Commit message

efivar: check that efivarfs is writeable

Some UEFI implementations (notably U-Boot) don't implement the
SetVariable() runtime service. On these systems the GRUB installation
must be completed manually. Write a warning in this case but avoid
throwing an error. (LP: #1965288)

Signed-off-by: Heinrich Schuchardt <email address hidden>

To post a comment you must log in.

Unmerged commits

7db6e17... by Heinrich Schuchardt

efivar: check that efivarfs is writeable

Some UEFI implementations (notably U-Boot) don't implement the
SetVariable() runtime service. On these systems the GRUB installation
must be completed manually. Write a warning in this case but avoid
throwing an error. (LP: #1965288)

Signed-off-by: Heinrich Schuchardt <email address hidden>

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1diff --git a/debian/patches/efivar-check-that-efivarfs-is-writeable.patch b/debian/patches/efivar-check-that-efivarfs-is-writeable.patch
2new file mode 100644
3index 0000000..93bcf16
4--- /dev/null
5+++ b/debian/patches/efivar-check-that-efivarfs-is-writeable.patch
6@@ -0,0 +1,117 @@
7+From 5bf070ddb6cbcc5af3725908a2e092fd02352f4c Mon Sep 17 00:00:00 2001
8+From: Heinrich Schuchardt <heinrich.schuchardt@canonical.com>
9+Date: Fri, 18 Mar 2022 15:21:33 +0100
10+Subject: [PATCH 1/1] efivar: check that efivarfs is writeable
11+
12+Some UEFI implementations (notably U-Boot) don't implement the
13+SetVariable() runtime service. On these systems the GRUB installation
14+must be completed manually. Write a warning in this case but avoid
15+throwing an error.
16+
17+Signed-off-by: Heinrich Schuchardt <heinrich.schuchardt@canonical.com>
18+---
19+ grub-core/osdep/unix/efivar.c | 81 +++++++++++++++++++++++++++++++++++
20+ 1 file changed, 81 insertions(+)
21+
22+diff --git a/grub-core/osdep/unix/efivar.c b/grub-core/osdep/unix/efivar.c
23+index d34df0f70..8a7ee0c94 100644
24+--- a/grub-core/osdep/unix/efivar.c
25++++ b/grub-core/osdep/unix/efivar.c
26+@@ -511,6 +511,79 @@ devices_equal (const_efidp a, const_efidp b)
27+ return false;
28+ }
29+
30++/**
31++ * efivar_is_rw - detect if the efivar file system exists and is writeable
32++ *
33++ * Return: true if efivarfs is writeable
34++ */
35++static bool
36++efivar_is_rw (void)
37++{
38++ const char filename[] = "/proc/self/mounts";
39++ int fd;
40++ grub_uint64_t size;
41++ char *data = NULL, *start, *end, *pos;
42++ bool ret = false;
43++
44++ fd = grub_util_fd_open (filename, GRUB_UTIL_FD_O_RDONLY);
45++ if (fd == -1)
46++ {
47++ grub_util_warn (_("cannot open `%s': %s"), filename, strerror (errno));
48++ return 0;
49++ }
50++
51++ /*
52++ * /proc/self/mounts does not provide a filesize. So read it into an initial
53++ * buffer. If the last byte of the buffer is overwritten, retry with double
54++ * the buffer size.
55++ */
56++ size = 4096;
57++ for (;;) {
58++ ssize_t s;
59++
60++ fd = grub_util_fd_open (filename, GRUB_UTIL_FD_O_RDONLY);
61++ if (fd == -1)
62++ {
63++ grub_util_warn (_("cannot open `%s': %s"), filename, strerror (errno));
64++ return 0;
65++ }
66++
67++ grub_util_info ("size %ld", size);
68++ data = xmalloc (size);
69++ grub_memset (data, 0, size);
70++ if (!data)
71++ {
72++ grub_util_warn ("%s", _("out of memory"));
73++ goto out;
74++ }
75++ s = read(fd, data, size);
76++ if (s < 0)
77++ {
78++ grub_util_warn (_("cannot read `%s': %s"), filename, strerror (errno));
79++ goto out;
80++ }
81++ grub_util_fd_close (fd);
82++ if (!data[size - 1])
83++ break;
84++ free(data);
85++ size *= 2;
86++ }
87++
88++ start = grub_strstr (data, "efivarfs ");
89++ if (!start)
90++ goto out;
91++ end = grub_strstr (start, "\n");
92++ if (!end)
93++ goto out;
94++ pos = grub_strstr (start, " rw,");
95++ if (pos && pos < end)
96++ ret = true;
97++
98++out:
99++ grub_free (data);
100++ return ret;
101++}
102++
103+ int
104+ grub_install_efivar_register_efi (grub_device_t efidir_grub_dev,
105+ const char *efidir, const char *efifile_path,
106+@@ -528,6 +601,14 @@ grub_install_efivar_register_efi (grub_device_t efidir_grub_dev,
107+ int rc;
108+ bool is_boot_efi;
109+
110++ /* Check if EFI variable can be written */
111++ if (!efivar_is_rw ())
112++ {
113++ grub_util_warn ("EFI variables cannot be set on this system");
114++ grub_util_warn ("You will have to complete the GRUB setup manually");
115++ return 0;
116++ }
117++
118+ is_boot_efi = strstr (efidir, "/boot/efi") != NULL;
119+ efidir_disk = grub_util_biosdisk_get_osdev (efidir_grub_dev->disk);
120+ efidir_part = efidir_grub_dev->disk->partition ? efidir_grub_dev->disk->partition->number + 1 : 1;
121+--
122+2.34.1
123+
124diff --git a/debian/patches/series b/debian/patches/series
125index 7942ada..0a4b388 100644
126--- a/debian/patches/series
127+++ b/debian/patches/series
128@@ -121,3 +121,4 @@ ubuntu-os-prober-auto.patch
129 efi-correct-struct-grub_efi_boot_services.patch
130 efi-implement-grub_efi_run_image.patch
131 fat-fix-listing-the-root-directory.patch
132+efivar-check-that-efivarfs-is-writeable.patch

Subscribers

People subscribed via source and target branches