ARM Chromebook Linux Install



Table of Contents

UPDATES

Update on Feb 16 2015 This will probably be my last ever update on the ARM chromebook, which I now consider a big mistake on my part. I switched to an intel machine that works so much better with linux. Everything worked out-of-the-box or with a little minor tweaking. I will never go back to an ARM machine again. Here is a list of things that frustrated me with the ARM chromebook, and now work flawlessly with an Acer chromebook.

  • I can chat using google talk, and make video calls using skype and google hangouts
  • I can watch flash video online when I need to unwind.
  • Dropbox works natively; this is a large part of my work. I no longer want to run unison and rsync using cronjobs. This is great for backup, but its not like having a simple efficient syncing daemon that I do need to worry about.
  • Netflix works on google chrome
  • Pulseaudio works pretty well too. I'm tired of the manual buggery with ALSA.
  • All my function keys work in XFCE and gnome. I did have to tweak somethings with xmodmap, but this is trivial and highly customizable. A modern alternative to xmodmap is xbindkeys.

Update from 2014 I tried the crouton chroot environment, and it works really well. However, if you want your own clean complete Ubuntu desktop, with all the customizability it brings with it, a chroot isn't sufficient.

One way to install your own clean Ubuntu desktop is through the Chrubuntu script, which has become fairly sophisticated and installs several different flavors and releases of Xubuntu, Lubuntu and Ubuntu desktop. I highly recommend it.

However, there are many things that it does not do, which includes setting up your keyboard, user accounts, customizing your touchpad and configuring sound. If you're interested in learning a little bit about how all of this --including bits of the Chrubuntu script-- works, my guide may be of some use to you. If not, just use Chrubuntu.

Introduction

My Dell XPS M1210 died after 5 or 6 years of use. It had a shitty battery and power cable, both of which I replaced under warranty. Then, they failed again. It had served me well. I had a few simple requirements for a new laptop:

  • Portability: I knew that I would be traveling by bus and train a lot, so I needed something very light that I could put in my backpack and forget about. This translates to a max weight of about 2lbs.
  • Battery Life: If there’s one thing that’s very annoying, it’s a computer that needs to be plugged in every few hours. Trust me, this is critical. You’re not going to be near a power outlet all the time, even in a university building. I would estimate my minimum requirement to be about 5-6 hours of battery life under light (no video, audio) use.

  • Cost: I was willing to spend up to $500, but would prefer to spend less. I was not willing to sacrifice warranty and peace of mind.

  • Operating System: A full-fledged operating system is key, and I’m most comfortable with linux. I do recognize that it’s an extremely tiresome operating system, and that it’s not for everyone.

  • Keyboard: I knew that I would be using my laptop for fairly long periods while on the move. A good keyboard was, erm… key.

  • Storage: I needed about 1-2GB of personal storage in addition to space for the operating system. I didn’t expect to be doing serious computing on my laptop, and neither did I plan to store a lot of music on it. UPDATE Aug 31 2014: This turned out to be wrong. I programmed in python, ran simulations, compiled LaTeX code; essentially, my laptop became my primary computing machine.

  • Computing Power: A powerful CPU is only necessary if you’re doing things that need a powerful CPU. I wasn’t going to be doing that. Light web browsing and LaTeX composition, and not very processor intensive tasks. That said, flash-heavy websites and streaming video run better with a fast processor.

  • Output ports: I needed VGA output, preferably, since most projectors have only VGA input.

So, I was mostly looking for a decent piece of hardware to install linux on.
There were several computers I considered:

  1. Samsung Series 5 Chromebook, Old version: This had a nice snappy Intel processor, 4GB of memory, 16GB of hard disk space, and a nice keyboard that reviews raved about. Cost, about $400. People complained about the build quality, though.
  • Samsung Series 5 Chromebook, New version: This had slightly better specs and build quality than the older series 5 version.

  • Samsung ARM chromebook (ARM CB): This was built on an ARM processor, had a 11" screen, was only $250, and had a 16GB SSD. This was quite a strong contender from the beginning.

  • Acer Chromebook: This had a 350GB conventional platter based hard
    drive, an Intel processor, and otherwise similar specifications to
    the Samsungs.

  • Used Macbook Air 11’’ or 13’’: You can get a decent one for about $350 - $500 on Craigslist, but they’re usually about a year old, and the warranty doesn’t transfer. And god knows in what shape they’d be in and whether they'd fail in a few months.

  • Asus Vivo book, Lenovo Idea pad and others. Some of these were decent pieces of hardware in the $400 - $600 range.

  • The most difficult choice was between the Acer and the ARM CBs, and a visit to Best Buy settled this. The ARM CB’s keyboard felt much better, and it felt less "plasticky". Nevertheless, it seemed like a good choice since it satisfied most of my requirements.

    1. Portability: The ARM CB weighed about 2.2lbs, whereas the Acer weighed about 3lbs.
  • Battery Life: 6 hours of medium-to-light use on the ARM, compared to about 4 on the Acer.

  • Cost: The Acer and the ARM were $200 and $250 respectively

  • Operating System: They both ran ChromeOS. The main problem was that the ARM CB didn't have an official Ubuntu build. I would have to rely on other people building this for me.

  • Keyboard: Addressed above.

  • Storage: The Acer had 350GB to the Samsung’s pitiful 16GB, but conventional hard-drives are so much slower, noisier and ran so much hotter than solid state devices. I decided that I didn’t need much storage if I was only going to edit LaTeX files. If I really needed extra storage, I could augment it with an external SD-CARD.

  • Computing Power: Tests did show that the Acer seemed a little snappier compared to the ARM, but this was mostly on the ChromeOS. The difference was marginal and performance wasn’t really an issue for me.

  • I finally decided to go with the ARM CB.

    Why linux and not ChromeOS?

    ChromeOS is based loosely on a Gentoo Linux distribution. It has a nice slick interface, a working shell that you can access (in Developer mode), Flash, Netflix, and perhaps even HDMI output.

    However, it has some drawbacks:

    • No package management system. Ubuntu, Arch, Fedora and other linux distributions do so well because the have good package management systems. Most packages one could ever need are in the distributions repositories. Debian’s apt-get system, for example, is very good at avoiding dependency-hell.

    One could get around this by compiling everything from source, but good luck keeping track of all your libraries and programs.

    • No rootfs access: The rootfs in ChromeOS is read-only, and this makes custom configuration messy. One could do something about this, but it involves a little bit of hacking.
  • Minimal set of installed packages: ChromeOS comes with a very minimal set of installed packages. The bash shell is workable, but the version of Vim installed is very very bare bones. If you like emacs, well, tough luck.

  • So, a light minimal distribution of linux would give me exactly what I needed from the Chromebook: a package manager, an X-Windows system with a low-footprint window manager, internet access, a LaTeX distribution, and perhaps even a working Mathematica or python installation.

    Picking a Linux Distribution

    It’s best to start with a some history; a little literature review if you will. The earliest Chromebook hacks were published on the chromium.org website by a Google engineer (Bill Richardson).

    There were several other people who made guides on it, including Olof Johannson at this Google+ page, on Oct 28, 2012. He installed Ubuntu. Then came Jay Lee, who wrote a simple script that automates (in essence) the process described by Olof and Bill. Ubuntu on Chromebooks was dubbed “Chrubuntu” and erm... the rest is history. Jay Lee has started a blog at blogspot.com. ARM has also been promoting platforms using its chips, and they’ve been big on linux. An ARM engineer produced this guide. On this guide, I learnt a little about the structure of linux, that I will recount in brief.

    Linux has a pretty simple setup:

    • Kernel: This is the core that communicates with and manages the hardware. It’s a tiny little package, rarely exceeding 50MB.
  • Root-filesystem (rootfs): This is the filesystem where the root partition / is mounted as the system is booted up. Once there’s a kernel in place, you need programs that’ll communicate with the kernel and its modules to produce, for example, a gui; this is what the rootfs contains.

  • The contents of the rootfs vary from distribution to distribution, and typically contain a set of programs and utilities that will help get the system to a minimal operational state. This is how the same linux kernel can run under several different distributions.

    So one could run any distribution one pleases just by getting a copy of the appropriate rootfs. It’s important to note that kernels and root-filesystems are architecture specific. Programs built for Intel processors wouldn’t usually work on programs built for ARM CPUs. So although most linux programs are open source, they have to be compiled for the specific architecture. There are several ways of compiling a kernel and building a rootfs. However, as in life, it’s easiest if you get someone else to build the kernel and rootfs for you. For the ARM processor, the usual suspects -- Fedora, OpenSUSE, ARCH-Linux, and Ubuntu -- provide rootfs.

    I wasn’t very familiar with OpenSUSE and Fedora (although I use RedHat at work), and wanted to check out Arch-Linux at some point. Unfortunately, they only had a massive 8GB rootfs. With the OS taking up 8GB, this wouldn’t leave enough room for ChromeOS or my own files. Or so I thought. You see, the easiest way to make a copy of a working rootfs is to get it working on your own system and then use the dd command as follows:

    [code lang=bash]
    dd if=/dev/partition of=/backup-media/partition-image.img
    gzip /backup-media/partition-image.img
    [/code]

    dd makes a perfect copy of a partition, and this includes the free space in the partition. Gzip usually compresses this fairly well, and the size of the image falls in half. Perhaps I’ll try Arch the next time.

    Then, I learned that ARM and several other companies including Samsung were part of this non-profit consortium that built linux for the ARM platform. They were Ubuntu-based, and produced drivers, kernels and rootfs. They had several light rootfs that were built for specifically for systems that had minimal resources. Since the distribution was Ubuntu-based, it came with Debian’s apt package management system, which is terrific. Upgrading packages and (eventually) distributions would be a piece of cake. So I chose to go with a Linaro rootfs called ALIP, which stands for the “ARM Linux Internet Platform” built on the light LXDE window manager. It has such a light footprint that it uses only 200-300 MB of RAM and boots in less than 10 seconds. Compare this to Ubuntu’s Unity or Gnome, which will gobble up gigabytes of RAM with just a few programs running. So the choice of rootfs, at least, was clear.

    Installing Linux on the Chromebook

    Developer Mode

    To begin hacking the Chromebook, you need to put it into developer mode. This tells the ChromeOS firmware that you will be booting your own kernels, and that it shouldn’t freak out. Developer mode is initiated using what Google calls the “three finger salute”. As indicated on this chromium.org page, you do the following:

    To invoke Recovery mode, you hold down the ESC and Refresh keys and
    poke the Power button.

    Once Recovery Mode is initiated, the computer reboots and shows you a
    white screen with a warning. You need to hit

    Ctrl + D
    

    to boot the computer into Developer Mode. There is no prompt on the first splash screen that tells you, “hit Ctrl+D to get Developer mode”. You just need to know it. When in developer mode, you need to hit Ctrl+D to boot the computer every time. There’s no easy fix for this, unless you do a little more hacking: there appears a way to bypass this “verified boot” process. However, we won't get into this here.

    Once you do this, ChromeOS takes about 10 minutes to put the computer into Developer mode. This seems to erase your personal files (and importantly, the stored wireless passwords). It should show a login screen once it finishes booting.

    Partitioning the Chromebook

    The next step is to partition the Chromebook and set aside a kernel
    partition and root partition for Linux. Boot into ChromeOS, and pull up
    the virtual terminal by hitting

    Ctrl+Alt+F1
    

    this should get you to a root prompt. ChromeOS appears to have the following users: root, chronos, guest. One can choose to add more. The chronos user is the one the gui runs under, and it has a home directory that you can put things into (/home/users/chronos). As root, run:

    cgpt show /dev/mmcblk0
    

    which results in a display of the form

    start        size    part  contents
    

    0 1 PMBR (Boot GUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx)
    1 1 Pri GPT header
    2 32 Pri GPT table
    282624 3194880 1 Label: "STATE"
    Type: Linux data
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    20480 32768 2 Label: "KERN-A"
    Type: ChromeOS kernel
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    Attr: priority=3 tries=0 successful=1
    26578944 4194304 3 Label: "ROOT-A"
    Type: ChromeOS rootfs
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    53248 32768 4 Label: "KERN-B"
    Type: ChromeOS kernel
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    Attr: priority=1 tries=6 successful=0
    22384640 4194304 5 Label: "ROOT-B"
    Type: ChromeOS rootfs
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    3477504 32768 6 Label: "KERN-C"
    Type: ChromeOS kernel
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    Attr: priority=5 tries=2 successful=1
    3510272 18874368 7 Label: "ROOT-C"
    Type: ChromeOS rootfs
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    86016 32768 8 Label: "OEM"
    Type: Linux data
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    16450 1 9 Label: "reserved"
    Type: ChromeOS reserved
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    16451 1 10 Label: "reserved"
    Type: ChromeOS reserved
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    64 16384 11 Label: "RWFW"
    Type: ChromeOS firmware
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    249856 32768 12 Label: "EFI-SYSTEM"
    Type: EFI System Partition
    UUID: xxxx-xxxx-xxxx-xxxxxxxxxxxx
    30777311 32 Sec GPT table
    30777343 1 Sec GPT header

    I’ve replaced the GUID(s) in the above snippet with xxxs, but they'll usually be some numbers. A bootable pair of partitions is a kernel about 16MB in size (although the kernel itself is typically about 3 to 4MB), and a rootfs that’s fairly large. The sizes are in units of sectors, and for the (current) Chromebook EMMCs, we know 1 sec = 512 bytes. Originally, all the root partitions were at 2GB, and the partition labeled stateful was about 10GB. The stateful partition is where ChromeOS keeps it’s user specific files, and if you want to give ChromeOS a little room to breathe, resize this to 1GB and resize ROOT-C to 9GB. You’re going to install the rootfs in ROOT-C, and the kernel in KERN-C. There are two options for you here:

    1. Steal the part of the Chrubuntu script that does this for you - it’s fairly straight forward to edit it. The Chrubuntu script gives you a 9GB ROOT-C. We will describe how to do this below.
  • Resize the partition using a utility like cgpt or partx that’s already on the Chromebook. Both these utilities are on the sucky side of things, since you’ll have to muck about with sector sizes. If you want to do the partitioning yourself, there are plenty of resources on the internet.

  • We will describe option 1: Open up the file 34v87, and scroll down to the part where there are a bunch of cgpt statements involving ROOT-C and KERN-C. You can comment out the rest of the script,
    with statements like

    [code lang=bash]
    if [ ! -d /mnt/stateful_partition/ubuntu ]
    then
    mkdir
    fi
    [/code]

    and then run it using

    sudo bash 34v87
    

    The system should display

    Your system is repairing itself
    

    In a few minutes, it ought to reboot. Once you reboot, you have to make a filesystem on the newly resized rootfs partition. You do this after logging in as root with

    mkfs.ext4 /dev/mmcblk0p7
    

    Copying a rootfs image

    I chose to use a Linaro ALIP image, but you can use anything you like. The one I used can be found here at linaro.org. I copied it onto a USB thumb drive. Download it using wget:

    wget http://releases.linaro.org/12.11/ubuntu/precise-images/alip/linaro-precise-alip-20121124-519.tar.gz -O /media/usb_drive/image.tar.gz
    

    where /media/usb_drive/image.tar.gz is where your usb drive is mounted. Now you have to copy the files from the USB drive onto the internal EMMC. So mount the ROOT-C partition with

    mkdir /mnt/rootc
    mount /dev/mmcblkp7 /mnt/rootc
    

    It’s important to preserve permissions when you copy your files. So
    untar carefully with

    cd /mnt/rootc
    tar zxvfp /media/usb_drive/images.tar.gz
    

    I once faced a problem where it wouldn't boot because there was no proc directory on my filesystem backup. This is easily fixed by creating the directory.

    Copy kernel and its modules

    There are a few options for the kernel. Bill Richardson’s post covers the options: you can copy ChromeOS’s kernel, firmware and modules, build your own from source or use a standard Ubuntu kernel but modify the ChromeOS boot process. The ChromeOS boot process uses initramfs, whereas Ubuntu requires initrd. Wikipedia’s page on initrd says:

    In computing, initrd (initial ramdisk) is a scheme for loading a
    temporary root file system into memory in the boot process of the
    Linux kernel. initrd and initramfs refer to two different methods of
    achieving this. Both are commonly used to make preparations before the
    real root file system can be mounted.

    Compiling a kernel on your own is time consuming. Since the objective is to get a light linux system running quickly, we’ll copy the ChromeOS kernel over. To get a kernel running, you need to configure it to boot the right rootfs (/dev/mmcblk0p7 for us), and that’s the reason why you cannot simply use

    dd if=/dev/mmcblk0p2 of=/dev/mmcblk0p6
    

    First, Save the a new kernel configuration with

    echo "console=tty1 debug verbose root=/dev/mmcblk0p7 rootwait rw lsm.module_locking=0" > config
    

    Note that the original kernel configuration that Bill Richardson used
    included a bunch of options like

    console=tty1 init=/sbin/init add_efi_memmap boot=local rootwait ro noresume noswap i915.modeset=1 loglevel=7 kern_guid=%U tpm_tis.force=1 tpm_tis.interrupts=0 root=/dev/sda7 noinitrd
    

    but some of these are either equivalent or not necessary. It’s important to note that if you want to use swap, you must explicitly enable it here, in the kernel options. I don’t use much ram for the OS, and rarely require swap. However, a swap partition (or a swapfile) is necessary for hibernation. Suspend causes your battery to drain and so if you put it to sleep overnight, it will leave your computer dead in the morning. However, the swap space needs to be at least as 2GB, since this is the amount of RAM the Chromebook has! This isn’t a problem since our linux install will take only about 1.5-2GB of space. You might need to leave some room for your personal files and music. So you could choose to have your swap partition in an SDCARD.

    I chose not to enable swap for the following reasons:

    1. My light Xfce based setup boots in about 8 seconds.
  • Xfce has a “save your current session” option: Enabling this opens up the programs you had open in the previous session. This works as well as hibernation for me.

  • We now need to repack the kernel blob, and this is achieved using a
    utility called vbutil:

    [code lang=bash]
    vbutil_kernel \
    --pack newkern \
    --keyblock /usr/share/vboot/devkeys/kernel.keyblock \
    --version 1 \
    --signprivate /usr/share/vboot/devkeys/kernel_data_key.vbprivk \
    --config config \
    --vmlinuz /boot/vmlinuz-`uname -r` \
    --arch arm
    [/code]

    This “signs” the kernel, telling the ChromeOS firmware that the kernel is safe to boot. This process appears to be called “self-signing” your kernel, and ChromeOS allows you to boot such kernels only in developer mode!

    The kernel is in a file called newkern and this needs to be written to the KERN-C partition. This is done easily with a dd command:

    dd if=newkern of=/dev/mmcblk0p#
    

    where # is the number of the kernel partition KERN-C. Recall that you can find this out using the cgpt command. The copying process should take just a couple of seconds.

    UPDATE Aug 31 2014: On newer chromebooks, this does not work.
    They have done away with the /boot folder, and only the kernel partition remains. Instead of the --vmlinuz clause, we have

    --oldblob 
    

    However, I've not been able to look into what goes here. Simply dding the kernel from KERN-A or KERN-B does not work. It seems this is handled differently now but its handled correctly by the chrubuntu script has become fairly sophisticated. If you want to figure out how to do it yourself, read the chrubuntu script.

    You now need to tell the ChromeOS firmware that KERN-C has the highest priority, and it must be booted first. For future use, it’s best to make a file called boot_linux_first, and copy the following code into it

    # make linux bootable
      sudo cgpt add -i 2 -P 3 -T 1 /dev/mmcblk0
      sudo cgpt add -i 6 -P 5 -T 1 /dev/mmcblk0
    
    # now show status
      sudo cgpt show -i 2 /dev/mmcblk0
      sudo cgpt show -i 6 /dev/mmcblk0
    

    and make the file executable. The cgpt command takes the partition
    number in the -i clause, gives it a priority (higher is booted
    earlier) given by the -P clause and tells the firmware to
    (presumably) try booting the partition -T times. Replace 2 and 6
    with the numbers appropriate to your system. The options are:

    Option What it does
    i partition number
    P priority value, highest is first
    S successful, whether boot is successful or not. I don’t really know what this option does. If you set it to 0, and the current kernel fails to boot, it will try other the kernels with lower priority.
    T number of times to try booting.

    The next step is to copy over the kernel and firmware modules. Assuming
    your linux rootfs is mounted at /mnt/rootc, run

    sudo cp -prv /lib/modules /mnt/rootc/lib/modules
    sudo cp -prv /lib/firmware /mnt/rootc/lib/firmware
    

    One utility that’s extremely useful is cgpt, and this will help you boot
    into ChromeOS later:

    cp -pv /usr/bin/cgpt /mnt/rootc/usr/bin/
    

    Now it’s time to reboot into your new linux system. Type:

    sudo reboot
    

    Making things work in Linux

    If everything went well, you should be booted into a linux desktop. Since I chose the Linaro ALIP tarball, my instructions will be for that system. There are several things to fix. And we will explore this section by section.

    Users, Groups and Hostname

    The Linaro rootfs has a default user called linaro with the default password linaro. You should remove this user and create one of your own with a strong password. Before deleting the Linaro user, there are a couple of things you must do: First, the Linaro user is a part of several groups, and the new user you create should belong to all these groups if you want to use the Xwindows, login to networks, and use the sound card. Second, the LXDE system is set to login the Linaro user automatically, and you need to switch this to your new user.

    We will be saving a lot of configurations and backups. So create an easy-to-find location that you will not accidentally delete. Let’s do this first. Open a terminal, and open up a sudo shell with

    sudo -s
    

    Then,

    [code lang=text]
    mkdir -p /backup/
    chmod 777 /backup/
    [/code]

    To list the groups the linaro user belongs to, type

    groups linaro > /backup/groups-linaro.txt; cat /backup/groups-linaro.txt
    

    This saves it to a file if you forget, and the cat statement lists the content of the file. The next command creates a user called myusername that belongs to all the groups the linaro user belonged to:

    useradd myusername -m -G`cat /backup/groups-linaro.txt | sed 's/linaro : linaro //' | sed 's/ /,/g'` 
    

    Then, create a password with

    passwd myusername
    

    Remember, the new user you create had better be in the sudoers list. To see if everything worked, use the groups command again. To append a user to the another group, use

    usermod myusername -a -Gsudo
    

    You can see if the user was correctly added with:

    id myusername
    

    You may also change your login shell to bash with:

    usermod myusername -s/bin/bash
    

    And do a test login with

    login myusername
    

    to see if everything works. An interesting tip that worked well for me was to make the uid and gid of my user the same as the uid and gid of the chronos user on the ChromeOS side. This way, my files were more easily accessible from both sides.

    Next, you need to edit the lightdm login manager configuration file at
    /etc/lightdm/lightdm.conf. Change the autologin line (or remove it
    completely) in the file:

    [SeatDefaults]
    greeter-session=lightdm-gtk-greeter
    user-session=LXDE
    autologin-user=linaro
    

    You should also customize your hostname. List the current hostname with

    hostname
    

    Change the hostname by editing the file /etc/hostname, and then run
    the hostname init script:

    /etc/init.d/hostname
    

    Now you can reboot the system, and if everything worked, delete the
    linaro user:

    userdel -r linaro
    

    A new window manager

    Some research online shows that although LXDE is a light, speedy desktop environment, it’s relatively new and has its issues. So I decided to go with the XFCE desktop environment, which has been around for a while. There are many ways to install this, and one is to just install the Xubuntu package from the ubuntu repositories:

    aptitude install xubuntu-desktop
    

    There are several packages that are essential for any xfce system.
    Make sure that they’re installed:

    • xfce4-mount-plugin
  • xfce-volumed

  • xfce4-panel

  • xfce4-mixer

  • xfce4-datetime

  • xfce4-battery-plugin

  • squeeze or file-roller: archive managers

  • Mounting the chrome partition

    Some configuration files must be copied from the chrome rootfs. Note that it’s a read-only filesystem, and must be mounted as such:

    [code lang=text]
    mkdir -p /mnt/root3
    mount -o ro /dev/mmcblk0p3 /mnt/root3
    [/code]

    To mount it everytime you boot, you must add the partition to your /etc/fstab file. Mine looks like this:

    /dev/mmcblk0p3    /mnt/root3  ext4    user,ro     0   0   
    

    Sound

    To get the audio working, we’ve got to copy drivers from the ChromeOS side. Assuming your’ve already mounted the ChromeOS partition, run,

    [code lang=text]
    sudo cp -rv /mnt/root3/usr/share/alsa/ucm/* /usr/share/alsa/ucm
    alsaucm -c DAISY-I2S
    [/code]

    What we’ve done here is essentially copy a User Case Manager (UCM) profile for alsa. This provides a layer of abstraction for applications that want to use sound. Test your sound using

    speaker-test 
    

    If it works, you’d be lucky. Usually, the default state has to be set too. There are many devices on the sound card, and many volume settings. I tried getting it to work by manually adjusting the volume on different devices, but it didn’t work. The easiest method is to copy over the asound.state file from the ChromeOS side and incorporate it into your alsa setup:

    cp /mnt/root3/etc/asound.state /etc/asound.state
    alsactl -F -f /etc/asound.state restore
    

    where the -F option tells alsactl to force or restore as much of
    the previous state as possible. This asound.state file may or may not exist. The way to create one is to go into chromeOS, and login as root. In the chromeOS prompt, run

    sudo -s
    mkdir mmcp7 /dev/mmcblk0p7
    alsactl -f mmcp7/etc/asound.state store
    

    Then, reboot into linux, and restore using alsactl as above. This has worked several times for me.

    Alsa doesn’t mix different sounds by default; that is, if both your browser and vlc player are trying to access the sound device, only one of them will play. So you need to setup a mixer plugin in alsa, or install a sound daemon like pulseaudio. Pulseaudio does handles mixing sounds well and has a lot of functionality, but I chose to setup something simple with alsa itself. This was in keeping with our theme of “as light as possible, but no lighter”. You can setup alsa with some simple mixing functionality with an .asoundrc file. The configuration file sets up the alsa dmix plugin. Mine can be found in my dropbox.

    Touchpad

    Save the following in a file called /etc/X11/xorg.conf.d/50-touchpad.conf

    [code lang=text]
    Section "InputClass"
    identifier "touchpad"
    MatchIsTouchpad "on"
    Option "FingerHigh" "5"
    Option "FingerLow" "5
    Option "HorizTwoFingerScroll" "on"
    EndSection
    [/code]

    This enables basic Touchpad functionality. There are several things you can enable, including Circular Scrolling, which is quite cool. You can enable it with the option: Option "CircularScrolling" "on"

    Wireless

    Wireless should be working by default, unless you have to connect to a WPA2 enterprise network - this is more a linux problem than anything else. After a lot time attempting to connect to these networks, most of the errors seemed to be coming from some openssl module. You can usually connect to these by just ignoring certificates.

    Network manager works fine for me, although it occasionally used to give me some trouble with frequent disconnections. To fix this I switched to using the command-line tool wpa_supplicant and wicd, a light gui based tool. Some people prefer wicd to network manager since it's lighter.

    In the end, it turned out that I all I needed to do was to wait a few weeks until google released a new wireless driver, a new kernel module called

    mwfiex.ko
    

    Once installing this and NetworkManager, I stopped running into wireless problems.

    Java

    Sun doesn’t seem to have released Java binaries for the ARM processor. So you would have to use openjdk, and the icedtea browser plugin which runs Java applets. I installed the following:

    aptitude install openjdk-7-jre icedtea-7-plugin 
    

    Then visit the Java test page to see if everything works.

    Flash

    UPDATE Nov 02 2013 (Thanks to commenter Charles Amith): Flash works with the pepperflash plugin, but you need to run it as the superuser. Copy the pepper flash plugin from the directory

    /opt/google/chrome/pepper/libpepflashplayer.so
    

    Then, run

    sudo chromium-browser --user-data-dir=/tmp --ppapi-flash-path=/libpepflashplayer.so
    

    UPDATE: Sep 01 2014 I've again lost compatibility between the flashplugin and the chromium-browser version I have installed. Developers from the chromium forums told me the flashplugin is closely coupled to google-chrome official versions, and if they work at all with the open source chromium-browser, it's just a matter of luck. The only hope is gnash, which works well for a fair number of purposes.

    I've recounted a little bit of my struggle below.

    I struggled with flash a lot, Adobe hasn’t released a flash plugin for ARM-linux. I tried android versions of the plugin, but nothing seemed to work. However, note that flash works on the ChromeOS side. This is because the Chrome browser has a custom flash plugin called pepperflash. Several forums discussed using this with the chromium browser (the open source version of Google Chrome), which is installed by default in the Linaro rootfs. This did not work for me, but you might have better luck.

    The flash plugin is in file called libpepflashplayer.so in

    /mnt/root3/opt/google/chrome/PepperFlash/
    

    along with other files that describe the flashplayer version. After looking at the contents of pepper-flash.info to determine the version number, I ran

    chromium-browser --ppapi-flash-path=/opt/google/chrome/pepper/libpepflashplayer.so --ppapi-flash-version=11.6.602.180 --enable-plugins
    

    This gave me the error:

    [ERROR:flash/platform/pepper/pep_module.cpp(143)] Browser does not support interface PPB_AudioInput(Dev);0.3|PPB_AudioInput(Dev);0.2.
    

    and failed to load flash. Looking at the about:plugins page in the browser shows the following

    Flash - Version: 11.6.602.180
    Shockwave Flash 11.6 r602
    Name:   Shockwave Flash
    Description:    Shockwave Flash 11.6 r602
    Version:    11.6.602.180
    Location:   /opt/google/chrome/pepper/libpepflashplayer.so
    Type:   PPAPI (out-of-process)
         Disable
         MIME types:    
         MIME type  Description File extensions
         application/x-shockwave-flash  Shockwave Flash .swf
         application/futuresplash   FutureSplash Player .spl
         Disable   Allow
    

    which seems to indicate that the browser at least tried to load the plugin.

    There are other people who claim they have it working.

    • (http://www.webupd8.org/2012/09/how-to-make-chromium-use-flash-player.html)
  • (http://www.murga-linux.com/puppy/viewtopic.php?t=86021)

  • (http://code.google.com/p/chromium/issues/detail?id=171122)

  • (http://www.murga-linux.com/puppy/viewtopic.php?t=86021)

  • (https://aur.archlinux.org/packages.php?ID=60443)

  • I then tried installing the libflashplayer.so from Adobe’s website. I
    copied the libflashplayer.so file everywhere:

    /usr/lib/adobe-flashplugin/libflashplayer.so
    /usr/lib/firefox-addons/plugins/libflashplayer.so
    /usr/lib/firefox/libflashplayer.so
    /home/myusername/.mozilla/plugins/libflashplayer.so
    

    I also tried several different versions of the libflashplayer.so file: Android, i386, etc.

    In fact, if you try to copy over the chrome binary from the ChromeOS side and run it, it complains about libraries. Once you copy over the libraries, it brings up an entire ChromeOS desktop inside a window. There is a chrome browser window inside the desktop, and it crashes instantaneously. I don’t know how to call the browser alone and not the entire desktop. Perhaps this is not possible.

    In any case, HTML5 videos work quite well inside linux - this means newer videos on youtube work. Things like quicktime don’t, but one probably needs to get ARM versions of the Medibuntu driver package. I haven’t looked into this as yet.

    I finally came across the gnash package which is an open source flash implementation. It is several versions behind Adobe Flashplayer, which means that it can only run older flash based videos. I’ve tested it on several Youtube videos and it works on most of them.

    Power management

    Power management tools can be installed using

    aptitude install pm-utils
    

    This installs several utilities like pm-powersave, pm-hibernate, pm-suspend, pm-suspend-hybrid. But except for pm-suspend, the rest do not work swap enabled. As I mentioned earlier, I chose not enable swap.

    Setting keys up: xmodmap

    The keyboard isn’t setup completely in your linux Chromebook. So volume buttons and brightness buttons don’t work - they’re mapped to function keys F6 through F10. What’s even worse is that there aren’t any Home, End, PgUp, or PgDown keys. I fixed this by making some custom mappings. Since most civilized people rarely use the Caps Lock key, I mapped the Caps Lock key to Mode_switch, a special key for the XWindows system. Then one can setup the following key mappings:

    Key combination Action
    Mode switch + Up PgUp
    Mode switch + Down PgDown
    Mode switch + Left Home
    Mode switch + Right End

    and so on. This is done with the help of two programs: xmodmap and xev. First, you need to find out what your CapsLock key is mapped to. Startup xev with

    xev
    

    and a small window pops up. Hit caps lock and the program should spit out something like this:

    KeyPress event, serial 31, synthetic NO, window 0x3000001,
        root 0x101, subw 0x0, time 1626557, (77,102), root:(671,418),
        state 0x0, keycode 133 (keysym 0xff7e, Super_L), same_screen YES,
        XLookupString gives 0 bytes: 
        XmbLookupString gives 0 bytes: 
        XFilterEvent returns: False
    
    KeyRelease event, serial 34, synthetic NO, window 0x3000001,
        root 0x101, subw 0x0, time 1626689, (77,102), root:(671,418),
        state 0x2000, keycode 133 (keysym 0xff7e, Super_L), same_screen YES,
        XLookupString gives 0 bytes: 
        XFilterEvent returns: False
    

    Mine happened to be mapped to the keysym SuperL, but yours could be different. Keycodes are hardware specific, but keysyms are hardware independent. So you could remap your SuperL to modeswitch on all computers with the same code. Now, you need to print out your current keycode mappings with:

    xmodmap -pke > keymap.txt
    

    Open keymap.txt and you will see a bunch of code like this:

    keycode  67 = F1 F1 F1 F1 F1 F1 XF86Switch_VT_1 F1 F1 XF86Switch_VT_1
    keycode 110 = Home NoSymbol Home
    keycode 111 = Up NoSymbol Up
    keycode 112 = Prior NoSymbol Prior
    keycode 113 = Left NoSymbol Left
    keycode 114 = Right NoSymbol Right
    keycode 115 = End NoSymbol End
    keycode 116 = Down NoSymbol Down
    

    The structure of a keycode line is as follows:

    [code lang=text]
    keycode = <key number> = <bare keypress> <Shifted keypress> <Mode_switched keypress> <Shift+Mode_switched keypress>
    [/code]

    This describes which keysyms are called when a keycode is either bare, modified with Shift, modified with Mode_switch, or with Shift and Mode_switch pressed together. The keysyms Prior and Next stand for PgUp and PgDown respectively. So I made a file called .Xmodmap in my home directory that does the following:

    1. Exchanges the functions of Control_L and Caps_Lock (Super_L)
  • Maps Mode_switch + key to the Home, End, PageUp and PageDown buttons described above.

  • Maps Shift + F# to XF86AudioLowerVolume XF86AudioRaiseVolume XF86AudioMute, and to the similar brightness functions XF86MonBrightnessDown and XF86MonBrightnessUp to the appropriate "F" key on your chromebook keyboard. Note that if you mapped these to Mode_switch + F# key, it does not work. I do not know why.

  • My Xmodmap file can be found here

    HDMI

    HDMI works on my TV, but there is limited functionality. Look into xrandr to see how to control output. It only works sporadically for me. It does work reasonably well on the chromeos side. If you want to convert HDMI to VGA for use with a projector, this externally powered HDMI to VGA is the only one that works. Note that the cable matters so called active HDMI to VGA converter does not work. Apparently, the chromebook USB port does not supply the converter enough power, as far as I can tell. In contrast, the other Conversions Technology converter comes with its own DC power supply.

    Again, I must emphasize HDMI performance is a hit or a miss. Do not rely on it to work from the linux side until we have better drivers and software.

    In contrast, the Acer chromebook HDMI works flawlessly.

    Appendix

    • Recovering OS cost: If you choose to buy a windows laptop that you just want to install linux on, you could consider getting back the cost of windows included in the price of the laptop. This is typically about $60 for Windows 7. Several have received refunds from the manufacturer! But many fail, since you have to persistent and sit for hours on the telephone with Customer Service. I didn’t want to be bothered with this.

    • Things that don’t work: Dropbox, with their closed source binaries do not have an ARM build as yet.

    • For next time: I’d probably just install crouton, or Ubuntu with Gnome3.

    • If I had to make the choice again: Samsung ARM Chromebook versus the Acer ARM chromebook, I'd probably choose the Intel based Acer.