diff options
Diffstat (limited to 'meta/recipes-bsp/grub/files/CVE-2020-15707-linux-Fix-integer-overflows-in-initrd-size-handling.patch')
-rw-r--r-- | meta/recipes-bsp/grub/files/CVE-2020-15707-linux-Fix-integer-overflows-in-initrd-size-handling.patch | 177 |
1 files changed, 0 insertions, 177 deletions
diff --git a/meta/recipes-bsp/grub/files/CVE-2020-15707-linux-Fix-integer-overflows-in-initrd-size-handling.patch b/meta/recipes-bsp/grub/files/CVE-2020-15707-linux-Fix-integer-overflows-in-initrd-size-handling.patch deleted file mode 100644 index d4f9300c0a..0000000000 --- a/meta/recipes-bsp/grub/files/CVE-2020-15707-linux-Fix-integer-overflows-in-initrd-size-handling.patch +++ /dev/null | |||
@@ -1,177 +0,0 @@ | |||
1 | From 68a09a74f6d726d79709847f3671c0a08e4fb5a0 Mon Sep 17 00:00:00 2001 | ||
2 | From: Colin Watson <cjwatson@debian.org> | ||
3 | Date: Sat, 25 Jul 2020 12:15:37 +0100 | ||
4 | Subject: [PATCH 9/9] linux: Fix integer overflows in initrd size handling | ||
5 | |||
6 | These could be triggered by a crafted filesystem with very large files. | ||
7 | |||
8 | Fixes: CVE-2020-15707 | ||
9 | |||
10 | Signed-off-by: Colin Watson <cjwatson@debian.org> | ||
11 | Reviewed-by: Jan Setje-Eilers <jan.setjeeilers@oracle.com> | ||
12 | Reviewed-by: Daniel Kiper <daniel.kiper@oracle.com> | ||
13 | |||
14 | Upstream-Status: Backport | ||
15 | CVE: CVE-2020-15707 | ||
16 | |||
17 | Reference to upstream patch: | ||
18 | https://git.savannah.gnu.org/cgit/grub.git/commit/?id=e7b8856f8be3292afdb38d2e8c70ad8d62a61e10 | ||
19 | |||
20 | Signed-off-by: Yongxin Liu <yongxin.liu@windriver.com> | ||
21 | --- | ||
22 | grub-core/loader/linux.c | 74 +++++++++++++++++++++++++++++++++++------------- | ||
23 | 1 file changed, 54 insertions(+), 20 deletions(-) | ||
24 | |||
25 | diff --git a/grub-core/loader/linux.c b/grub-core/loader/linux.c | ||
26 | index 471b214..8c8565a 100644 | ||
27 | --- a/grub-core/loader/linux.c | ||
28 | +++ b/grub-core/loader/linux.c | ||
29 | @@ -4,6 +4,7 @@ | ||
30 | #include <grub/misc.h> | ||
31 | #include <grub/file.h> | ||
32 | #include <grub/mm.h> | ||
33 | +#include <grub/safemath.h> | ||
34 | |||
35 | struct newc_head | ||
36 | { | ||
37 | @@ -98,13 +99,13 @@ free_dir (struct dir *root) | ||
38 | grub_free (root); | ||
39 | } | ||
40 | |||
41 | -static grub_size_t | ||
42 | +static grub_err_t | ||
43 | insert_dir (const char *name, struct dir **root, | ||
44 | - grub_uint8_t *ptr) | ||
45 | + grub_uint8_t *ptr, grub_size_t *size) | ||
46 | { | ||
47 | struct dir *cur, **head = root; | ||
48 | const char *cb, *ce = name; | ||
49 | - grub_size_t size = 0; | ||
50 | + *size = 0; | ||
51 | while (1) | ||
52 | { | ||
53 | for (cb = ce; *cb == '/'; cb++); | ||
54 | @@ -130,14 +131,22 @@ insert_dir (const char *name, struct dir **root, | ||
55 | ptr = make_header (ptr, name, ce - name, | ||
56 | 040777, 0); | ||
57 | } | ||
58 | - size += ALIGN_UP ((ce - (char *) name) | ||
59 | - + sizeof (struct newc_head), 4); | ||
60 | + if (grub_add (*size, | ||
61 | + ALIGN_UP ((ce - (char *) name) | ||
62 | + + sizeof (struct newc_head), 4), | ||
63 | + size)) | ||
64 | + { | ||
65 | + grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow is detected")); | ||
66 | + grub_free (n->name); | ||
67 | + grub_free (n); | ||
68 | + return grub_errno; | ||
69 | + } | ||
70 | *head = n; | ||
71 | cur = n; | ||
72 | } | ||
73 | root = &cur->next; | ||
74 | } | ||
75 | - return size; | ||
76 | + return GRUB_ERR_NONE; | ||
77 | } | ||
78 | |||
79 | grub_err_t | ||
80 | @@ -173,26 +182,33 @@ grub_initrd_init (int argc, char *argv[], | ||
81 | eptr = grub_strchr (ptr, ':'); | ||
82 | if (eptr) | ||
83 | { | ||
84 | + grub_size_t dir_size, name_len; | ||
85 | + | ||
86 | initrd_ctx->components[i].newc_name = grub_strndup (ptr, eptr - ptr); | ||
87 | - if (!initrd_ctx->components[i].newc_name) | ||
88 | + if (!initrd_ctx->components[i].newc_name || | ||
89 | + insert_dir (initrd_ctx->components[i].newc_name, &root, 0, | ||
90 | + &dir_size)) | ||
91 | { | ||
92 | grub_initrd_close (initrd_ctx); | ||
93 | return grub_errno; | ||
94 | } | ||
95 | - initrd_ctx->size | ||
96 | - += ALIGN_UP (sizeof (struct newc_head) | ||
97 | - + grub_strlen (initrd_ctx->components[i].newc_name), | ||
98 | - 4); | ||
99 | - initrd_ctx->size += insert_dir (initrd_ctx->components[i].newc_name, | ||
100 | - &root, 0); | ||
101 | + name_len = grub_strlen (initrd_ctx->components[i].newc_name); | ||
102 | + if (grub_add (initrd_ctx->size, | ||
103 | + ALIGN_UP (sizeof (struct newc_head) + name_len, 4), | ||
104 | + &initrd_ctx->size) || | ||
105 | + grub_add (initrd_ctx->size, dir_size, &initrd_ctx->size)) | ||
106 | + goto overflow; | ||
107 | newc = 1; | ||
108 | fname = eptr + 1; | ||
109 | } | ||
110 | } | ||
111 | else if (newc) | ||
112 | { | ||
113 | - initrd_ctx->size += ALIGN_UP (sizeof (struct newc_head) | ||
114 | - + sizeof ("TRAILER!!!") - 1, 4); | ||
115 | + if (grub_add (initrd_ctx->size, | ||
116 | + ALIGN_UP (sizeof (struct newc_head) | ||
117 | + + sizeof ("TRAILER!!!") - 1, 4), | ||
118 | + &initrd_ctx->size)) | ||
119 | + goto overflow; | ||
120 | free_dir (root); | ||
121 | root = 0; | ||
122 | newc = 0; | ||
123 | @@ -208,19 +224,29 @@ grub_initrd_init (int argc, char *argv[], | ||
124 | initrd_ctx->nfiles++; | ||
125 | initrd_ctx->components[i].size | ||
126 | = grub_file_size (initrd_ctx->components[i].file); | ||
127 | - initrd_ctx->size += initrd_ctx->components[i].size; | ||
128 | + if (grub_add (initrd_ctx->size, initrd_ctx->components[i].size, | ||
129 | + &initrd_ctx->size)) | ||
130 | + goto overflow; | ||
131 | } | ||
132 | |||
133 | if (newc) | ||
134 | { | ||
135 | initrd_ctx->size = ALIGN_UP (initrd_ctx->size, 4); | ||
136 | - initrd_ctx->size += ALIGN_UP (sizeof (struct newc_head) | ||
137 | - + sizeof ("TRAILER!!!") - 1, 4); | ||
138 | + if (grub_add (initrd_ctx->size, | ||
139 | + ALIGN_UP (sizeof (struct newc_head) | ||
140 | + + sizeof ("TRAILER!!!") - 1, 4), | ||
141 | + &initrd_ctx->size)) | ||
142 | + goto overflow; | ||
143 | free_dir (root); | ||
144 | root = 0; | ||
145 | } | ||
146 | |||
147 | return GRUB_ERR_NONE; | ||
148 | + | ||
149 | + overflow: | ||
150 | + free_dir (root); | ||
151 | + grub_initrd_close (initrd_ctx); | ||
152 | + return grub_error (GRUB_ERR_OUT_OF_RANGE, N_("overflow is detected")); | ||
153 | } | ||
154 | |||
155 | grub_size_t | ||
156 | @@ -261,8 +287,16 @@ grub_initrd_load (struct grub_linux_initrd_context *initrd_ctx, | ||
157 | |||
158 | if (initrd_ctx->components[i].newc_name) | ||
159 | { | ||
160 | - ptr += insert_dir (initrd_ctx->components[i].newc_name, | ||
161 | - &root, ptr); | ||
162 | + grub_size_t dir_size; | ||
163 | + | ||
164 | + if (insert_dir (initrd_ctx->components[i].newc_name, &root, ptr, | ||
165 | + &dir_size)) | ||
166 | + { | ||
167 | + free_dir (root); | ||
168 | + grub_initrd_close (initrd_ctx); | ||
169 | + return grub_errno; | ||
170 | + } | ||
171 | + ptr += dir_size; | ||
172 | ptr = make_header (ptr, initrd_ctx->components[i].newc_name, | ||
173 | grub_strlen (initrd_ctx->components[i].newc_name), | ||
174 | 0100777, | ||
175 | -- | ||
176 | 2.14.4 | ||
177 | |||