Dual Boot Windows and Linux

By Erik Jan de Vries for BigData Republic

Is Linux your preferred operating system for machine learning, especially for GPU accelerated algorithms? But do you like to use Microsoft Office for word processing, spreadsheets and presentations? Or perhaps you like to use your GPU for gaming on Microsoft Windows? In this blog I will discuss my experiences with setting up a dual boot system. Hopefully it will help you avoid some of the frustrations I faced while setting up my system.

This blog post is part of a larger series:

My laptop is an MSI GS63VR laptop, with Nvidia Geforce 1070 GPU, 500GB SSD and 2TB HDD. The laptop comes pre-installed with Windows 10 and at first I simply installed my favourite data science tools, such as Anaconda and TensorFlow (with GPU support), but there comes a time when you want to use some tools that are only available for Linux. In particular, I want to run CUDA powered Nvidia-Docker containers, which requires a Linux OS and direct access to a GPU. Since it is not possible to create a virtual machine with GPU passthrough on Windows 10 (unlike Windows Server 2016, which supports Direct Device Assignment, but I haven’t tested that) this requires a bare-metal installation of a Linux host.

On the other hand, the laptop has a bunch of fancy gaming features, such as an RGB-lit keyboard and some extra software for recording game videos. I have to admit I haven’t used many of those features, but it somehow feels wrong to simply throw them all away. That’s why I chose to set up a dual boot system, instead of going straight for the “Clean installation of Windows in a virtual machine on a Linux host” solution.

Preparing Windows for dual boot

Before installing Linux, you’ll have to make some modifications to your Windows installation.

First of all, you should turn off Fast Startup from the Power Options.

Also, you will have to make space on your hard drive. Normally you can do this by shrinking the partition on which Windows is installed. I used the Windows disk management tool to shrink the C-drive partition by about one third (about 150 GB).

During the installation of Kubuntu I manually created partitions for my Linux installation in the freed-up space. I created one partition of about 30 GB to mount the root, /, and one with the remaining space (about 120 GB) to mount /home.
Keep in mind: if you plan to use Docker a lot, it can easily take up a lot of storage. By default Docker uses /var/lib/docker for storage, which in my case falls under the root / partition, so either make sure your partition is large enough, or be prepared to move the Docker storage to another partition.

Selecting a Linux distribution

When you’re installing Linux, one of the first questions to ask, is “which distribution?” I don’t consider myself an expert on this (I have some experience with Arch Linux, Ubuntu and CentOS) so I won’t attempt to give you any advice here. I chose Kubuntu (specifically, 16.04 LTS), a variation of Ubuntu that has KDE Plasma included, because there is a lot of documentation and there are many blogs and tutorials covering all aspects of Ubuntu. Furthermore, I like the way the Plasma desktop looks.

UEFI

When setting up a dual boot system, you have to make a choice between UEFI and BIOS to boot your system. My pre-installed laptop uses UEFI, the modern day standard, and I expected (hoped) it would be less work to simply stick with it. As it turns out, when installing Linux besides Windows, I got the impression that UEFI adds an extra layer of separation — the Windows boot manager and GRUB (default boot manager for Ubuntu) can coexist on separate partitions, so if I messed something up with Linux, I probably wouldn’t have wrecked my Windows installation at the same time.

Installing Linux (and configuring ACPI)

I installed Kubuntu by downloading an ISO image of Kubuntu 16.04 LTS and copying it to as USB stick using Rufus (I had to use dd-mode to be able to boot from the USB). I have tried a lot of different distributions, since I couldn’t get the installers to work properly and set up a bootable system afterwards. As it turns out, there was a simple modification I needed to make to the boot loader for my system to work properly.

The Advanced Configuration and Power Interface (ACPI) is used to perform power management. Using the default boot configuration for ACPI completely messed up my machine, but by adding a simple acpi_osi=Linux to the boot line, all these problems vanished like snow before the sun. You can do it manually once when booting the installer from the USB stick, and set this up permanently for your installed system — see Ask Ubuntu for instructions on how to do this:

For the permanent solution, edit the file /etc/default/grub, and find the line starting with GRUB_CMDLINE_LINUX_DEFAULT and append acpi_osi=Linux to the end, for example:

GRUB_CMDLINE_LINUX_DEFAULT="quiet splash acpi_osi=Linux"

Save the file and run

sudo update-grub

Reboot, and you can check your changes were processed by running cat /proc/cmdline.

If, after installing Linux, your computer boots directly into Windows without showing you the GRUB bootloader, check your BIOS settings and make sure that the UEFI boot order of your hard disk is set to load Linux first and Windows second.

Time

In their standard configuration, Windows and Linux work differently with the hardware clock. Windows uses local time, while Linux uses UTC time. When you switch from one to the other, this can lead to your time settings getting messed up. The easiest solution is to have Linux work with the hardware clock in local time:

timedatectl set-local-rtc 1 --adjust-system-clock

Encryption

On the preinstalled Windows I have set up BitLocker to encrypt my hard drives. Ideally, I would like to have a partition on my SSD for Windows (NTFS, BitLocker encrypted), another partition on my SSD for Linux (e.g. ext4, with encrypted home dir), and a shared data partition on my HDD. I originally used BitLocker to encrypt my data partition (formatted with NTFS), so I hoped to be able to use that from my Linux installation as well. As it turns out, even though many people warn to be cautious about using NTFS from Linux, this is very well possible using a tool called Dislocker. So far, I have not yet experienced any problems.

Under Kubuntu I am mounting my NTFS data drive manually with a simple script I created. There are two steps to mounting the NTFS drive. In the first step, the drive gets decrypted using the recovery key you specify. If you are saving this key in a script or in your /etc/fstab, make sure these files are properly encrypted, or anyone can use them to decrypt your BitLocker encrypted drive! The second step mounts the decrypted dislocker-file as a folder on your system.

sudo dislocker -r -V /dev/<DEVICE> -p<KEY> -- /mnt/dislocker/<NAME>
sudo mount -o ro,loop /mnt/dislocker/<NAME>/dislocker-file /mnt/<NAME>

You’ll have to replace <DEVICE>, <KEY> and <NAME> with your own values. If you want to be able to write into the NTFS drive, simply remove the read-only options ( -r and ro,). To unmount the drive, I use the following script:

sudo umount /mnt/data
sudo umount /mnt/dislocker/data

Conclusion

Starting with a laptop that came pre-installed with Windows 10, I have set up a dual boot system with Kubuntu 16.04 LTS. On Linux I can run GPU-powered machine learning algorithms, such as those using TensorFlow, using Nvidia-Docker, while using the Intel GPU for displaying the desktop. When I need to use Microsoft Office (Word, Excel, PowerPoint) I can reboot into Windows. To give me maximum virtualisation flexibility, I have now also set up my Linux system to run virtual machines, but without GPU-passthrough. Two websites to help you get started with virtual machines: the Ubuntu community and LinuxConfig.org. I hope my experiences help you avoid some of the pitfalls I fell into!


Continue with: GPU Machine Learning on Linux (using Nvidia-Docker)


About the author

Erik Jan de Vries is a data scientist at BigData Republic, a data science consultancy company in the Netherlands. We hire the best of the best in BigData Science and BigData Engineering. If you are interested in deploying machine learning and deep learning solutions in production using Docker and Kubernetes, feel free to contact us at info@bigdatarepublic.nl.