[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PATCH] osdep: linux: getroot: Fix stack exhaustion
From: |
Andri Yngvason |
Subject: |
[PATCH] osdep: linux: getroot: Fix stack exhaustion |
Date: |
Mon, 18 Mar 2019 14:52:07 +0000 |
struct mountinfo_entry is c.a. 64k big. It is unwise to put such a large
variable onto the stack as this may cause the stack to grow too large on
systems with smaller stacks.
Signed-off-by: Andri Yngvason <address@hidden>
---
grub-core/osdep/linux/getroot.c | 31 +++++++++++++++++--------------
1 file changed, 17 insertions(+), 14 deletions(-)
diff --git a/grub-core/osdep/linux/getroot.c b/grub-core/osdep/linux/getroot.c
index 90d92d3ad..4e3ed2019 100644
--- a/grub-core/osdep/linux/getroot.c
+++ b/grub-core/osdep/linux/getroot.c
@@ -385,7 +385,7 @@ grub_find_root_devices_from_mountinfo (const char *dir,
char **relroot)
size_t len = 0;
grub_size_t entry_len, entry_max = 4;
struct mountinfo_entry *entries;
- struct mountinfo_entry parent_entry = { 0, 0, 0, "", "", "", "" };
+ static struct mountinfo_entry parent_entry = { 0, 0, 0, "", "", "", "" };
int i;
int retry = 0;
int dir_fd = -1;
@@ -405,27 +405,28 @@ again:
entry_len = 0;
+ struct mountinfo_entry* entry = xmalloc (sizeof(*entry));
+
/* First, build a list of relevant visible mounts. */
while (getline (&buf, &len, fp) > 0)
{
- struct mountinfo_entry entry;
int count;
size_t enc_path_len;
const char *sep;
if (sscanf (buf, "%d %d %u:%u %s %s%n",
- &entry.id, &parent_entry.id, &entry.major, &entry.minor,
- entry.enc_root, entry.enc_path, &count) < 6)
+ &entry->id, &parent_entry.id, &entry->major, &entry->minor,
+ entry->enc_root, entry->enc_path, &count) < 6)
continue;
- unescape (entry.enc_root);
- unescape (entry.enc_path);
+ unescape (entry->enc_root);
+ unescape (entry->enc_path);
- enc_path_len = strlen (entry.enc_path);
+ enc_path_len = strlen (entry->enc_path);
/* Check that enc_path is a prefix of dir. The prefix must either be
the entire string, or end with a slash, or be immediately followed
by a slash. */
- if (strncmp (dir, entry.enc_path, enc_path_len) != 0 ||
+ if (strncmp (dir, entry->enc_path, enc_path_len) != 0 ||
(enc_path_len && dir[enc_path_len - 1] != '/' &&
dir[enc_path_len] && dir[enc_path_len] != '/'))
continue;
@@ -435,10 +436,10 @@ again:
continue;
sep += sizeof (" - ") - 1;
- if (sscanf (sep, "%s %s", entry.fstype, entry.device) != 2)
+ if (sscanf (sep, "%s %s", entry->fstype, entry->device) != 2)
continue;
- unescape (entry.device);
+ unescape (entry->device);
/* Using the mount IDs, find out where this fits in the list of
visible mount entries we've seen so far. There are three
@@ -460,7 +461,7 @@ again:
/* Initialise list. */
entry_len = 2;
entries[0] = parent_entry;
- entries[1] = entry;
+ entries[1] = *entry;
}
else
{
@@ -470,23 +471,25 @@ again:
{
/* Insert at end, pruning anything previously above this. */
entry_len = i + 2;
- entries[i + 1] = entry;
+ entries[i + 1] = *entry;
break;
}
- else if (i == 0 && entries[i].id == entry.id)
+ else if (i == 0 && entries[i].id == entry->id)
{
/* Insert at start. */
entry_len++;
memmove (entries + 1, entries,
(entry_len - 1) * sizeof (*entries));
entries[0] = parent_entry;
- entries[1] = entry;
+ entries[1] = *entry;
break;
}
}
}
}
+ free(entry);
+
/* Now scan visible mounts for the ones we're interested in. */
for (i = entry_len - 1; i >= 0; i--)
{
--
2.11.0
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [PATCH] osdep: linux: getroot: Fix stack exhaustion,
Andri Yngvason <=