Installing Arch Linux with System Encryption Enabled

I still use Arch Linux because it is pretty much the only rolling-release distro that offers binary (pre-compiled) packages by default *and* only installs bare minimum packages required to get a working Linux system (no window manager, no desktop environment). I was re-installing Arch Linux on my desktop last week to set up system-wide encryption and decided to record all of the commands I used to get the bare minimum working. I am not aware of any source out there that actually tells you all of the console commands you need to run when you first install Arch Linux in plaintext format so I decided to write this post.

The system I am setting up is simple: it has only 1 hard drive. This drive has 1 boot partition 100MB big, and the rest is a single LVM partition that will eventually contain the / (aka “root”), /home, and swap partitions. This single LVM partition will be encrypted, so that when the system boots, it would require a password to unlock the /, /home, and swap partitions to actually load up the Kernel and userland.

If you are wondering why the /home partition is mounted on /mnt/home in some of the commands, this is because the Arch Linux live CD environment will load up a temporary Linux system onto your RAM, and we use the /mnt directory (again all files/folders are temporarily in your RAM) to mount the hard drive partitions. You can always use a live CD anywhere to load up a barebone Linux system to your RAM and mount the hard drives on your computer for inspection, and in such a case you will again use the /mnt directory to mount your hard drives here.

If you don’t know how to use vi (tsk, tsk), then just substitute that command with “nano” or something. Here are the commands, with comments, in plaintext format:

    # Put in the Arch Linux live CD and run the following commands...

    # Set up 2 partitions; the first one is the boot 100MB partition (be sure
    # to toggle the BOOT flag on it), and the second will be the LVM partition.
    # Be sure to select 8E for the LVM partition! You can use
    # /dev/disk/by-uuid/XXXX for more fine-grained control; use "blkid -o list"
    # to find out which drives are given which UUIDs.

    cfdisk /dev/sda

    # Now set up encryption on the LVM partition (the 2nd partition, so it's
    # /dev/sda2). It is recommended to use aes-xts-plain64 if the partition is
    # larger than 2 TB, I think.

    cryptsetup -c aes-xts-plain -y -s 512 luksFormat /dev/sda2

    # Decrypt the encrypted partition with LUKS. We need to decrypt it first
    # before setting up LVM volumes and filesystems on it. This will create
    # an entry under /dev/mapper/luks.

    cryptsetup luksOpen /dev/sda2 luks

    # Set up LVM. We call our volume group "vg0". To be honest I am not sure if
    # the "--contiguous y" option for swap matters because we are encrypting it
    # (doesn't block encryption encrypt data randomly on the disk?), but that's
    # what I found online and that's what I'll use here. The "+100%FREE" option
    # is a very handy option that tells LVM to fill up all remaining free space,
    # in this case, for the "home" logical volume.
    # Read more about LVM on your favorite online wiki.

    pvcreate /dev/mapper/luks
    vgcreate vg0 /dev/mapper/luks
    lvcreate --size 40G vg0 --name root
    lvcreate --size 2G --contiguous y vg0 --name swap
    lvcreate -l +100%FREE vg0 --name home

    # Initialize filesystems. Btrfs is still experimental, so I choose ext4
    # here. The vg0-root, vg0-home, and vg0-swap volumes should
    # appear under /dev/mapper as you create them with the lvcreate command.

    mkfs.ext4 /dev/mapper/vg0-root
    mkfs.ext4 /dev/mapper/vg0-home
    mkswap /dev/mapper/vg0-swap

    # Mount the logical volumes. Why? Because we need to install Arch Linux onto
    # it! You probably don't need to mount the "home" volume but it couldn't
    # hurt. Besides, it's nice to test that all volumes can be mounted OK anyway.

    mount /dev/mapper/vg0-root /mnt # /mnt is our system's "/" root   directory
    mkdir /mnt/home
    mount /dev/mapper/vg0-home /mnt/home
    swapon /dev/mapper/vg0-swap

    # Set up package download mirrors. The kernel mirror is generally a good one
    # if you live in the US. Google "arch linux mirror status" to find the
    # fastest mirrors.

    vi /etc/pacman.d/mirrorlist

    # Download and install the core minimum packages to get a working Linux
    # terminal (console) environment. Ah, simplicity!

    pacstrap -i /mnt base base-devel

    # Generate and inspect the filesystem tables needed when the system first
    # starts. The file should contain four "partitions" (I put them in quotes
    # because remember, we are using only 2 real partitions; 1st one is /boot and
    # the 2nd one is our LVM containing /, /home, and swap).

    genfstab -U -p /mnt >> /mnt/etc/fstab
    vi /mnt/etc/fstab

    # Make the system pretend that /mnt is /. This is called "chrooting". We need
    # to do this because some of the commands like locale-gen, systemctl, etc.
    # read configuration files from /etc, for example, and right now our /etc is
    # the /etc used by the Arch Linux live CD, not our newly-installed system's
    # root directory, /mnt.

    arch-chroot /mnt /bin/bash

    # Choose and generate locale; programs supporting internationalization (aka
    # "i18n") will use the language you pick to generate the proper text used in
    # menus, error messages, etc. Just choose "en_US.UTF-8 UTF-8" if you live in
    # the US.

    vi /etc/locale.gen
    echo LANG=en_US.UTF-8 > /etc/locale.conf

    # Choose default font used by the virtual console (the terminal screen you
    # will see when you first boot up your new Arch Linux system).

    setfont Lat2-Terminus16
    echo FONT=Lat2-Terminus16 > /etc/vconsole.conf

    # Choose timezone. Here, we tell hwclock that we want the hardware clock on
    # the motherboard to be set to UTC, which will then be interpreted as UTC
    # time by the kernel and re-adjusted to the timezone you chose when you
    # actually use the system. This is nice because UTC is the "master" time the
    # world uses anyway, so it makes sense to tell your motherboard to use it.

    ln -s /usr/share/zoneinfo/America/Los_Angeles /etc/localtime
    hwclock --systohc --utc

    # Choose your computer's name. Keep it simple, without spaces. I use "k0".

    echo MYHOSTNAME > /etc/hostname

    # Enable DHCPCD... aka "acquire dynamic ip address from your router/switch".
    # Be sure to choose the right eth0 or eth1 (eth2, if you have 3 ethernet
    # ports) port. If you choose the wrong "eth" number, just go to
    # /etc/systemd/system/ and rename the symlink; e.g.,
    # rename /etc/systemd/system/ to
    # /etc/systemd/system/

    systemctl enable dhcpcd@eth0.service

    # Disable unused package repos. You will want to disable the [testing] repo
    # unless you want to test unstable packages and engage in the package
    # debugging/development process. For Haskellers, be sure to add the
    # [haskell-core] repo (see

    vi /etc/pacman.conf

    # Set up the root user ("administrator" for you Windows people) password.


    # Install zsh, because you will like it better any other shell out there.

    pacman -S zsh

    # Add your regular user, and set up your password. This is your normal
    # username. We use the "-s /bin/zsh" option to tell useradd that we want to
    # log in with zsh.

    # useradd -m -g users -G wheel,storage,power -s /bin/zsh MYUSERNAME
    # passwd MYUSERNAME

    # VERY IMPORTANT: Add in the filesystem type that /root partition (LVM) is
    # using (for this tutorial, it is "ext4") into the MODULES variable and also
    # add 'encrypt' and 'lvm2' into HOOKS.

    vi /etc/mkinitcpio.conf

    # Re-generate the linux image to take into account the LVM and encrypt
    # flags we added into /etc/mkinitcpio.conf. I say "re-generate" because this
    # is our second time doing this (the first time was when we installed the
    # linux package with the pacstrap command above).

    mkinitcpio -p linux

    # Install boot loader. I like SYSLINUX because of the saner/easier-looking
    # boot configuration file, compared to GRUB 2. Be sure to add in
	#     "APPEND cryptdevice=/dev/disk/by-uuid/xxxxxxxxxx:luks root=/dev/mapper/vg0-root resume=/dev/mapper/vg0-swap ro"
    # under the "LABEL arch" entries, so that SYSLINUX tells the kernel to look
    # for the encrypted LVM partition. Otherwise, your system won't boot! Don't
    # forget to actually look up the UUID of your LVM partition (/dev/sda2 in
    # this tutorial). You don't need to tell the kernel about your vg0-home
    # volume because that will get mounted by /etc/fstab when it is read later in
    # the boot process.

    pacman -S syslinux
    syslinux-install_update -i -a -m
    vi /boot/syslinux/syslinux.cfg

    # Exit chroot environment.


    # Unmount volumes, and reboot. Remove your Arch Linux live CD when your
    # computer powers on again.

    umount /mnt/{boot,home}

PROTIP: Use the ALT+F2, ALT+F3, etc. shortcuts to log into and switch between different TTY screens; this is very useful when you are unsure about some of the commands used above and want to look at their manpages for more detailed explanations.

The process of installing Arch Linux is long, but arguably extremely clean and clutter-free. *EVERY* command counts, and matters. And you also get system-level encryption (everything except the /boot partition is encrypted). I would go ahead and install gvim, emacs, xmonad, and all the other little programs I use daily, but that can wait until the next reboot. And because it’s Linux, you don’t have to worry about restarting the whole system when you install new programs, so you can actually install 99% of everything you need within one session.

Arch Linux: Clean up those .pacnew and .pacsave files

Once in a while, pacman gives messages about some system config file, and the creation of either a .pacnew or .pacsave file (or sometimes a .pacorig file). The reason why this happens is because your system upgrade results in conflicting configuration files — pacman is smart enough to realize that it would be very dangerous to simply overwrite your configuration files automatically with the new ones from the newer package(s). A good example is GRUB’s menu.lst file — you certainly would NOT want to delete the old (unupgraded) one, since it holds all your valuable data about which partition to boot from, and as well as any other operating systems you use under GRUB. So, how should you take care of them — after all, the newer config files DO often contain newer settings and options.

The answer: install the yaourt package from AUR if you haven’t already. Then, issue the command yaourt -C. This will take care of all those pesky config files via an interactive shell session. Yaourt will let you view the original config file, and the .pacnew or .pacsave variant of it, using a variety of programs — including gvim and vim. I use gvim because my default colorscheme in vim is too dark for displaying the diffs properly. Simply do CTRL + W, W in normal mode to switch between the two windows (copy and paste to quickly merge long sections).

You should get in the habit of doing yaourt -C every time you encounter a message about a .pacnew or .pacsave.

Arch Linux + Xmonad

I finally got around to installing Arch on my desktop yesterday. At first I installed XFCE, and then Xmonad, and then I decided to dump XFCE altogether and just use Xmonad for all my computing needs. Xmonad is tricky to configure, so I only have a very basic xmonad.hs file (it’s the template config file found on the Xmonad wiki pages, minus the parts that give me errors on Xmonad 0.8.1).

I think tiling window managers like Xmonad are really the only way to go. I was getting sick of doing ALT+MOUSE2 to resize my windows to make most of my screen real estate on XFCE. I really like how my windows perfectly line up into neat groups. I haven’t even touched any of the great extensions out there for Xmonad yet.

In other news: I started using vimperator. It’s really neat once you spend 1 day with it. The biggest advantage for me: I don’t have to click on History -> Recently closed tabs -> tab to open up a tab I accidentally deleted. All I do instead now is just type ‘u’! And I don’t do CTRL+T, CTRL+K to do my searches — instead it’s now just ‘t searchterm’ or ‘t a packagename’ (where the ‘a’ is a keyword for the Arch Package Repository search engine). Woohoo!

UPDATE January 28, 2010: So it’s been just over 1 year since I’ve used Xmonad on Arch. Some pro’s and cons of using Xmonad:


  • Excellent use case for dual monitors — since windows instantaneously move & maximize between two (or more) monitors, the awkward feeling of seeing a window with fat monitor bezel “dividing” it up never happens. (In other words, a tiling WM makes a monitor’s bezel width irrelevant.)
  • Probably the best way to research something online while working on a problem. You can open up multiple windows and switch between them instantly. Whenever I’m researching an idea (usu. a school research project or a computer programming-related problem) I have multiple Firefox browsers maximized in various workspaces. A tiling WM + multiple workspaces (FYI, I have 22 workspaces — 1 through 0 in the horizontal numeric keys and F1 through F12) is a lot like having an “expandable” desk — if you run out of space in the current one, you just go grab the next empty one and put more stuff there. Marathon, 4, 5+ hour research/programming sessions have not resulted in my need to have more than 10 workspaces (but I still like having 22 of them).
  • You can do away with an omnipresent “status bar” for the clock, network bandwidth useage, CPU usage, etc., and instead have full-screen versions of such monitoring programs run all the time. For example, I have F12 (the 22nd workspace) set to display htop full screen, F11 to iftop and alsamixer, F10 to alpine (mail viewer), F9 to weechat (IRC), and F8 to ncmpcpp. Having many workspaces frees you from using pesky, real-estate cluttering programs like conky to keep track of your system. I don’t use any kind of status bar like dzen or xmobar whatsoever (I just don’t need to).
  • Encourages you to live in the terminal, since there are no desktop icons or menus. In the course of a year I’ve learned some very useful console commands, and it’s made me appreciate more of the GNU in GNU/Linux.
  • The tiling environment is probably the best one for doing computer programming — it’s easy to instantly launch a new terminal right below your current window to test the binary/script you just compiled/wrote.
  • Xmonad has never crashed on me. (It’s come somewhat close to crashing in cases where I tried to run some PC games over WINE, when the game wanted to change to a different full-screen resolution (yuck) than the one already set by (one of my) monitors. But it’s never crashed.) I’ve never experienced my mouse not responding or my Xmonad workspace-switching hotkeys failing on me. It’s never crashed. Ever.


  • In the early days of Xmonad (v. 0.8.1), updates to GHC would sometimes break Xmonad’s configuration files. Xmonad would start and function normally, but changes to the ~/.xmonad/xmonad.hs configuration file would not be recognized by Xmonad. However, this had to do with Arch’s packaging process and the lack of synchronization between Arch’s packages and the Haskell community. I haven’t experienced any significant problems at all since v.0.9.1 came out, so, this is a non-issue.
  • Some windows are naturally designed to “float” (not become maximized and tiled), especially small apps like galculator or agave. Such apps have to be manually configured to float every time in your xmonad.hs config file. Doing so requires that you use the “xprop” command and parse everything manually — a bit annoying each time you do it, but thankfully after 20 or so of these customizations you won’t have to be bothered with this for a good while.
  • To make most out of a tiling WM, you will have to learn to live in the terminal. That means knowing your ~/.zshrc or ~/.bashrc intimately well, and coordinating your shell aliases to work well with Xmonad (e.g., like how I have “of” aliased to “sudo poweroff” — or how I have “usbon” aliased to “sudo mount -w -t vfat -o uid=shinobu,gid=shinobu /dev/sdc1 /mnt/media-flash”). I even had to make a custom ZSH function called univ_open() to satisfy my needs. And because everything in Xmonad is heavily keyboard-shortcut-driven, use of the mouse becomes somewhat annoying. Thus I keep getting annoyed by things that are mouse-centric, like any app, or even galculator to a degree. But even if I could do everything from the keyboard, the problem is that many programs do not allow you to easily change the default key bindings — such as apvlv, mirage, alpine, htop, iftop, alsamixer, rtorrent, etc. You have to learn the different key bindings for all these programs.

Pros or cons depending on whether you are a geek:

  • Since there is no status bar or task tray like GNOME/KDE/etc., that means that you have to figure out how to access very low-level stuff manually. These are things like setting the volume, changing the monitor brightness, sleeping or shutting the computer off, mounting/unmounting USB devices and CD/DVD media. Thus, I have to have Xmonad hotkeys to lower/raise/mute the volume and change the brightness (for my laptops). To turn the computer off, I have “of” bound to “sudo poweroff” and “ofo” bound to “sudo reboot” (I had to learn these console commands online — as they are distro-specific).  Unless you’re a geek like me, you’re going to have a hard time trying to get everything working smoothly. (Another example of something I had to learn online: I have to type “& disown” after typing up a command to start up a GUI, since otherwise my current terminal can’t do anything until the GUI app is exited.) I had to learn commands like ssh, du, df, mount, and umount to get all the information/functionality I’d expect from a regular DE like GNOME. On the other hand, learning these commands have made me work faster and better than ever. So in short, if you’re a geek, a tiling WM helps you learn more essential UNIX-y commands, but if you’re a regular average Joe, a tiling WM is probably not what you want.
  • Customizing Xmonad is somewhat of a challenge at first. It helps if you know some Haskell (only after learning what Haskell lists are did I add 13 more workspaces to the default 9, while still maintaining the mod + key and mod + shift + key functionality to those 13 new windows, in the way the keys are physically lined up on the keyboard (i.e., the ‘0’ key is mapped to workspace 10, not 1)). Unfortunately, there are so many ways that you can slice Xmonad — much like the task of customizing your ~/.vimrc or your ~/.zshrc. If you’re a geek, you’ll enjoy taking small steps to add additional functionality here and there as you go along. But for the average computer user, customizing everything to your liking will be difficult.

Overall though, I am glad I made the switch to a tiling WM. Whenever I find myself sitting in front of a non-tiling WM, I shudder to think of how I used to do all my work (internet-based research, especially, with all those overlapping windows!). I cannot imagine doing any real work without a tiling WM. The only use case I’ve not really done any serious testing with Xmonad is digital content creation — i.e., using GIMP or Blender for digital multimedia work. GIMP is currently awkward to use on Xmonad because of the default floating windows (the 3 that start up by default, plus the many floating dialog boxes). Blender currently does not support multiple monitors, so dual-head setups like mine suffer from it. However, the next GIMP version (2.8) is supposed to support single-window mode. And Blender 2.6 is supposed to support multiple monitors. So things are only going to get better with Xmonad/tiling WMs.

UPDATE June 16, 2010: Here are some more reasons why using a tiling WM (Xmonad in my case) is so great:

  • A better IDE: Because Xmonad is a tiling WM, you make constant use of the keyboard to move around various windows. This means that, suddenly, everything on your workspace becomes “unified” by Xmonad. For example, I remember using Netbeans once when I started programming again a few years ago. I remember the various features of that IDE, such as a file browser, build window, etc. I’ve since switched to Vim for editing any text file, and have realized that with Xmonad, my entire workspace is my IDE! I just create one window for Vim, a terminal for file browsing (any shell, when used intelligently with enough super-concise aliases and shell expansion, beats using a dedicated file browser program) and general-purpose file navigation (with the ack and find commands), another terminal for compiling, another terminal (or two or three) for irb or ghci if I’m working with Ruby or Haskell, a Firefox window for viewing online help (documentation, API, etc.), a PDF-viewer for that interesting computer science article, maybe another window for a calculator (perhaps on a different workspace)… and now, all the various windows serve a distinct purpose. Everything comes together nicely to make to create an evolving IDE. Every time I sit down to do some fun programming projects in my free time, I create only those parts of the IDE that I need. Nothing is wasted. Again, the fact that I can switch between all the various windows (and resize them to emphasize the important ones — Xmonad does this with “layouts” which can be customized) with a single unified set of hotkeys defined by Xmonad’s configuration file makes it all work seamlessly. No more pressing F5 to execute some elongated, intra-(Netbeans, Eclipse, etc.)-compile command — I just move to the compile-dedicated terminal window and press UP for the last build command) and ENTER to do the same thing, but better because nothing separates you from the compiler.
  • Universal access to various “function” keys: The so-called “mod key” that you will come to love and which Xmonad makes extensive use of (you can define multiple mod keys, btw), is always interpreted first by Xmonad, regardless of which workspace you are in or what window you are currently focused on. This is true even for full-screened windows (e.g., mplayer). This means that you can essentially roll your own set of “function” keys to control the volume, screen brightness, and audio player (mpd, in my case). Here’s a snippet of code from my xmonad.hs for this task:

    — ncmpcpp (mpd) controls
    , ((mod4Mask .|. controlMask, xK_o     ), spawn “ncmpcpp toggle”)
    , ((mod4Mask .|. controlMask, xK_h     ), spawn “ncmpcpp stop; ncmpcpp play”) — “reset” current song to beginning
    , ((mod4Mask .|. controlMask, xK_j     ), spawn “ncmpcpp next”)
    , ((mod4Mask .|. controlMask, xK_k     ), spawn “ncmpcpp prev”)
    , ((mod4Mask .|. controlMask, xK_l     ), spawn “ncmpcpp stop”)
    , ((mod4Mask .|. controlMask, xK_semicolon ), spawn “ncmpcpp play”)
    — volume controls
    , ((modm              , xK_backslash ), spawn “amixer -q set Master toggle”)
    , ((modm              , xK_minus     ), spawn “amixer -q set Master 3- unmute”)
    , ((modm              , xK_equal     ), spawn “amixer -q set Master 3+ unmute”)
    — screen brightness (call the script “~/syscfg/shellscripts/sys/”, which is symlinked to /usr/bin/brightness to toggle screen brightness — entry for this in “sudo visudo” allows us to do it as sudo w/o password prompt)
    , ((modm     .|. shiftMask, xK_backslash ), spawn “sudo brightness”) — toggle brightness (100 or 0)

    Since my Xmonad config is spread out across all my personal systems, I have essentially created “unified” hotkeys. Now, the fact that I use different keyboards with different keys, different multimedia keys, etc. does not matter any more, as my Xmonad config file ensures that, at least for mpd, volume, and screen brightness, I can always rely on the same hotkeys to manipulate them. This is a godsend for those pesky multimedia keys on laptops which are usually quirky and don’t always work (and worst of all, are located in different places on different laptop models, if at all). Notice that all of the above commands to change mpd state, volume, and brightness do not produce any screen noise; everything is done silently so that you can focus on what’s important (the movie playing full-screen, the article you’re reading, the code you’re reviewing, and so on). You can see how I’ve mapped the ncmpcpp commands close to the “home row” of keys for extra convenience. All of this is made possible by Xmonad’s straightforward, no-frills keybindings (good luck syncing your keybindings from XFCE/GNOME/KDE/any-other-bloated-DE across your systems). (Btw, the script is a custom zsh script that I’ve written myself — you will find it in my post here.)

Update April 19, 2011: I use pentadactyl instead of vimperator now, as I noted a while ago in this post. Anyway, I’m still using Xmonad! Since learning Haskell earlier this year, I’ve managed to customize my configuration file quite a bit. If you know Haskell, then choosing Xmonad is a no-brainer; the xmonad.hs configuration file is a Haskell source file that is used as a top-level file which pulls in all the necessary Xmonad dependencies to generate the xmonad executable! This means that you can do pretty much anything you want with Xmonad. The cool thing about customizing xmonad.hs is that, even if it gets very complex, the generated xmonad executable will still be rock-solid (unless you shoot yourself in the foot doing stupid things, which is very hard to do in Haskell). This is in sharp contrast to other programs where extensive customization generally leads to less stability. Oh, and Xmonad still hasn’t crashed on me since I started using it.