An Engineer's take on Chrome OS


I recently switched to using a Chromebook Pixel as my primary device, for both personal and work tasks. Having mentioned this on Twitter, quite a few people asked me to elaborate on my experiences as the Pixel is an enticing device and Chrome OS is largely unknown to many people. Professionally, I am an Systems/Infrastructure/Devops Engineer and my tools mostly consist of a terminal and a browser. I do not generally spend a lot of time in Photoshop, AutoCAD, or Eclipse. If I were a heavy user of such an app, I'd seriously reconsider switching to Chrome OS.

I'm going to focus on Chrome OS in this post, as several other blogs and sites have done in-depth reviews of the Pixel hardware, but I did notice a few things that other reviews seem to have glossed over...

The Pixel is easily one of the best laptops I've ever owned. Coming from a 13" Macbook Air, the size is roughly the same (a bit different due to the 3:2 aspect ratio), it doesn't weigh too much, the battery lasts just about as long, and the display is unbelievably pretty. The top-row of "function" keys are harder to press and have less travel than the rest of the keyboard, with the Esc key being the most annoying for a heavy vim user. The only Apple-patented feature I miss is the magsafe adapter. The barrel plug with the Pixel has a tendency to come loose a bit too easy, but is otherwise acceptable. Overall, it's an incredibly solid feeling device that lacks the cheap plasticy feel of most PCs.

Immediately after I ordered the Chromebook Pixel, I spent some time cleaning up my Google account and switched to an all-Chrome based workflow on my Macbook Air. I had cycled through an Google Apps email, Gmail, and a Google-independent email address over the years, all of which had separate Google accounts. An hour of futzing around with various settings and verifying addresses, I had everything on one unified account. I have a feeling that if I hadn't taken the time to do this, my experience would've involved quite a bit more pain as *everything* on Chrome OS is tied to your Google account.

Upon opening the Pixel, I was greeted with a relatively simple setup wizard that involved connecting to my wireless network (which worked on the second try, dunno why it didn't work the first time), waiting about five minutes for updates to download and install, then logging into my Google account. Once logged in, I was greeted with a set of animations and videos demonstrating basic features of the OS and hardware. The most striking of these demos was "TimeScapes", an HD video that showed off the color depth and resolution of the Pixel's display. Sadly, this is a rare experience. Once you open a Chrome browser, everything you see is scaled to 2x resolution, similar to the way the retina iPad and Macbooks. Type and vector graphics are rendered natively and have nice sharp edges, but most images and videos are disappointingly blurry. I'm sure this will improve in time, as more people own high DPI devices and bandwidth available to the average user increases. Until then, finding high resolution content is a rare and exciting treat.

The tutorial on multi-touch gestures for the trackpad was quick and informative, but I immediately became aware of how few gestures are supported compared to Mac OSX. Scrolling, clicking, and dragging work as expected, and a two-finger tap to emulate a right-click is a welcome addition. Macs might support this, but I was never aware of it, I always just Ctrl-tap. There is no swipe left/right to switch apps as I was used to with Expose/Spaces and pinch to zoom is not supported outside of Google Maps as far as I can tell.

On the subject of multi-touch gestures, the Pixel's display is a capacitive touch surface with Gorilla Glass, and feels very much like a Tablet (except that it's vertical). Scrolling and tapping work as expected with no perceptible lag. Again, pinch-to-zoom and even double-tap-to-zoom aren't supported outside of Google Maps. In it's current state, the touchscreen on the Pixel is mostly a novelty. Reaching up from the keyboard to tap or scroll feels somewhat unnatural and excessive when the touchpad is literally at your fingertips. I occasionally use the touchscreen to scroll through long pages when I'm sitting back and reading, but otherwise only use the touchscreen when showing off the device to other people. I suspect that Google has plans for the touchscreen, but for now it just feels like it was tacked on because why not?

Once I had finished with the tutorials and demos, I was surprised to find that all of the apps and bookmarks I had installed in Chrome on my Mac had been sync'd over and installed automatically, without any visual indication. This saved me a bit of time, but some of the apps didn't sync their settings, so I had to poke around to get things setup the way I like. The most obvious one here was the SSH client. None of my connection settings or keys had been saved, which at first sounds like an inconvenience but is actually a feature. I do not want my keys and credentials anywhere near anybody's servers but my own. Google made the right decision here to require a bit more user interaction to improve security.

Getting my SSH keys onto the Chromebook proved a bit more difficult than I had anticipated. I keep a copy of my private keys on an IronKey USB drive, which requires a userspace program to "unlock" and decrypt the data on it. When plugged in, it mounts a read-only FAT32 filesystem with Windows, Mac, and Linux unlocking utilities. I double-clicked on the Linux binary in the "Files" window, but was informed that it was not supported by Chrome OS. I suspect that I could have switched to Developer Mode at that point and gotten it working in a shell, but I wanted to stay in normal user mode for a few days to really understand the limitations of a fully signed and trusted OS.

I admit that I caved at this point. I opened up my Macbook Air, copied my private key to a web server, and downloaded it on the Pixel from there. This is far from an ideal solution, and would have made me much more nervous if I didn't have an authenticated web server handy. I suppose I could also have copied the key to an unencrypted USB drive, but none of these options were really satisfying. The native SSH client app currently does not support generating new keys either, although based on what I have seen in Chromium bug reports, this is an often-requested feature and will likely be added soon.

Keys imported, I was able to connect to my personal server's tmux session, where I run irssi and bitlbee, as well as an ssh-agent with my credentials for accessing several other sites and servers. I immediately noticed that Ctrl-N and Ctrl-P keybindings in irssi did not behave as expected and would cause Chrome to open a new window or open the print dialog. A few more Google searches later, I learned that I could right-click on the SSH client app in the launcher and set it to always open in it's own window rather than a Chrome tab, which removes these keybindings and allows them to pass through to irssi unharmed. Initially, I thought I'd get tired of having to switch windows to get to my terminal, but this ended up being a non-issue, as Alt-Tab works as expected and fits nicely with the Ctrl-Tab binding that switches tabs in Chrome.

As soon as I started to feel comfortable with this workflow, some minor emergency caused me to login to some servers for work, patch some code, commit it, and deploy it. As I was working on this issue, I didn't feel Chrome OS getting in my way too much. On OSX, I was used to having four to six terminal windows open in a tiled arrangement, with a browser covering 50% of the screen and overlapping a few of the terminals. Due to the scaling of fonts in Chrome OS, only a single 80x24 terminal fits on the screen at once, making it more efficient to just run the terminal full-screen and rely on tmux's pane splitting. This took a little getting used to, but hasn't impeded my workflow much. I've yet to find a way to make the fonts in the Chrome native terminal smaller, but a cursory look at the Chromium hterm code leads me to believe that the formatting of text in ther terminal is solely based on a CSS stylesheet embedded in the extension. I'll likely need to build a custom version of the extension to make the font smaller, but for now it's easy enough to work with.

I was able to change the size of the fonts inside Chrome itself, as everything felt a bit large with the defaults. I feel like this is probably overcompensation for the high native resolution of the display and Chrome OS' pedigree as an OS for netbooks with smaller, lower resolution displays.

The next day, I took the Pixel to work with me, not only to show it to curious co-workers, but also to see if I could truly use it as my primary device. Overall, the answer is yes. I spent several hours writing code, diagnosing problems on production servers, reading logs, poking at Jenkins, reviewing GitHub pull requests, trolling IRC, and responding to things with Gmail. The Google Drive integration is a bit awkward as I'm logged into Chrome OS with my personal account, but have a browser tab logged into my work Google Apps account to edit documents there, but I surprisingly didn't have any issues with other Google services getting confused about which user I was, everything seemed to *stick* to whichever account I had used most recently for that service.

Later that night, I decided it was time to try to run Minecraft on the Pixel. Minecraft is written in Java, uses the LWJGL library, and is supported on Windows, Mac, and Linux using the Sun JRE. However, Java is most definitely not supported on Chrome OS and attempting to run Minecraft as a Java applet in the browser was met with a lovely error about unsupported plugins. We must go deeper.

Armed with the knowlege that Chrome OS is really just a polished Linux system, I found instructions for turning on the "Developer Switch" on the Pixel. The Developer Switch was a physical hardware switch in previous Chromebooks, but has been implemented as a part of the BIOS on the Pixel. Boot into recovery mode with Esc-Refresh-Power, hold Ctrl-D at the right moment, confirm that you want to wipe the stateful partition, and away you go. Yes, switching to Developer Mode requires deleting all non-OS data on the Chromebook. This was a bit disappointing, as I had downloaded a few documents and things already, but it didn't take me too long to copy everything to Google Drive so that I could safely wipe the system. Once again, I had to fool around getting my SSH key imported, but it didn't take me very long this time around, because I immediately jumped to the web server approach.

At first glance, Developer Mode looks no different than the normal mode. If you didn't know any better, you'd say it was exactly the same system. The real difference is in the "crosh" terminal (Ctrl-Alt-T), which originally just had simple commands like ping. With Developer Mode enabled, a "shell" command spawns a familiar bash shell on a Linux system. The shell starts logged in as the "chronos" user, which contains all of Chrome's user data in it's home directory. Reading and understanding the structure of mountpoints and the encrypted loopback devices in /mnt/stateful_partition is incredibly informative and goes a long way toward understanding how Google has hardened Chrome OS against malicious code.

Basically, only the rootfs "/" mountpoint is mounted without the "noexec" option, meaning that files under any other mountpoint are restricted to reading and writing data only, and files stored there cannot be executed as programs. Only the root user can edit files in the rootfs, so this means no executables can be changed without root privileges. Developer mode is a chink in this armor, as it allows the chronos user to use sudo to escalate to root and run any command.

Chrome OS does not include a package manager like apt or yum in it's default install as most other modern Linux distributions do. Instead, package installation is done as a part of building the OS image, which is almost always done by Google themselves. You're free to compile and build your own Chrome OS image, but this requires a fair bit of effort.

I decided to try setting up a minimal Ubuntu chroot jail to run on the Chrome OS system. It is worth mentioning that just wiping Chrome OS and installing a normal Linux distribution on the Pixel may be less trouble at this point. I haven't had any issues with Chrome OS for performing normal tasks, so I wanted to see how much I could do without replacing the OS.

Chrome OS uses a recent Linux kernel, on a common CPU architecture, with a userspace that includes the chroot command. It's certainly possible to work around all of those requirements, but taking advantage of the fact that Chrome OS is a mostly-standard Linux system, we can use some mostly-standard tricks to get a new userspace running.

On another Ubuntu box in a cloud somewhere, I ran this:

mkdir dist
debootstrap precise dist
cd dist
tar -czpvf ../precise.tar.gz .

Then downloaded the resulting precise.tar.gz on the Pixel. Given the noexec flag on most of the mountpoints, and not wanting to trample the Chrome OS install, I built a sparse 8GB loopback image on the stateful partition. This could theoretically be larger, but 8GB is enough for my purposes, and makes it easy to copy the image to a USB drive later if I want a backup.

dd if=/dev/zero of=/mnt/stateful_partition/precise.img bs=1M count=0 skip=8192
losetup /dev/loop1 /mnt/stateful_partition/precise.img
mkfs.ext4 /dev/loop1
mkdir /mnt/stateful_partition/precise
mount /dev/loop1 /mnt/stateful_partition/precise
cd /mnt/stateful_partition/precise
tar -xzvpf /home/chronos/Downloads/precise.tar.gz
cp /etc/resolv.conf /mnt/stateful_partition/precise/etc/
umount /mnt/stateful_partition/precise

Theoretically all of those operations could have been performed on any Linux box, then the resulting image copied to the Pixel, but I did it locally for some reason. Shouldn't matter. Now on to the mounting and chrooting...

mount -o loop /mnt/stateful_partition/precise.img /mnt/stateful_partition/precise
mount -t proc none /mnt/stateful_partition/precise/proc
mount -o bind /dev /mnt/stateful_partition/precise/dev
chroot /mnt/stateful_partition/precise /bin/bash

Those mounts will have to be re-mounted every time the laptop is rebooted, so you may want to shove that in a script somewhere, or add them to /etc/fstab. At this point, it's a mostly functional Ubuntu chroot with very few things installed, no upstart daemon, and full access to all of the host's hardware. Needless to say, this is not secure at all. I haven't played with cgroups and namespaces on Chrome OS yet, but I see no reason why you wouldn't be able to build a more comprehensive jail if you wanted. For my purposes, this is good enough.

A bit of messing about with locales (hint: locale-gen en_US.UTF-8; dpkg-reconfigure locales) and other minor bits of configuration, I installed the Sun JVM and minecraft.jar inside the chroot and bind-mounted /home/chronos into the jail as well, in order to make it find the .Xauthority file. The Minecraft launcher started up (in native eye-bleedingly small resolution), but upon logging in and trying to initialize OpenGL, the screen went blank and X restarted. Sadly, I've not been able to get Minecraft to start without crashing X.

The next day, this jail came in handy as I needed to use a serial console on a router at work. I plugged in my USB-Serial adapter, it showed up as /dev/ttyUSB0 as it does on most Linux boxes, installed picocom in my jail, and jumped on the console, all within a crosh tab.

Over the last week, having an Ubuntu jail handy has become quite useful for even basic tasks like traceroute, nmap, and tcpdump which are not included in the stripped-down Chrome OS install. If you're doing any sort of network or security work, access to these tools is indispensible.

This post is getting a bit long, so I should wrap it up with some conclusions. After a week of using Chrome OS, I've found it to be more than adequate for both work and personal use cases.

As a terminal and browser combination, Chrome OS is perfect. The browser is fast and the terminal works as expected in every scenario I've needed it. Developer mode is nice to have available for when your world doesn't fit inside the sandboxes you're given.

As a media player, I found that Spotify's web player is not available to US accounts yet but Rdio, Amazon Cloud Player, and Grooveshark are viable alternatives. Netflix detects developer mode and refuses to stream any video. The lack of a serious content catalog on Google Play makes it laughable to even mention it. Chrome has libavcodec installed as a plugin, but has certain patent-encumbered codecs disabled and is not associated with all of the Content-types that it actually supports. For example, if you rename a .mkv to .mp4, it'll demux just fine (likely because WebM uses Matroska containers), but some codecs you'd expect to work, like AC3, are missing. For gaming, Chrome OS has a long way to go.

As a gaming platform, few games have been ported to NaCL, and those that have been are more like what you'd find on a tablet device than Steam (think Angry Birds), probably because NaCL only exposes OpenGLES, even though there's an Intel HD 4000 GPU underneath.

Overall, Chrome OS is a really solid attempt to bring a simplified, stripped down computing experience to the masses. As with many other new platforms, you have to buy into the world view of the people that built it. In this case, that means storing the majority of your data in the "cloud" and doing nearly everything in the context of a web browser. It's still a bit rough around the edges but is evolving quickly and there are reasonable workarounds for most issues. If you're tied to a specific application or environment native to an existing platform (Office, Xcode, Adobe), then Chrome OS is not ready for you yet.

I'm pleased with my decision to give Chrome OS a try. While I can't say with certainty that I'll use it forever, I'm happy for now and will continue to use it on a daily basis, supplemented by a Mac Mini for Ableton Live and a Linux box for 3D printing.