From 23c28a97add1866973eebe07c51c2ce4ceba0d94 Mon Sep 17 00:00:00 2001 From: Francis Rowe Date: Fri, 13 Feb 2015 22:46:19 -0500 Subject: getgrub: add notes about work on longstanding bug in GRUB Relating to vesamenu.c32 file support in the syslinux_configfile function of GRUB. --- diff --git a/getgrub b/getgrub index 709fe99..36b7336 100755 --- a/getgrub +++ b/getgrub @@ -49,6 +49,24 @@ git reset --hard 32cd33bd19348afb77ab849846e0b6d6157ea308 # Replace "GNU GRUB version" in GRUB screen with "FREE AS IN FREEDOM" git am "../resources/grub/patch/0001-grub-core-normal-main.c-Display-FREE-AS-IN-FREEDOM-n.patch" +## See these threads on grub-dev@gnu.org: +## [bug #44238] Add support for menu.c32 and vesamenu.c32 in lib/syslinux_parse +## [bug #44239] Behavior of syslinux_parse differs from SYSLINUX for initrd= option +## These make vesamenu.c32 work (translation: Debian/Tails ISOLINUX) but they are +## buggy at the moment; Trisquel ISOLINUX parsing fails with these patches, for instance: +## "error: syntax error.", "error: Incorrect command." +## The mailing list contains updated versions of the patches mentioned below +## Work with Lunar^ on IRC on finishing the patch so that it fixes the issue +## while not causing other regressions. Wait until this is merged in GRUB(upstream). +# Add support for menu.c32 and vesamenu.c32 in lib/syslinux_parse +# See https://savannah.gnu.org/bugs/index.php?44238 +# TODO: Remove this patch when it is upstreamed. +# git am "../resources/grub/patch/0002-syslinux_parse-add-support-for-vesa-menu.c32.patch" +# Behavior of syslinux_parse differs from SYSLINUX for initrd= option +# See https://savannah.gnu.org/bugs/index.php?44239 +# TODO: Remove this patch when it is upstreamed. +# git am "../resources/grub/patch/0003-syslinux_parse-keep-initrd-in-kernel-the-command-lin.patch" + cd ../ echo "FINISHED DOWNLOADING GRUB" diff --git a/resources/grub/patch/0002-syslinux_parse-add-support-for-vesa-menu.c32.patch b/resources/grub/patch/0002-syslinux_parse-add-support-for-vesa-menu.c32.patch new file mode 100644 index 0000000..504b277 --- /dev/null +++ b/resources/grub/patch/0002-syslinux_parse-add-support-for-vesa-menu.c32.patch @@ -0,0 +1,199 @@ +From c3b8bd878e97fe5c1b1d6409bcecf70f64e63669 Mon Sep 17 00:00:00 2001 +From: Lunar +Date: Sat, 14 Feb 2015 14:14:25 +0100 +Subject: [PATCH] lib/syslinux_parse: add support for (vesa)menu.c32 + +--- + grub-core/lib/syslinux_parse.c | 156 ++++++++++++++++++++++++++--------------- + 1 file changed, 98 insertions(+), 58 deletions(-) + +diff --git a/grub-core/lib/syslinux_parse.c b/grub-core/lib/syslinux_parse.c +index 2c874b1..1012f02 100644 +--- a/grub-core/lib/syslinux_parse.c ++++ b/grub-core/lib/syslinux_parse.c +@@ -840,6 +840,74 @@ simplify_filename (char *str) + } + + static grub_err_t ++print_config (struct output_buffer *outbuf, ++ struct syslinux_menu *menu, ++ const char *filename, const char *basedir) ++{ ++ grub_err_t err; ++ char *new_cwd, *new_target_cwd; ++ ++ new_cwd = get_read_filename (menu, basedir); ++ if (!new_cwd) ++ return grub_errno; ++ new_target_cwd = get_target_filename (menu, basedir); ++ if (!new_target_cwd) ++ return grub_errno; ++ ++ struct syslinux_menu *menuptr; ++ char *newname; ++ int depth = 0; ++ ++ newname = get_read_filename (menu, filename); ++ if (!newname) ++ return grub_errno; ++ simplify_filename (newname); ++ ++ print_string ("#"); ++ print_file (outbuf, menu, filename, NULL); ++ print_string (" "); ++ print (outbuf, newname, grub_strlen (newname)); ++ print_string (":\n"); ++ ++ for (menuptr = menu; menuptr; menuptr = menuptr->parent, depth++) ++ if (grub_strcmp (menuptr->filename, newname) == 0 ++ || depth > 20) ++ break; ++ if (menuptr) ++ { ++ print_string (" syslinux_configfile -r "); ++ print_file (outbuf, menu, "/", NULL); ++ print_string (" -c "); ++ print_file (outbuf, menu, basedir, NULL); ++ print_string (" "); ++ print_file (outbuf, menu, filename, NULL); ++ print_string ("\n"); ++ } ++ else ++ { ++ err = config_file (outbuf, menu->root_read_directory, ++ menu->root_target_directory, new_cwd, new_target_cwd, ++ newname, menu, menu->flavour); ++ if (err == GRUB_ERR_FILE_NOT_FOUND ++ || err == GRUB_ERR_BAD_FILENAME) ++ { ++ grub_errno = err = GRUB_ERR_NONE; ++ print_string ("# File "); ++ err = print (outbuf, newname, grub_strlen (newname)); ++ if (err) ++ return err; ++ print_string (" not found\n"); ++ } ++ if (err) ++ return err; ++ } ++ grub_free (newname); ++ grub_free (new_cwd); ++ grub_free (new_target_cwd); ++ return GRUB_ERR_NONE; ++} ++ ++static grub_err_t + write_entry (struct output_buffer *outbuf, + struct syslinux_menu *menu, + struct syslinux_menuentry *curentry) +@@ -1240,6 +1308,35 @@ write_entry (struct output_buffer *outbuf, + break; + } + ++ if (grub_strcasecmp (basename, "menu.c32") == 0 || ++ grub_strcasecmp (basename, "vesamenu.c32") == 0) ++ { ++ char *ptr; ++ char *end; ++ ++ ptr = curentry->append; ++ if (!ptr) ++ return grub_errno; ++ ++ while (*ptr) ++ { ++ end = ptr; ++ for (end = ptr; *end && !grub_isspace (*end); end++); ++ if (*end) ++ *end++ = '\0'; ++ ++ /* "~" is supposed to be current file, so let's skip it */ ++ if (grub_strcmp (ptr, "~") == 0) ++ continue; ++ err = print_config (outbuf, menu, ptr, ""); ++ if (err != GRUB_ERR_NONE) ++ break; ++ for (ptr = end; *ptr && grub_isspace (*ptr); ptr++); ++ } ++ err = GRUB_ERR_NONE; ++ break; ++ } ++ + /* FIXME: gdb, GFXBoot, Hdt, Ifcpu, Ifplop, Kbdmap, + FIXME: Linux, Lua, Meminfo, rosh, Sanbboot */ + +@@ -1252,70 +1349,13 @@ write_entry (struct output_buffer *outbuf, + } + case KERNEL_CONFIG: + { +- char *new_cwd, *new_target_cwd; + const char *ap; + ap = curentry->append; + if (!ap) + ap = curentry->argument; + if (!ap) + ap = ""; +- new_cwd = get_read_filename (menu, ap); +- if (!new_cwd) +- return grub_errno; +- new_target_cwd = get_target_filename (menu, ap); +- if (!new_target_cwd) +- return grub_errno; +- +- struct syslinux_menu *menuptr; +- char *newname; +- int depth = 0; +- +- newname = get_read_filename (menu, curentry->kernel_file); +- if (!newname) +- return grub_errno; +- simplify_filename (newname); +- +- print_string ("#"); +- print_file (outbuf, menu, curentry->kernel_file, NULL); +- print_string (" "); +- print (outbuf, newname, grub_strlen (newname)); +- print_string (":\n"); +- +- for (menuptr = menu; menuptr; menuptr = menuptr->parent, depth++) +- if (grub_strcmp (menuptr->filename, newname) == 0 +- || depth > 20) +- break; +- if (menuptr) +- { +- print_string (" syslinux_configfile -r "); +- print_file (outbuf, menu, "/", NULL); +- print_string (" -c "); +- print_file (outbuf, menu, ap, NULL); +- print_string (" "); +- print_file (outbuf, menu, curentry->kernel_file, NULL); +- print_string ("\n"); +- } +- else +- { +- err = config_file (outbuf, menu->root_read_directory, +- menu->root_target_directory, new_cwd, new_target_cwd, +- newname, menu, menu->flavour); +- if (err == GRUB_ERR_FILE_NOT_FOUND +- || err == GRUB_ERR_BAD_FILENAME) +- { +- grub_errno = err = GRUB_ERR_NONE; +- print_string ("# File "); +- err = print (outbuf, newname, grub_strlen (newname)); +- if (err) +- return err; +- print_string (" not found\n"); +- } +- if (err) +- return err; +- } +- grub_free (newname); +- grub_free (new_cwd); +- grub_free (new_target_cwd); ++ print_config (outbuf, menu, curentry->kernel_file, ap); + } + break; + case KERNEL_NO_KERNEL: +-- +1.9.1 + diff --git a/resources/grub/patch/0003-syslinux_parse-keep-initrd-in-kernel-the-command-lin.patch b/resources/grub/patch/0003-syslinux_parse-keep-initrd-in-kernel-the-command-lin.patch new file mode 100644 index 0000000..2582e6d --- /dev/null +++ b/resources/grub/patch/0003-syslinux_parse-keep-initrd-in-kernel-the-command-lin.patch @@ -0,0 +1,65 @@ +From c4722dc86c68fda07fe2972d8364465487d64118 Mon Sep 17 00:00:00 2001 +From: Lunar +Date: Sat, 14 Feb 2015 16:50:14 +0100 +Subject: [PATCH] lib/syslinux_parse: keep initrd= in kernel the command line + +SYSLINUX parses but does not remove "initrd=..." option from the kernel +command line. As some distributions (e.g. Tails) rely on its +presence, let's keep the same behavior. +--- + grub-core/lib/syslinux_parse.c | 24 +++++------------------- + 1 file changed, 5 insertions(+), 19 deletions(-) + +diff --git a/grub-core/lib/syslinux_parse.c b/grub-core/lib/syslinux_parse.c +index 1012f02..3e58bee 100644 +--- a/grub-core/lib/syslinux_parse.c ++++ b/grub-core/lib/syslinux_parse.c +@@ -939,6 +939,7 @@ write_entry (struct output_buffer *outbuf, + char *ptr; + char *cmdline; + char *initrd = NULL; ++ cmdline = grub_strdup(curentry->append); + for (ptr = curentry->append; ptr && *ptr; ptr++) + if ((ptr == curentry->append || grub_isspace (ptr[-1])) + && grub_strncasecmp (ptr, "initrd=", sizeof ("initrd=") - 1) +@@ -946,33 +947,18 @@ write_entry (struct output_buffer *outbuf, + break; + if (ptr && *ptr) + { +- char *ptr2; +- grub_size_t totlen = grub_strlen (curentry->append); + initrd = ptr + sizeof ("initrd=") - 1; +- for (ptr2 = ptr; *ptr2 && !grub_isspace (*ptr2); ptr2++); +- if (*ptr2) +- { +- *ptr2 = 0; +- ptr2++; +- } +- cmdline = grub_malloc (totlen + 1 - (ptr2 - ptr)); +- if (!cmdline) +- return grub_errno; +- grub_memcpy (cmdline, curentry->append, ptr - curentry->append); +- grub_memcpy (cmdline + (ptr - curentry->append), +- ptr2, totlen - (ptr2 - curentry->append)); +- *(cmdline + totlen - (ptr2 - ptr)) = 0; ++ for (; *ptr && !grub_isspace (*ptr); ptr++); ++ *ptr = '\0'; + } +- else +- cmdline = curentry->append; + print_string (" if test x$grub_platform = xpc; then " + "linux_suffix=16; else linux_suffix= ; fi\n"); + print_string (" linux$linux_suffix "); + print_file (outbuf, menu, curentry->kernel_file, NULL); + print_string (" "); +- if (cmdline) +- print (outbuf, cmdline, grub_strlen (cmdline)); ++ print (outbuf, cmdline, grub_strlen (cmdline)); + print_string ("\n"); ++ grub_free(cmdline); + if (initrd || curentry->initrds) + { + struct initrd_list *lst; +-- +1.9.1 + -- cgit v0.9.1