GRUB:有什么办法可以有第二次超时或选择,或热键?

GRUB:有什么办法可以有第二次超时或选择,或热键?

我正在运行 openSUSE Tumbleweed(当我输入此内容时为 20120913,很可能在您阅读它时它有所不同),内核 5.14.1-1-default,grub2 版本 2.06-6.1。如果我的硬件规格与此相关(除了我使用的是 GF1080ti,在华硕 Strix Z270F 主板上使用 nvidia 驱动程序版本 470.63.01,那么请让我知道,我将发布它们)。

无论如何,我双启动 Windows/Linux,大概是 60/40%。我正在从安装 Linux 的驱动器上启动(UEFI 但安全启动关闭)(除非 Microsoft 认为它拥有我的计算机并在没有询问我的情况下更改启动顺序),并使用 YaST 将 Windows 启动加载程序设置为默认启动加载程序,并已超时(8秒,可能不重要)。

问题是我有一个多显示器设置,并且出于某种原因,显卡使用侧面显示器作为默认显示器(BIOS 出现在此处,以及加载图形驱动程序之前的其他任何内容),即使很多时候该屏幕甚至没有插入电源(当我不使用它时,不需要它成为能量吸血鬼)。这意味着 grub 仅在该屏幕上加载,因此虽然我可以正常启动到 Windows(不执行任何操作)或选择一个选项(通过按某个键),所以我要么必须插入并打开另一台显示器,要么盲目地尝试在启动菜单中选择正确的东西(给出一些可用的选项,可能不是一个好主意)。打开另一台显示器并不理想,因为这会使 KDE 自动将其切换为主显示器,因此我必须进入显示设置(当您的显卡连接了五个设备时,需要一些时间来加载)重置它,但这是对另一篇文章的投诉(除非你现在可以提供帮助,我不介意)。

那么我正在寻找什么...有什么方法可以设置 grub,以便如果我取消初始倒计时,它会为 Linux 启动另一个倒计时作为默认设置?或者设置一个键,这样我只需在启动时将其混搭,直到主显示屏打开并且我知道它正在启动到 Linux?或者类似的东西......基本上是一种在 grub 中选择(最好是特定的)非默认条目的盲目方式?

预先感谢您的回答!

答案1

Grub 2 支持热键,因此您可以实现这一点。

如果您编辑 grub.cfg 并将参数 --hotkey=l 添加到菜单项中,您将能够实现您正在寻找的内容。但执行 grub-update 时 /boot/grub.cfg 文件会被覆盖。

我没有双启动,因此无法正确测试它,但编辑 /etc/grub.d/10_linux 在我的系统中成功了。

在该文件中找到此部分:

linux_entry ()
{
  os="$1"
  version="$2"
  type="$3"
  args="$4"

  if [ -z "$boot_device_id" ]; then
      boot_device_id="$(grub_get_device_id "${GRUB_DEVICE}")"
  fi
  if [ x$type != xsimple ] ; then
      case $type in
          recovery)
              title="$(gettext_printf "%s, with Linux %s (%s)" "${os}" "${version}" "$(gettext "${GRUB_RECOVERY_TITLE}")")" ;;
          init-*)
              title="$(gettext_printf "%s, with Linux %s (%s)" "${os}" "${version}" "${type#init-}")" ;;
          *)
              title="$(gettext_printf "%s, with Linux %s" "${os}" "${version}")" ;;
      esac
      if [ x"$title" = x"$GRUB_ACTUAL_DEFAULT" ] || [ x"Previous Linux versions>$title" = x"$GRUB_ACTUAL_DEFAULT" ]; then
          replacement_title="$(echo "Advanced options for ${OS}" | sed 's,>,>>,g')>$(echo "$title" | sed 's,>,>>,g')"
          quoted="$(echo "$GRUB_ACTUAL_DEFAULT" | grub_quote)"
          title_correction_code="${title_correction_code}if [ \"x\$default\" = '$quoted' ]; then default='$(echo "$replacement_title>
          grub_warn "$(gettext_printf "Please don't use old title \`%s' for GRUB_DEFAULT, use \`%s' (for versions before 2.00) or \`>
      fi
      echo "menuentry '$(echo "$title" | grub_quote)' ${CLASS} \$menuentry_id_option 'gnulinux-$version-$type-$boot_device_id' {" | >
  else
      echo "menuentry '$(echo "$os" | grub_quote)' ${CLASS} --hotkey=l \$menuentry_id_option  'gnulinux-simple-$boot_device_id' {" |>
  fi      
  if [ "$quick_boot" = 1 ]; then
      echo "    recordfail" | sed "s/^/$submenu_indentation/"
  fi
  if [ x$type != xrecovery ] ; then
      save_default_entry | grub_add_tab
  fi

并添加--热键=l参数它所在的位置。执行 grub-update 并测试按 l 是否可以直接启动到 linux

答案2

感谢@shaola 为我指明了正确的方向!事实证明,不需要配置,至少在我的机器上是这样。原来 grub 已经内置了这些!当我注意到这一切已经在/etc/grub.d/10_linux

hotkey=1
incr_hotkey()
{
  [ -z "$hotkey" ] && return
  expr $hotkey + 1
}
print_hotkey()
{
  keys="123456789abdfgijklmnoprtuvwyz"
  if [ -z "$hotkey" ]||[ $hotkey -eq 0 ]||[ $hotkey -gt 30 ]; then
    return
  fi
  echo "--hotkey=$(expr substr $keys $hotkey 1)"
}

linux_entry ()
{
  os="$1"
  version="$2"
  type="$3"
  args="$4"

  if [ -n "${linux_root_device_thisversion}" ]; then
    root_device="root=${linux_root_device_thisversion}"
  else
    root_device=""
  fi

  if [ -z "$boot_device_id" ]; then
      boot_device_id="$(grub_get_device_id "${GRUB_DEVICE}")"
  fi
  if [ x$type != xsimple ] ; then
      case $type in
      recovery)
          title="$(gettext_printf "%s, with Linux %s (recovery mode)" "${os}" "${version}")" ;;
      *)
          title="$(gettext_printf "%s, with Linux %s" "${os}" "${version}")" ;;
      esac
      if [ x"$title" = x"$GRUB_ACTUAL_DEFAULT" ] || [ x"Previous Linux versions>$title" = x"$GRUB_ACTUAL_DEFAULT" ]; then
      replacement_title="$(echo "Advanced options for ${OS}" | sed 's,>,>>,g')>$(echo "$title" | sed 's,>,>>,g')"
      quoted="$(echo "$GRUB_ACTUAL_DEFAULT" | grub_quote)"
      title_correction_code="${title_correction_code}if [ \"x\$default\" = '$quoted' ]; then default='$(echo "$replacement_title" | grub_quote)'; fi;"
      grub_warn "$(gettext_printf "Please don't use old title \`%s' for GRUB_DEFAULT, use \`%s' (for versions before 2.00) or \`%s' (for 2.00 or later)" "$GRUB_ACTUAL_DEFAULT" "$replacement_title" "gnulinux-advanced-$boot_device_id>gnulinux-$version-$type-$boot_device_id")"
      fi
      echo "menuentry '$(echo "$title" | grub_quote)' $(print_hotkey) ${CLASS} \$menuentry_id_option 'gnulinux-$version-$type-$boot_device_id' {" | sed "s/^/$submenu_indentation/"
      hotkey=$(incr_hotkey)
  else
      echo "menuentry '$(echo "$os" | grub_quote)' $(print_hotkey) ${CLASS} \$menuentry_id_option 'gnulinux-simple-$boot_device_id' {" | sed "s/^/$submenu_indentation/"
      hotkey=$(incr_hotkey)
  fi      
  if [ x$type != xrecovery ] ; then
      save_default_entry | grub_add_tab
  fi

  # Use ELILO's generic "efifb" when it's known to be available.
  # FIXME: We need an interface to select vesafb in case efifb can't be used.
  if [ "x$GRUB_GFXPAYLOAD_LINUX" = x ]; then
      echo "    load_video" | sed "s/^/$submenu_indentation/"
      if grep -qx "CONFIG_FB_EFI=y" "${config}" 2> /dev/null \
      && grep -qx "CONFIG_VT_HW_CONSOLE_BINDING=y" "${config}" 2> /dev/null; then
      echo "    set gfxpayload=keep" | sed "s/^/$submenu_indentation/"
      fi
  else
      if [ "x$GRUB_GFXPAYLOAD_LINUX" != xtext ]; then
      echo "    load_video" | sed "s/^/$submenu_indentation/"
      fi
      echo "    set gfxpayload=$GRUB_GFXPAYLOAD_LINUX" | sed "s/^/$submenu_indentation/"
  fi

  echo "    insmod gzio" | sed "s/^/$submenu_indentation/"

我不完全是一个出色的程序员 - 事实上,我什至无法弄清楚它是什么语言(除非它是它自己的语言),但我猜测列表中的每个项目都有一个自动递增热键,并且我的 openSUSE 安装位于列表的顶部,这意味着我只需1在启动时进行混搭并等待我的迹象不会被迫使用一家想要效仿苹果来接管我生活的公司的操作系统加载Linux。

另外,如果你有像我这样的设置(或者至少像我这样)并且想尝试@shaola的想法,我必须运行grub2-mkconfig而不是grub-update.可能是发行版或版本类型的东西。绝对不是我的专业领域。

相关内容