From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from list by lists.gnu.org with archive (Exim 4.71) id 1VXebp-0005vw-PD for mharc-grub-devel@gnu.org; Sat, 19 Oct 2013 18:02:57 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:35165) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1VXebh-0005ul-GN for grub-devel@gnu.org; Sat, 19 Oct 2013 18:02:55 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1VXebb-0006i6-I8 for grub-devel@gnu.org; Sat, 19 Oct 2013 18:02:49 -0400 Received: from powerman.name ([109.86.197.238]:52744) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1VXebb-0006hu-6Y for grub-devel@gnu.org; Sat, 19 Oct 2013 18:02:43 -0400 Received: (qmail 16906 invoked by uid 1000); 19 Oct 2013 22:02:41 -0000 Date: Sun, 20 Oct 2013 01:02:41 +0300 From: Alex Efros To: grub-devel@gnu.org Subject: [patch] more configurable menu generation Message-ID: <20131019220241.GD8031@home.power> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="3MwIy2ne0vdjdPXF" Content-Disposition: inline Organization: http://powerman.name/ User-Agent: Mutt/1.5.21 (2010-09-15) X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x [generic] [fuzzy] X-Received-From: 109.86.197.238 X-BeenThere: grub-devel@gnu.org X-Mailman-Version: 2.1.14 Precedence: list Reply-To: The development of GNU GRUB List-Id: The development of GNU GRUB List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sat, 19 Oct 2013 22:02:55 -0000 --3MwIy2ne0vdjdPXF Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Hi! I've developed a patch which implement few related features: - ability to define which linux kernels and in which order will be listed in top menu instead of single auto-detected latest kernel - ability to show kernel version in top menu items, to distinguish between different kernels added by previous feature - ability to use custom kernel command line parameters for depending on kernel version instead of GRUB_CMDLINE_LINUX_DEFAULT for all kernels Here is my real use-case explaining needs in these features. I'm experimenting with switching between proprietary nvidia driver and nouveau. My main kernel is 3.10.1-hardened-r1 (for proprietary nvidia driver), and I've also compiled experimental kernel with "_nouveau" local version: 3.10.1-hardened-r1_nouveau. First issue - auto-detect of latest kernel choose 3.10.1-hardened-r1_nouveau, which is wrong for me, and only way to change this is add some fake local version for main kernel just to make sure it will be sorted before "_nouveau" string. Second issue - main kernel need "vga=" parameter, while nouveau kernel need "video=" parameter, but there is no way to configure this. Third issue - I'd like to have both normal and nouveau kernels in main menu, in manually defined order. All these features configured in /etc/default/grub using new variables: GRUB_SIMPLE_VERSION, GRUB_MENU_LINUX, GRUB_CMDLINE_LINUX_CUSTOM. Example: ---cut--- # Show kernel version in top menu entries GRUB_SIMPLE_VERSION=true # Manually define list of top menu entries instead of auto-detecting # latest kernel. GRUB_MENU_LINUX=' /boot/vmlinuz-3.10.1-hardened-r1 /boot/vmlinuz-3.10.1-hardened-r1_nouveau ' # Append parameters to the linux kernel command line for non-recovery entries # for some kernels (instead of GRUB_CMDLINE_LINUX_DEFAULT) # Should contain any amount of pairs: shell pattern for kernel version and # kernel command line for it (must be quoted if contain spaces). # First matched pattern will be used. Example: # GRUB_CMDLINE_LINUX_CUSTOM=' # *_nouveau video=800x600 # 3.10.* "vga=0x315 it87.force_id=0x8721" # 3.9.9-hardened "init=/bin/sh" # ' GRUB_CMDLINE_LINUX_CUSTOM=' *_nouveau "video=800x600" ' ---cut--- Attached patch is for grub-2.00_p5107. Patch tested with dash and bash. -- WBR, Alex. --3MwIy2ne0vdjdPXF Content-Type: application/x-patch Content-Disposition: attachment; filename="customize_menu.patch" Content-Transfer-Encoding: quoted-printable diff -uNr grub-2.00.orig/util/grub.d/10_linux.in grub-2.00/util/grub.d/10_l= inux.in=0A--- grub-2.00.orig/util/grub.d/10_linux.in 2013-08-04 22:24:58.00= 0000000 +0300=0A+++ grub-2.00/util/grub.d/10_linux.in 2013-10-20 00:30:13.3= 05280525 +0300=0A@@ -98,7 +98,12 @@=0A fi=0A echo "menuentry '$= (echo "$title" | grub_quote)' ${CLASS} \$menuentry_id_option 'gnulinux-$ver= sion-$type-$boot_device_id' {" | sed "s/^/$submenu_indentation/"=0A else= =0A- echo "menuentry '$(echo "$os" | grub_quote)' ${CLASS} \$menuentry= _id_option 'gnulinux-simple-$boot_device_id' {" | sed "s/^/$submenu_indenta= tion/"=0A+ if [ "x$GRUB_SIMPLE_VERSION" =3D xtrue ]; then=0A+ title= =3D"$(gettext_printf "%s, with Linux %s" "${os}" "${version}")"=0A+ el= se=0A+ title=3D"${os}"=0A+ fi=0A+ echo "menuentry '$(echo= "$title" | grub_quote)' ${CLASS} \$menuentry_id_option 'gnulinux-simple-$b= oot_device_id' {" | sed "s/^/$submenu_indentation/"=0A fi =0A if [= x$type !=3D xrecovery ] ; then=0A save_default_entry | grub_add_tab= =0A@@ -150,6 +155,25 @@=0A EOF=0A }=0A =0A+make__get_cmdline_linux () {=0A+= local func IFS=0A+ IFS=3D'=0A+'=0A+ set -- `echo "$GRUB_CMDLINE_LINUX_CUST= OM" | xargs -n 1 echo` "*" "$GRUB_CMDLINE_LINUX_DEFAULT"=0A+ if [ $(( $# % = 2 )) -ne 0 ]; then=0A+ echo GRUB_CMDLINE_LINUX_CUSTOM must contain even el= ements >&2=0A+ exit 1=0A+ fi=0A+ func=3D'get_cmdline_linux () { case $1 in= ';=0A+ while [ $# -gt 0 ]; do=0A+ func=3D"$func $1) echo '$2' ;;"=0A+ sh= ift 2=0A+ done=0A+ func=3D"$func esac; }"=0A+ eval $func=0A+}=0A+make__get_= cmdline_linux=0A+=0A machine=3D`uname -m`=0A case "x$machine" in=0A xi?= 86 | xx86_64)=0A@@ -161,6 +185,9 @@=0A if grub_file_is_no= t_garbage "$i" ; then echo -n "$i " ; fi=0A done` ;;=0A esac=0A+list_= simple=3D`for i in ${GRUB_MENU_LINUX} ; do=0A+ if grub_file_is_not_garbag= e "$i" ; then echo -n "$i " ; fi=0A+ done`=0A =0A case "$machine" in=0A= i?86) GENKERNEL_ARCH=3D"x86" ;;=0A@@ -179,9 +206,15 @@=0A # yet, so it= 's empty. In a submenu it will be equal to '\t' (one tab).=0A submenu_inden= tation=3D""=0A =0A+submenu_tmpfile=3D/tmp/grub.10_linux.submenu.$$=0A+exec = 3>$submenu_tmpfile=0A+=0A is_first_entry=3Dtrue=0A while [ "x$list" !=3D "x= " ] ; do=0A linux=3D`version_find_latest $list`=0A+ if [ "x$list_simple"= !=3D "x" ]; then=0A+ linux=3D${list_simple%% *}=0A+ fi=0A gettext_pr= intf "Found linux image: %s\n" "$linux" >&2=0A basename=3D`basename $linu= x`=0A dirname=3D`dirname $linux`=0A@@ -189,6 +222,7 @@=0A version=3D`ec= ho $basename | sed -e "s,^[^0-9]*-,,g"`=0A alt_version=3D`echo $version |= sed -e "s,\.old$,,g"`=0A linux_root_device_thisversion=3D"${LINUX_ROOT_D= EVICE}"=0A+ cmdline_linux=3D`get_cmdline_linux ${version}`=0A =0A initrd= =3D=0A for i in "initrd.img-${version}" "initrd-${version}.img" "initrd-$= {version}.gz" \=0A@@ -226,24 +260,28 @@=0A linux_root_device_thisversio= n=3D${GRUB_DEVICE}=0A fi=0A =0A+ submenu_indentation=3D""=0A if [ "x$i= s_first_entry" =3D xtrue ]; then=0A linux_entry "${OS}" "${version}" si= mple \=0A- "${GRUB_CMDLINE_LINUX} ${GRUB_CMDLINE_LINUX_DEFAULT}"=0A+ = "${GRUB_CMDLINE_LINUX} ${cmdline_linux}"=0A =0A- submenu_indentation=3D"= $grub_tab"=0A- =0A if [ -z "$boot_device_id" ]; then=0A boot_device= _id=3D"$(grub_get_device_id "${GRUB_DEVICE}")"=0A fi=0A # TRANSLATO= RS: %s is replaced with an OS name=0A- echo "submenu '$(gettext_printf "= Advanced options for %s" "${OS}" | grub_quote)' \$menuentry_id_option 'gnul= inux-advanced-$boot_device_id' {"=0A+ echo "submenu '$(gettext_printf "A= dvanced options for %s" "${OS}" | grub_quote)' \$menuentry_id_option 'gnuli= nux-advanced-$boot_device_id' {" >&3=0A+ elif [ "x$list_simple" !=3D "x" ]= ; then=0A+ linux_entry "${OS}" "${version}" simple \=0A+ "${GRUB_CMDLIN= E_LINUX} ${cmdline_linux}"=0A fi=0A+ list_simple=3D${list_simple#* }=0A = =0A- linux_entry "${OS}" "${version}" advanced \=0A- "${GRUB_= CMDLINE_LINUX} ${GRUB_CMDLINE_LINUX_DEFAULT}"=0A+ submenu_indentation=3D"$= grub_tab"=0A+ linux_entry "${OS}" "${version}" advanced \=0A+ = "${GRUB_CMDLINE_LINUX} ${cmdline_linux}" >&3=0A if [ "x${GRUB_DISABLE_R= ECOVERY}" !=3D "xtrue" ]; then=0A linux_entry "${OS}" "${version}" reco= very \=0A- "single ${GRUB_CMDLINE_LINUX}"=0A+ = "single ${GRUB_CMDLINE_LINUX}" >&3=0A fi=0A =0A list=3D`echo $list | t= r ' ' '\n' | grep -vx $linux | tr '\n' ' '`=0A@@ -253,7 +291,10 @@=0A # If = at least one kernel was found, then we need to=0A # add a closing '}' for t= he submenu command.=0A if [ x"$is_first_entry" !=3D xtrue ]; then=0A- echo= '}'=0A+ echo '}' >&3=0A+ exec 3>&-=0A+ cat $submenu_tmpfile=0A+ rm $su= bmenu_tmpfile=0A fi=0A =0A echo "$title_correction_code"=0Adiff -uNr grub-2= =2E00.orig/util/grub-mkconfig.in grub-2.00/util/grub-mkconfig.in=0A--- grub= -2.00.orig/util/grub-mkconfig.in 2013-08-15 20:09:04.000000000 +0300=0A+++ = grub-2.00/util/grub-mkconfig.in 2013-10-20 00:13:27.799357848 +0300=0A@@ -1= 92,8 +192,11 @@=0A GRUB_BUTTON_CMOS_ADDRESS \=0A GRUB_BUTTON_CMOS_CLEAN= \=0A GRUB_DISTRIBUTOR \=0A+ GRUB_SIMPLE_VERSION \=0A+ GRUB_MENU_LINUX = \=0A GRUB_CMDLINE_LINUX \=0A GRUB_CMDLINE_LINUX_DEFAULT \=0A+ GRUB_CMD= LINE_LINUX_CUSTOM \=0A GRUB_CMDLINE_XEN \=0A GRUB_CMDLINE_XEN_DEFAULT \= =0A GRUB_CMDLINE_LINUX_XEN_REPLACE \=0A --3MwIy2ne0vdjdPXF--