Upgrading to Grub 2 on Xen VPS Guests

Posted: May 8th, 2015 | Author: | Filed under: computing | No Comments »

If you have a linux VPS server hosted at a cloud provider you may find that you’re stuck on legacy Grub, and in some cases, may find that update-grub doesn’t properly update when a new kernel is installed. Here you’ll find two solutions, one to get Grub Legacy updating properly, and the second on how to update to Grub 2. This was personally tested on Debian, but the principles should translate to most distros.

*** WARNING: Do not attempt this if you do not have a solid understanding of Grub and the boot process for your distribution. Mangling up Grub can very easily make your system non-bootable and impossible to fix remotely unless you have access to a recovery console. ***

PART 1 -- Fixing Grub Legacy
The kernel updating issue is typically caused by Grub Legacy’s inability to realize it’s in a Xen guest environment. This can be solved by using to PvGrub to keep your /boot/grub/grub.conf updated (grub.conf is linked to /boot/grub/menu.lst).

1) Take a look in your /etc/fstab to find the root “/” partition for your VPS (if it lists a separate partition for /boot then use it instead). This will likely be something like “/dev/xvda1” or “/sda/xvda1”

2) Make a backup copy of your current /boot/grub/grub.conf

$ sudo cp /boot/grub/grub.conf /boot/grub/grub.conf.bak

3) Install PVGrub (aka. pvgrub-legacy or pv-grub-menu in Deb). This will remove the grub-legacy package but keep grub-common:

$ sudo apt-get install pv-grub-menu

4) Make sure your /etc/default/grub is configured how you want it, then run PvGrub:

$ sudo update-menu-lst

5) PvGrub should now have updated your /boot/grub/grub.conf with entries for all your kernels, with a structure similar to the example below. Verify that the “root” line lists the root (or boot) partition from step 1. Also verify that the UUID listed in the “kernel” line matches the UUID for your root “/” partition (use “ls -al /dev/disk/by-uuid/” to list UUIDs). Finally, make sure the “default” line lists the kernel you want to boot.

title Debian GNU/Linux, kernel 3.2.0-4-amd64
root (hostdisk//dev/xvda1)
kernel /boot/vmlinuz-3.2.0-4-amd64 root=UUID=5d83xx6a-7ed6-422a-8579-70a4a6eb3bb3 ro
initrd /boot/initrd.img-3.2.0-4-amd64

6) Reboot and confirm you’re running the new kernel (uname -a).

7) If the system won’t reboot then use the recovery console provided by your host to log-in as root, manually mount your root (or boot) filesystem and copy your backup grub.conf back over the new one (or try to fix the errors in the new one).

Additional Resources:
Installing PvGrub on other distros (Arch, Cent, Fedora Gentoo, etc) by Rackspace
PvGrub on Amazon EC2 instances

PART 2 -- Upgrading to Grub 2 (aka. PvGrub 2, aka. Grub 2 Xen)
If, and only if, you have a fully working Grub Legacy that’s booting nicely, then you can proceed to upgrade to Grub 2. The kicker here is that in most cloud VPS environments, you cannot actually overwrite the existing Grub Legacy in the MBR/partition boot sector, so the approach here is to do a one-time tweak of the Grub Legacy install to chainload Grub 2. Once completed, the Grub Legacy config will remain static and all future kernel updates will be maintained using Grub 2 in the normal fashion (i.e. update-grub).

*** WARNING: This has been tested on Debian 8.0 (Jessie), which includes new grub-xen packages (Grub 2 started including Xen support with 2.02~beta2). I do not believe the “grub-xen” package is available in prior releases. ***

1) Again, make a backup copy of your currently working /boot/grub/grub.conf and /etc/default/grub files.

2) Remove any current grub packages installed on the system (this will only remove the packages, not the existing grub binaries in the boot sector):

apt-get remove pv-grub-menu grub-common grub-legacy grub-pc grub2 grub2-common

3) Install Grub Xen package (Not grub-xen-host!)

apt-get install grub-xen

4) Double check that it installed fully (should have been automagically by APT, but just in case):

$ sudo grub-install --target=x86_64-xen

or if appropriate:

$ sudo grub-install --target=i386-xen

Ignore the junk warnings as long as you see “No error reported”.

Installing for x86_64-xen platform.
grub-install: warning: no hints available for your platform. Expect reduced performance.
grub-install: warning: WARNING: no platform-specific install was performed.
Installation finished. No error reported.

5) You should now have a file /boot/xen/pvboot-x86_64.elf (or pvboot-i386.elf)

6) Configure /etc/default/grub with your preferred settings, then run:

$ sudo update-grub

7) Verify that the Grub 2 config file (/boot/grub/grub.cfg, not grub.conf !!) was updated with your kernels and all looks in order (e.g. root partitions, etc).

8) Now setup Grub Legacy to chainload Grub 2. Edit /etc/grub/grub.conf (menu.lst). Set “default 0” and “timeout 1”, then add the following as the first entry in the kernels list (you may want to leave the other kernel entries as backup while testing). Make sure to adjust the “root” and “kernel” path as appropriate.

title Chainload Grub 2
root (hostdisk//dev/xvda1)
kernel /boot/xen/pvboot-x86_64.elf

9) If you had “GRUB_DEFAULT=saved” in your /etc/default/grub then remember to run grub-set-default before rebooting. If you make any more changes to /etc/default/grub or the /etc/grub.d/ files, then re-run update-grub.

10) Reboot!

11) If everything has gone according to plan then your Grub Legacy config never needs touched again. If your VPS host actually supports direct loading of Grub 2 (currently rare), then it may even skip the Grub Legacy config and directly load your Grub 2. Either way, the net effect is essentially the same -- booting for all future kernel updates is now handled directly using your Grub 2 config. There should not be any packages updating your Grub Legacy grub.conf file (update-grub and update-grub2 are just linked commands, both for updating Grub 2’s /boot/grub/grub.cfg config).

Additional Resources/Credit:
Many thanks to Ian Campbell for this post.

Leave a Reply