How to Encrypt Your USB Flash Drives

Did you know that your modern Linux kernel comes with a built-in encryption framework? I am talking about dm-crypt (device-mapper crypt) and the user-friendly layer on top of it, called LUKS (Linux Unified Key Setup). I just encrypted all of my USB flash drives two weeks ago using the dm-crypt + LUKS method and I am very happy with the results.

The process itself is very simple.

# 1. Find the correct device.

lsblk

# 2. Wipe the device with random data. I prefer to target the disk by its UUID
# because using the /dev/sdX convention is not very reliable (the letters can
# change between boots/hotmounts). NOTE: You might be interested in
# http://frandom.sourceforge.net/ if your device is over 16 GiB or so, because
# using /dev/urandom can be very slow. If using Arch Linux, you can get it from
# the AUR: https://aur.archlinux.org/packages/frandom/.

dd if=/dev/urandom of=/dev/disk/by-uuid/XXX bs=4096

# 3. Create the partition on the device.

cfdisk /dev/disk/by-uuid/XXX

# 4. Encrypt the partition and make it LUKS-compatible. See the manpage for
# cryptsetup(8).
#   -c: cipher type to use
#   -y: LUKS will ask you to input the passphrase; using -y will ask you twice
#       and complain if the two do not match.
#   -s: Key size in bits; the larget the merrier, but limited by the cipher/mode used.

cryptsetup -c aes-xts-plain -y -s 512 luksFormat /dev/disk/by-uuid/XXX

# 5. Open the partition with LUKS.

cryptsetup luksOpen /dev/disk/by-uuid/XXX mycrypteddev

# The partition is now available from /dev/mapper/mycrypteddev as a "regular"
# partition, since LUKS is now handling all block device encryption between the
# user and the device.

# 6. Set up a filesystem on the partition.

mkfs.ext4 /dev/mapper/mycrypteddev

# 7. Close the partition with LUKS.

cryptsetup luksClose /dev/mapper/mycrypteddev

# Encryption setup complete! Now every time you want to access the partition,
# you must first open it with LUKS and then mount it. Then when you're done, do
# the reverse: unmount and close it with LUKS.

# To mount and open with LUKS:

cryptsetup luksOpen /dev/disk/by-uuid/XXX mycrypteddev
mount -t ext4 /dev/mapper/mycrypteddev /mnt/mount_point

# To unmount and close with LUKS:

umount /mnt/mount_point
cryptsetup luksClose mycrypteddev

The mount/open and unmount/close steps necessary for using the device is laborious. That’s why you should write a bash script to run them. I’ve written the following bash script called cmount.sh to access my 3 USB drives this way:

#!/bin/zsh
# LICENSE: PUBLIC DOMAIN
# mount/unmount encrypted flash drives

mp=$3
uuid=""

case $2 in
    "0")
        uuid="11e102cd-dea1-46a8-ae9b-b3f74b536e64" # my red USB drive
        ;;
    "1")
        uuid="cf169437-b937-4a39-86cb-7ca82bd9fe94" # my green one
        ;;
    "2")
        uuid="57a0b7d5-d2a6-47e0-a0e3-adf69501d0cd" # my blue one
        ;;
    *)
        ;;
esac

if [[ $uuid == "" ]]; then
    echo "No predefined device specified."
    exit 0
fi

case $1 in
    "m")
        echo "Authorizing encrypted partition /dev/mapper/$mp..."
        sudo cryptsetup luksOpen /dev/disk/by-uuid/$uuid $mp
        echo -n "Mounting partition on /mnt/$mp..."
        sudo mount -t ext4 /dev/mapper/$mp /mnt/$mp && echo "done."
        ;;
    "u")
        echo -n "Unmounting /mnt/$mp..."
        sudo umount /mnt/$mp && echo "done."
        echo -n "Closing encrypted partition /dev/mapper/$mp..."
        sudo cryptsetup luksClose $mp && echo "done."
        ;;
    *)
        ;;
esac

To mount the green USB to /mnt/ef0 (“ef0” is just an arbitrary folder name):

./cmount.sh m 1 ef0

Then to unmount:

./cmount.sh u 1 ef0

Simple, eh? Go forth and encrypt all of your USB drives, so that when they get lost, they can’t be read by curious strangers. You can use the above steps to create and encrypt multiple partitions in the same device, or to only encrypt one partition while leaving other partitions unencrypted (i.e., steps 4 through 7 are partition-specific). The choice is yours. I prefer partition-level (aka “block device”) encryption over file/folder encryption because I don’t have to mentally think every time “hey, do I want to encrypt this?” for every file/folder I create.

If you want to look into encrypting your hard drives and swap partitions, read through this disk encryption page, and particularly, this section. There are many “levels” of encryption, and you should consider the many options available to you.

Xorg: Using the US International (altgr-intl variant) Keyboard Layout

TL;DR: If you want to sanely type French, German, Spanish, or other European languages on a standard US keyboard (101 or 104 keys), your only real option is the us layout with the (relatively new) altgr-intl variant.

I like to type in French and German sometimes because I study these languages for fun. For some time, I had used the fr and de X keyboard layouts to input special characters from these languages. However, it wasn’t until recently that I realized how most European layouts, such as fr and de, require that you have a 105-key keyboard. A 105-key keyboard looks exactly like the standard, full-sized IBM-style 104-key keyboard (i.e., IBM Model “M” 101-key keyboard plus 2 Windows keys and 1 “Menu entry” key on the bottom row), except that it has 1 more extra key on the row where the Shift keys are (and also has a “tall” Enter key with some of the existing keys on the right side rearranged a bit).

I personally use a 104-key keyboard (a Unicomp Space Saver 104, because that’s how I roll). Now, when I switched to the fr layout the other day, I wanted to type the word âme. Unfortunately, the circumflex dead key was not where it was supposed to be. This was because I only had 104 keys instead of 105, and during the process of switching forcibly to the fr layout, there was a malfunction in the conversion (rightfully so).

Now, the choice was to either buy a 105-key keyboard or just find an alternative 104-key layout that had dead keys. I didn’t want to buy a new 105-key keyboard because (1) the extra 1 key results in a squished, “square” looking left-Shift key and (2) the tall Enter key would make it more difficult for me to keep my fingers happy on the home row, since I’d have to stretch my pinky quite a bit to reach it, and (3) I just didn’t feel like spending another ~$100 for a keyboard (my Unicomp is still in excellent condition!).

So, I had to find a new keyboard layout that could process accented/non-English Latin characters better. The Canadian Multilingual Standard keyboard layout (http://en.wikipedia.org/wiki/Keyboard_layout#Canadian_Multilingual_Standard) looked very, very cool, but it was only for a 105-key keyboard. I then discovered a layout called the US International Standard keyboard layout, which enables you to type all the cool accented letters from French or German (and other European languages) while still retaining a QWERTY, 101/104 key design. This sounded great, until I realized that the tilde (~), backtick (`), single quote (‘) and other keys were dead keys. I.e., to type ‘~’ in this layout, you have to type ‘~’ followed by a space. This is horrible for programmers in Linux because the ~ key comes up everywhere (it’s a shell shortcut for the $HOME directory). To type a single quote character, you have to type (‘) followed by a space! Ugh. I’m sorry, but whoever designed this layout was obviously a European non-programmer who wanted to type English easier.

But then, all hope was not lost. When browsing all of the choices for the us keyboard layout variant under X (/usr/share/X11/xkb/rules/base.lst), I found a curious variant called altgr-intl. A quick google search turned up this page, an email from the creator of this layout to the X developers: http://lists.x.org/archives/xorg/2007-July/026534.html. Here was a person whose desired usage fit perfectly with my own needs! Here’s a quote:

I regularly write four languages (Dutch, English, French and German)
on a US keyboard (Model M – © IBM 1984).

I dislike the International keyboard layout. Why do I have to press
two keys for a single quote (‘ followed the spacebar) just because the
‘ key is a dead-key that enables me to type an eacute (é)?

I decided to ‘hide’ the dead-keys behind AltGr (the right Alt key).
AltGr+’ followed by e gives me eacute (é). It also gives me
m² (AltGr+2).

Excellent! Apparently, this layout was so useful that it became included eventually into the upstream X codebase, as the altgr-intl variant for the standard us (QWERTY) keyboard layout. The most compelling feature of this layout is that all of the non-US keys are all hidden behind a single key: the right Alt key. If you don’t use the right Alt key, this layout behaves exactly the same as the regular plain us layout. How cool is that?! And what’s more, this layout makes it compatible with the standard 101-key or 104-key IBM-styled keyboards!

This variant deserves much more attention. Unfortunately, there seems to be little or no information about it other than the above-quoted email message. Also, I’ve noticed that it is capable of generating Norse characters as well, like þ and ø. There does not seem to be a simple keyboard layout picture on the internet to show all the keys. Anyway, I’ve been using it recently and it really does work great. There is no need for me to switch between the us, fr, and de layouts to get what I want. I just use this layout and that’s it. Take that, Canadian Multilingual Standard!

Here’s how to set it up: use either the setxkbmap program like this:

setxkbmap -rules evdev -model evdev -layout us -variant altgr-intl

in a script called by ~/.xinitrc, or use it directly in your keyboard xorg settings:

Section "InputClass"
    Identifier "Keyboard Defaults"
    MatchIsKeyboard "yes"
    Option  "XkbLayout" "us"
    Option  "XkbVariant" "altgr-intl"
EndSection

I personally prefer the script method because you can tweak it easily and reload it without restarting X. For me, I had to use the -rules evdev -model evdev options because -model pc104 would mess things up (probably due to an interaction with xmodmap and such in my ~/.xinitrc). Whatever you do, make sure everything works by testing out the AltGr (right Alt) key. For example, AltGr+a should result in ‘á’.

A couple caveats: Some keys like â and è (which are AltGr+6+a and AltGr+`+e (i.e., uses dead keys)) do not show up at all on urxvt. I’m guessing that the dead keys are broken for urxvt (or maybe it’s a bug with this layout; who knows). Luckily, I can just use a non-console app (like GVIM) to do my Euro-language typing, so it’s OK (although, eventually, I’ll run into this bug again when I start typing French emails from within mutt inside urxvt 20 years later… but by then it will be fixed, I’m sure.) Also, the nifty xkbprint utility can generate nice pictures of keyboard layouts (just do a google image search on it), but it’s currently missing (https://bugs.archlinux.org/task/17541) from Arch Linux’s xorg-xkb-utils package. So, if you’re on Arch, you’ll have to experiment a bit to figure out the various AltGr+, and AltGr+Shift+ key combinations.

See also: Xorg: Switching Keyboard Layouts Consistenly and Reliably from Userspace

UPDATES:

  • October 30, 2011: I just found out that the dead keys bug in urxvt is actually a bug in ibus/SCIM (I use ibus, which relies on SCIM, to enter Japanese/Korean characters when I need to). I tried out uim, which is a bit more complicated (much less user friendly, although there are no technical defects, from what I can tell), and with uim, the dead keys work properly in urxvt. The actual bug report for ibus is here.
    So, use uim if you want to use the altgr-intl layout flawlessly, while still retaining CJK input functionality. Of course, if you never needed CJK input methods in the first place, this paragraph shouldn’t concern you at all.
  • December 7, 2011: Fix typo.
  • January 24, 2012: Fix grammar.

Things I Like About Git

Ever since around 2009-2010, developers have been engaging in an increasingly vocal debate about version control systems. I attribute this to the hugely popular rise of the distributed version control systems (DVCSs), namely Git and Mercurial. From my understanding, DVCSs in general are more powerful than nondistributed VCSs, because DVCSs can act just like nondistributed VCSs, but not vice versa. So, ultimately, all DVCSs give you extra flexibility, if you want it.

For various reasons, there is still an ongoing debate as to why one should use, for example, Git over Subversion (SVN). I will not address why there are still adamant SVN (or, gasp, CVS) users in the face of the rising tsunami tidal wave of DVCS adherence. Instead, I will talk about things I like about Git, because I’ve been using it almost daily for nearly three years now. My intention is not to add more flames to the ongoing debate, but to give the curious, version control virgins out there (these people do exist!) a brief rundown of why I like using Git. Hopefully, this post will help them ask the right questions before choosing a VCS to roll out in their own machines.

1. Git detects corrupt data.

Git uses an internal data structure to keep track of the repo. These objects, which are highly optimized data structures called blobs, are hashed with the SHA-1 algorithm. If suddenly a single byte gets corrupt (e.g., mechanical disk failure), Git will know immediately. And, in turn, you will know immediately.

Check out this quote from Linus Torvalds’ Git talk back in 2007:

“If you have disc corruption, if you have RAM corruption, if you have any kind of problems at all, git will notice them. It’s not a question of if. It’s a guarantee. You can have people who try to be malicious. They won’t succeed. You need to know exactly 20 bytes, you need to know 160-bit SHA-1 name of the top of your tree, and if you know that, you can trust your tree, all the way down, the whole history. You can have 10 years of history, you can have 100,000 files, you can have millions of revisions, and you can trust every single piece of it. Because git is so reliable and all the basic data structures are really really simple. And we check checksums. And we don’t check some UDP packet checksums that is a 16-bit sum of all the bytes. We check checksums that is considered cryptographically secure.

[I]t’s really about the ability to trust your data. I guarantee you, if you put your data in git, you can trust the fact that five years later, after it is converted from your harddisc to DVD to whatever new technology and you copied it along, five years later you can verify the data you get back out is the exact same data you put in. And that is something you really should look for in a source code management system.”

(BTW, Torvalds, opinionated as he is, has a very high signal-to-noise ratio and I highly recommend all of his talks.)

2. It’s distributed.

Because it is based on a distributed model of development, merging is easy. In fact, it is automatic, if there are no conflicting changes between the two commits to be merged. In practice, merge conflicts only occur as a result of poor planning. Sloppy developers, beware!

Another benefit of its distributed model is that it naturally lends itself to the task of backing up content across multiple machines.

3. It’s fast.

I can ask Git if any tracked files in a repo have been edited/changed with just one command: git diff. And it needs but a split second, even if my $PWD is not the repo’s root directory or if there are hundreds and thousands of tracked files littered across everywhere (because Git doesn’t think in terms of files, remember?)

4. It gives me surgical precision before and after committing changes.

Several things help me keep my commits small, and sane. The biggest factor is the index concept. Apparently, Git is the only VCS that gives you this tool! After editing your files, you go back and select only those chunks you want to be in the commit with git add -p. This way, you are free to change whatever you think is necessary in your files, without any nagging idea in the back of your mind going, “Hey, is this change exactly what you need/intended for your next commit?”

The other big factor is the rebase command. With rebase, I can do pretty much anything I want with my existing commits. I can reorder them. I can change their commit messages (known as amending). I can change the commits themselves (i.e., change the diffs). I can change 4 tiny commits into a single commit (known as squashing). I can even delete a commit (as long as the later commits do not rely on it). Essentially, you can rewrite your commits in any you like. This way, you can sanitize your commits in a logical way, regardless of work history.

Other Thoughts

I could go on, but the remaining points don’t have as much “oomph” as the ones listed already. I fear that I am unable to see many of the “problems” with Git’s methodology and workflow, because I had the (un?)fortunate experience of learning Git as my first and only VCS. I learned concepts like the index, rebasing, committing, amending, branching, merging, pulling, and pushing all for the first time from Git. I also learned how to use Git by typing the core Git commands into a terminal (since I’m in there all the time anyway), so I have not been biased in favor of GUI-only operation (these days, tig is the only GUI tool I use — and only as a brief sanity check at that). Then again, I’ve never suffered data corruption, lost branches, or anything like that, so I’m probably doing things the right way in this whole VCS thingamajig.

Oh, and here are some aliases I use for Git:

alias g='git'
alias gdf="[[ \$(git diff | wc -l) -gt 0 ]] && git diff || echo No changes"
alias gdfc="[[ \$(git diff --cached | wc -l) -gt 0 ]] && git diff --cached || echo Index empty"
alias gst='git status'
alias gbr='git branch'
alias gcm='git commit'
alias gco='git checkout'
alias glg='git log'
alias gpl='git pull'
alias gps='git push'

Detecting Unmounted Partitions With Blkid

Did you know that you can instantly check all partitions on your system (including USB thumb drives), and see if they’re mounted or not? The hero command of the day is sudo blkid -o list:

$ sudo blkid -o list
device       fs_type label    mount point      UUID
-----------------------------------------------------------------------------------
/dev/sda1    ntfs             /mnt/windows-xp  XXXXXXXXXXXXXXXX
/dev/sda2    ext4             /                XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX
/dev/sda3    ext4             /home            XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX
/dev/sda6    swap             <swap>           XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX
/dev/sda5    ext4             /mnt/data        XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX
/dev/sdb1    ext2             (not mounted)    XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX
/dev/sdc1    vfat             (not mounted)    XXXX-XXXX

As you can see, I have two USB drives (one in ext2 and the other in vfat format) plugged in, but not mounted, and blkid detects this for me. Pretty useful, don’t you think? There’s no need to parse /proc/mounts or fiddle with the (very) verbose output of sudo fdisk -l. I stumbled upon blkid’s obscure “-o list” option while trying to write a shell script to automatically mount unmounted USB drives.

The only troublesome aspects of “-o list” are that you can’t customize which columns are displayed (e.g., for me, I’d like to drop the label column), and also you can’t separate the columns by whitespace because of how there is a space inside the (not mounted) mount point. Looking at the sources for blkid, it seems that there are also two other descriptions with whitespace in them: (in use) and (mounted, mtpt unknown) (see http://git.kernel.org/?p=utils/util-linux-ng/util-linux-ng.git;a=blob_plain;f=misc-utils/blkid.c;hb=HEAD). These deficiencies make it hard to easily and reliably parse the output with just a shell script.

I actually ended up writing a 300 line Haskell program that uses Parsec to reliably parse the output of blkid. It took a while to write, considering my newbie Haskell skills (aren’t most Haskellers late bloomers?). Anyway, it also leverages the CmdArgs library, and automatically mounts/unmounts USB devices with ease and grace. Speaking of Haskell, I’m slowly in the process of converting my various error-prone shell scripts into robust, mini Haskell programs, and I’ve been very satisfied with the results. And porting shell scripts into Haskell is a great way to learn more Haskell, too!

UPDATE December 1, 2011: Here is a convenience link to said ~300 line program for you Googlers: Parsec and CmdArgs in Action: A Small Example.

UPDATE December 11, 2011: Fixed broken link. Also, the recent kernel.org fiasco has changed the home of util-linux-ng to: https://github.com/karelzak/util-linux/, and the blkid source is at https://github.com/karelzak/util-linux/blob/master/misc-utils/blkid.c.

A Summary of Linux vs. Windows XP

As you may have figured out by now, I don’t use Windows XP full-time any more. I only use it for one or two games. Anyway, I don’t think I’ve written a post yet comparing Linux (Arch Linux to be specific) to Windows XP. I keep referring to XP, because that’s the last Windows OS I’ve actually used on my own machines. But the points that follow still pertain to the latest incarnation of Windows (Windows 7), and perhaps all future versions of it.

I just had to get these annoyances about XP out of my system, and let you, my dear reader, know about them. So the following is my very biased point of view as a relatively new, SELF-IMPOSED Linux convert:

Linux pros:

  • Unlimited, sane configurability: Everything you can imagine about Linux can be configured with TEXT FILES (or simple TEXT based interfaces), containing HUMAN-READABLE text. There are no strange “registry” files like in Windows, and hence, no need to invoke strange programs like “regedit.exe” to do your bidding. If you know how to use a text editor (what you Windows folks hideously understand as “Notepad”), then nothing can stand in your way. EVERYTHING is exposed by Linux. An extremely simple root vs. non-root user dichotomy ensures sane, “system files” vs. “user files” separation. Windows is living in the stone age when it comes to user rights/management.
  • Few, if any, viruses: Because the consumer-level Linux ecosystem is so small, evil hackers don’t spend time writing virus programs for it. More on this virus/malware/spyware discussion below.
  • Does not slow down or get unstable with uptime: If you leave your Windows computer on for more than a day, it’s bound to slow down. Linux has never done this to me. Ever. Even with uptimes past 5 days.
  • Simplified, unified, and standardized software installation/upgrade/removal: On Windows, individual programs have to check if a newer version of itself is available. There is no standard for this — some programs do it automatically if you’re connected to the internet, some programs ask for your approval (incessantly), some programs have a “Check for updates…” button that you have to manually click on, and some are just standalone .exe files that you need to manually remove and reinstall with the newer version! This is insanity. On Arch (or any other desktop-user distro), you just type in your shell “sudo pacman -Syu” to do a system-wide upgrade. With a single command, you upgrade every single package that you have installed (after transparently downloading them from Arch’s world-wide network of package “repositories”). Here, “package” means either a program, or system files — even the OS kernel! You can optionally choose to upgrade only certain packages, or to ignore some of them, to customize your upgrade. Some Archers upgrade every day, and others wait a month or more to upgrade. There are no nag screens, popups, or “automatic” upgrades/installs that break behind your back should you choose to shut down your computer.
  • Tons of free, industrial-strength software: Actively-developed open source programs are, quite simply, the most reliable, robust programs around. Take for example the Linux Kernel: this project is one of the finest achievements of software engineering to date. Legions of high-profile companies rely on the Linux Kernel to power their servers (and many thousands of Linux desktop users, like myself, benefit from this same, state-of-the-art reliability). And because free, open source software (“FOSS”) developers are humans too, there are mountains of open source programs for your use. Things like text editors, web browsers, email clients, office suites, image editors, movie editors, etc. all exist for free in FOSS-land. And many of these programs are the very best in their field, because they are extremely actively developed (where new releases come in weeks or months, instead of years). The Arch repositories are packed with FOSS programs. Packed, I say!
  • No malware/spyware: In Arch, there are two types of repositories: official and unofficial. The official repository only has packages that have been examined, tested, and uploaded by sanctioned members of the Arch Linux Team. The unofficial repositories are those repositories that have packages uploaded by anyone. The biggest and most popular unofficial repository is the Arch User Repository (“AUR”), which has thousands of packages. As time progresses, popular packages from the AUR collect votes from users, and the most popular ones receive the blessings of the Arch Linux Team and gets adopted into the official repository, and hence undergo regular, official maintenance. In short, the room for spyware/malware to creep into any of the official repositories is virtually zero. Even if you install an AUR package that has 0 votes for it, the de facto AUR client yaourt will still tell you to examine the contents of all installation files (these are, predictably enough in the Linux world, TEXT files) before executing them. Of course, you could go out of your way to download a suspicious-looking executable file and run it, but such a course of action is rare and remote enough (and downright stupid enough) to ignore.
  • No annoyances: Two things: (1) Because 95+% of software you use will be FOSS in Linux, this means that there will be no annoyances from programs. By “annoyances” I mean things like unrequested popups, tooltips, and screen-real-estate-plundering dialog boxes. This is because FOSS is community-driven — if a majority of users find some feature in a FOSS program annoying, it will get removed soon enough. This feature of FOSS does not get enough visibility, but it is one of the most satisfying: the absence of half-assed work by imminent-deadline-driven, exhausted developers. (2) Because Linux is so configurable, you can configure-away lesser annoyances by editing HUMAN-readable TEXT files 99% of the time. The other 1% of the time, you have to use TEXT-driven interactive sessions, which is just as easy to do.
  • Fast, easy problem resolution: Let’s say you did a system upgrade, and something broke as a result. Because there are hundreds, if not thousands, of users who all run the same system (see “Simplified, unified, and standardized software installation/upgrade/removal” above), your problem will be voiced in your distro’s forum soon enough. Windows users have an instinctive distrust of other Windows users: you have no idea what programs they’ve installed, and which anti-virus programs they have running (if at all!). This is why fixing a Windows problem takes quite a bit of skill and specialized expertise (and why, if you’re a geek, others tend to ask you to fix their Windows problems). Not so with Linux. If you encounter an error, all you have to do is copy/paste the error message (human-readable, SAVE-able error messages are part of FOSS culture) into a search engine and add in the name of your distro and the word “forum”. You are now one or two clicks away from reading the latest word (in the world) on the problem.
  • Gentle, but eventual, path to a true understanding of your operating system’s ecosystem: Here, I define “OS ecosystem” as understanding how and why your operating system behaves the way it does. Windows is a horrible platform to learn how your OS behaves. This is because it actively hides many important concepts from you. For example, do you have any idea how and why a program shows up on the “Add/Remove Programs” list on XP, even though you just removed it? (Answer: NO.) Such mystical voids of system-level confusion are rather rare in the Linux world.

Windows pros:

  • Industry-leading games: Almost all commercial games are released for Windows.

Seriously, after all of the extremely positive things that I’ve said about Linux, and how Windows fails in each of those areas, what can I say?

Misunderstandings about Linux (unfortunate from the Linux/FOSS community’s perspective):

  • It’s only for power users: No, it’s for people who don’t mind learning why their computer behaves a certain way. If you enjoy driving your car blindfolded, you are the right type of person to use Windows (actually, Mac OSX might be a better candidate).
  • It’s 100% secure: Yes, after all the overwhelmingly positive things I’ve said about the rarity of viruses/spyware/malware on Linux, nothing’s perfect. However, I will at least argue that Linux is more secure than Windows, because Linux does not hide things as much. I mean, there are dozens of sites out there designed to answer the question, “Is svchost.exe a safe process? How about wuauclt.exe?”, all because of how Windows likes to hide things from you. In Linux, pretty much everything is exposed. In Arch, specifically, you can do a “pacman -Qo XYZ” to see which package is responsible for that file. If no package is responsible for it, then that means either (1) a program created that file (e.g., an optional configuration file) or (2) you created it yourself!
  • If you use Linux, you’re an evil hacker: Congratulations, you’ve been brainwashed.

All non-brain-damaged people get sick and tired of Windows’ limitations and shortcomings every day. There are no secrets in the Windows world when it comes to user dissatisfaction. I used to be one of these people. Then one day, I started using Linux. And the difference is night and day. It’s just unfortunate that legions of PC users have been brainwashed to accept non-configurability and the “Windows way” to do a simple task: make the computer work for them for their needs. I used to be brainwashed that way. Here are some things that opened my eyes to just how horrible Windows is out of the box (Windows’ default “feature” vs. Linux’s superior equivalent):

  • “shortcuts” vs. symlinks (downright superior in every way)
  • “drives” (C:\, D:\, … Z:\) vs. mount points (unlimited and customizable)
  • “cmd.exe” vs. zsh/bash/etc (it’s like comparing the speed of a clown’s unicycle with a Formula-1 race car)
  • “Notepad” vs. vim/emacs (I’m at a loss for words)
  • “MS Word” vs. latex/xetex (imagine if MS Word did everything transparently: enter latex)
  • “I need Adobe program XYZ to export to PDF documents” vs. “Not in Linux.” (need I say more?)
  • “CPU-Z” vs. “cat /proc/cpuinfo” (no wonder there’s no CPU-Z for Linux; you don’t need it!)
  • none vs. “sleep 10m; echo ‘alarm message’; mplayer alarm.mp3” (super-simple, customizable alarm)
  • none vs. “sleep 1h5m3s; sudo shutdown -t 1 -hP now & disown; exit” (which means, “turn off the computer 1 hour, 5 minutes, 3 seconds from now”; the long command that starts with “sudo …” is actually aliased to just “of” for me, so I actually only type “sleep 1h5m3s; of”)
  • none vs. “sleep 1h5m3s; sudo shutdown -t 1 -r now & disown; exit” (which means “restart the computer 1 hour, 5 minutes, 3 seconds from now”; I use an alias here as well)

And here are some precious programs/tools that I had zero knowledge of until I entered the Linux/FOSS community:

  • vim (see above)
  • the latex toolchain (see above)
  • ssh (it’s zsh/bash/etc, but on a remote machine)
  • scp (transfer files over to a remote machine, but encrypt it during the transmission for state-of-the-art security)
  • rsync (copy files over to a remote machine; if a similar file already exists there, rsync will take less time to complete the copy)
  • git (source code management system; GREAT for backing up configuration files, text files, etc.)
  • mutt (text-based, no-nonsense email client)
  • gnupg (cutting-edge encryption tool to encrypt your most important files)
  • cron daemon (another TEXT based, no-nonsense way to control which programs/commands are regularly run at which intervals (minutes, hours, days… even years!))

Perhaps the most rewarding feature of using Linux is that there is always something to learn from it. In other words: the longer you use it, the more you learn to control and customize your computing experience (versus “the more I use Windows, the better I get fixing it”).

I must reiterate that I am a SELF-IMPOSED Linux convert. I didn’t get pushed into Linux, or had to learn it for some school/work requirement. I did it first as an adventure, and later on, just fell in love with it. No one held hands with me, and the help that I did get came from the internet. Linux reached critical mass years ago, and there are enough forum/blog posts out there to help you if you ever get stuck.

Use Linux!

UPDATE January 3, 2012: I just re-read this post (as I do time to time with my other posts) because Antaku commented on it, and wanted to list some awesome FOSS software that I forgot to mention:

  • diff/colordiff: This is probably the second-most important thing after text editors when it comes to dealing with text files — it tells you the difference between two text files. English teachers: when they turn in their drafts, you can immediately tell what parts they changed in 0.01 seconds. You don’t have to re-read half of it! There are tons of other useful things you can do with diff, any time text files are involved.
  • sha1sum: State-of-the-art file integrity verifier (using the very famous SHA-1 hash algorithm). It generates a 40-byte digital fingerprint, called a “hash”, of any file. You use this hash in a “reverse” fashion to see if your file is bit-perfect (i.e., does it still have the same hash that it had last month? last year?). (BTW, git uses SHA-1 for all of the data it tracks.) You can also use sha1sum as a crude substitute for diff, because two similar files with even just 1 different byte will have different hashes.
  • gcc/clang: Open source compilers for the C programming language — great if you want to learn to program in C and need a compiler. Since C will be around in the lifetime of everyone reading this post, I suggest you learn it. You can interface with Linux in a very, very tight way with C, which is very cool.
  • dd: Great utility whenever you want to move around bytes. Yes, this is a very generic statement, but that’s just how powerful (and useful!) dd can be. If you want to benchmark your new SSD, you can use dd to generate thousands of files filled with random bytes.
  • xxd/hexdump: Hex viewers! Vim uses xxd to turn itself into a hex editor.
  • cat: Short for concatenate. I.e., if you do “cat foo bar quux > ash”, all of the contents of foo, bar, and quux (their bytes) will be joined up into a single file, into ash. It comes in handy lots of times, whenver you’re using a shell.
  • dmesg: Kernel-level log messages (what the Kernel detected, did) for your browsing pleasure. Great for understanding your computer’s behavior at its lowest levels. Does Windows even have an equivalent???
  • iftop: Excellent network traffic viewer. It tells you which IP addresses you are downloading/uploading from. Great for troubleshooting LAN setups in your home.
  • htop: Like Windows’ famous “Task Manager”, but it actually tells you EVERY SINGLE running process, not just what you launched yourself.

Ugly Xmodmap Caps Lock Workaround

So, I decide to do a system upgrade (including all xorg packages) the other day and suddenly xmodmap isn’t working any more. Specifically, these lines in my .xinitrc no longer do the job (of making Caps lock my mod3 key (for use in Xmonad)):

xmodmap -e "remove Lock = Caps_Lock"
xmodmap -e "add mod3 = Caps_Lock"

So after tons of googling, I found this page: http://forums.gentoo.org/viewtopic-t-857625.html.

Basically, to get the same behavior back, I have to have

remove Lock = Caps_Lock
remove mod3 = Super_L
keysym Caps_Lock = Super_L
add mod3 = Super_L

in my (new) ~/.xmodmap file, and then do this in my ~/.xinitrc:

xmodmap -e "remove Lock = Caps_Lock"
xmodmap -e "add mod3 = Caps_Lock"
xmodmap ~/.xmodmap

This is a very, very ugly hack, but even after spending a solid hour trying manual xmodmap commands and this and that and all sorts of combinations, this is the only method that works.

I have no idea which package exactly broke xmodmap’s former 2-liner functionality, but it was sometime in the past couple months, probably. If the old 2-liner starts working again, I’ll let you all know…

Linux: Highlighting + Middle Mouse Click vs Copy & Paste

I finally learned the difference between highlighting+middle mouse clicking (or SHIFT+INSERT if you’re on the keyboard) and copying/pasting text in Linux today, all thanks to the manpage for the nifty xsel program:

The X server maintains three selections, called PRIMARY, SECONDARY and CLIPBOARD. The PRIMARY selection is conventionally used to implement copying and pasting via the middle mouse button. The SECONDARY and CLIPBOARD selections are less frequently used by application programs.


There is no X selection buffer. The selection mechanism in X11 is an interclient communication mediated by the X server each time any program wishes to know the selection contents, eg. to perform a middle mouse button paste.

That is the most useful explanation about highlighted text vs. copied text I’ve seen since entering the Linux world a few years ago. The PRIMARY selection (highlight + middle mouse click) is, as far as I can tell, available in pretty much every Linux program. I’ve never encountered the SECONDARY selection type. The CLIPBOARD selection is somewhat rare; I’ve only encountered it when I explicitly highlight some text in Firefox and then do right-click -> Copy (before I knew about PRIMARY selections).

As for xsel itself, you can use it as a very simple buffer. The best use scenario would be a case where you want to use the output of some command for a while, but where creating a temporary file would be overkill. Here is a random example of xsel:

$ <file.txt | tail -n1 | xsel -p

Now the last line of file.txt is in your PRIMARY selection buffer. Then, after some other miscellaneous work in your shell, you can recall what’s in the PRIMARY buffer like so:

$ xsel | less

The -p flag makes the piped text go into the PRIMARY selection buffer. However, the -p flag is the default one, so you can omit it. Interestingly, the -x flag can be given to swap the PRIMARY and SECONDARY selections.

The Best Serif Font in the World: Linux Libertine

I did not find out about Linux Libertine until a couple months ago. Simply put, it’s the best serif font ever. For some reason, it still remains relatively unknown, even though Wikipedia uses it for its logo. Maybe it’s because the main developers don’t care to advertise it, or because powerhouse Linux distros have spread the word for other fonts like Nimbus Roman or Liberation Serif. Whatever the case, I think that it’s a shame that Linux Libertine remains in the shadows.

Reasons why you should use Linux Libertine:

  • It supports thousands of Unicode characters, which makes this font the best font to view all Western languages (including Cryllic).
  • It comes with an OpenType variant, “Linux Libertine O” (which is the one I use anywhere OpenType is supported)
  • It supports vritually all ligatures like “fi”, “ff”, “fl”, etc.
  • If you use Linux Libertine O in Firefox, Firefox will automatically put in ligatures for “fi,” “ff,” etc — but you will still be able to search through text as if they were their originals (i.e., ligature substitution is transparent to the user). This feature alone has made reading text zoomed at 150%-200% a pleasure — suddenly, larger text looks better.
  • It is open source (the fonts are generated from source code — which is GPL’d). This means that (1) this font will never die, and (2) this font will constantly improve over time.
  • It already looks asthetically far better than Times New Roman, yet it is not overly flamboyant like Garamond.
  • It has a good x-height, so it’s easy to read.
  • It has support for old-style figures (OSF). It even has variants for proportionally-spaced and non-proportionally spaced numerals (for both regular and OSF digits), making this an excellent choice for typesetting documents that deal heavily with numbers and tables.
  • It works beautifully well with XeTeX (fontspec)/LaTeX, and even comes with its own TeX package called “libertine”, making its symbols/glyphs easily programmable.
  • It comes with a TrueType (TTF) variant as well, so you can still use it in older programs.
  • It even has a glyph for Linux’s mascot, Tux (at codepoint U+E000)!

I can’t think of any cons. Its free, open-source nature makes it belong to the elite club of universally available, robust, free fonts (such as Latin Modern). Its robustness, versatility, and inclusion of numerous OpenType features make it easily the leading open-source serif font in the world.

UPDATE July 30, 2011: Grammar fixes; some sentences reworded.

Updated Autolily Script

UPDATE July 24, 2010: This post is now totally obsolete. See this post instead.

This is an update to my previous post. Now, Autolily’s single argument is no longer required to be the bare *.ly filename itself, but instead may optionally include a path! See the embedded comments in the source code below. Enjoy!


 1 #!/usr/bin/ruby
 2 #===============================================================================================================#
 3 # Program name: Autolily                                                                                        #
 4 # LICENSE: PUBLIC DOMAIN                                                                                        #
 5 # This program takes 1 argument, the name of a lilypond file (*.ly), and watches it for changes every 1 second. #
 6 # If there has been any change, it simply calls lilypond on it to create a new .pdf/.ps/.midi of it.            #
 7 #                                                                                                               #
 8 # Place this script somewhere, like in ~/scripts                                                                #
 9 # Then, open up a terminal and call it like so: ~/scripts/autolily.rb [file]                                    #
10 # [file] must be a LilyPond file (.ly), but it can be located anywhere -- i.e., you may include paths in your   #
11 # file, such as "~/sheet-music/classical/bach2.ly" or "../../bach3.ly".                                         #
12 #                                                                                                               #
13 # You might want to do a "sudo ln -s" of autolily.rb to one of your system's $PATH directories (e.g., /usr/bin) #
14 # to avoid typing out the path to autolily.rb every time you use it. Continuing the example from above,         #
15 # something like "sudo ln -s ~/scripts/autolily.rb /usr/bin/autolily" should do (make sure that                 #
16 # /usr/bin/autolily does not exist already, as the above comman will overwrite that file if it exists).         #
17 #                                                                                                               #
18 # Now you can just do:                                                                                          #
19 #                                                                                                               #
20 #     autolily [file]                                                                                           #
21 #                                                                                                               #
22 # from anywhere in your system!                                                                                 #
23 #                                                                                                               #
24 # To exit, press CTRL-C.                                                                                        #
25 #===============================================================================================================#
26
27 if ARGV.size > 0
28     file_data_orig = ""
29     file = ARGV.shift
30     pathsize = file.split("/").size
31     ls_call = "ls --full-time"
32
33     # make sure that the "file" variable is a filename, and not mixed with its path
34     if pathsize > 1
35         path_to_file = file.split("/").first(pathsize - 1).join("/")
36         file = file.split("/").last
37         ls_call << " #{path_to_file}" # modify our `ls` command to reflect relative location of file
38     end
39
40     `#{ls_call}`.split("\n").each do |line|
41         if line.split(/\s/).last == file
42             file_data_orig = line
43             break
44         end
45     end
46     file_data_new = ""
47
48     # enter infinite loop -- keep compiling the given lilypond file if it has changed in the past 1 second
49     while true
50         # detect the file size and also timestamp
51         lsarr = `#{ls_call}`.split("\n")
52         lsarr.shift # get rid of the first line, since that is the size of all the files in the directory
53
54         # find our file from ls's output!
55         lsarr.each do |line|
56             if line.split(/\s/).last == file
57                 file_data_new = line
58                 break
59             end
60         end
61
62         # if there is any change detected, run lilypond on it
63         if file_data_orig != file_data_new
64             puts "\n\e[1;4;38;5;226mAutolily: Change detected in given file; invoking lilypond...\e[0m\n"
65             if pathsize > 1
66             `lilypond "#{path_to_file}/#{file}"`
67             else
68             `lilypond "#{file}"`
69             end
70             file_data_orig = file_data_new
71         end
72         sleep 1
73     end
74 else
75     puts "No .ly file specified.\n"
76 end

Linux Dual Monitor Setup: Nvidia & Xinerama Guide: Rotating just one monitor

I have 2 LCD monitors (both are widescreen) hooked up to an Nvidia card in Linux. For a while, I rotated both of them into a “portrait” view, because, aside from the other benefits a portrait view can give (to webpages and documents), putting two widescreens on a landscape configuration takes up too much horizontal space.

But yesterday, I decided to take a hybrid approach and put my left monitor in landscape view, but my right one into portrait view — i.e., I only wanted one monitor rotated 90 degrees. Of course, this is fairly straightforward in Windows with the proprietary Nvidia utility, but it takes a little bit of work with Linux. I googled around a bit, and found this page. I couldn’t really understand what was going on by just looking at the sample xorg.conf file on that page, so I decided to write out my usual in-depth explanation on the matter.

First, to get this hybrid approach, you have to use Xinerama, and NOT Nvidia’s popular TwinView utility/configuration. This is because TwinView (in Linux) only allows you to rotate BOTH monitors together in the same direction.

The only thing you have to do is edit your /etc/X11/xorg.conf file. First, if you already have TwinView set up to work in a dual monitor configuration, you have to run sudo nvidia-settings, and then change from “TwinView” to “Separate X screen” under the “X Server Display Configuration” settings, like so:

2009-10-04-133053_914x657_scrot

The reason we do this (if you already have nvidia-settings installed) is because it auto-generates a working xorg.conf for us. The thing is, under TwinView, you just have 1 option for everything in Xorg — i.e., you just have Device0, Screen0, Monitor0, but now with the “Separate X screen”, you have Device1, Screen1, etc. Not only that, but your old, irrelevant TwinView settings will be automatically deleted or commented out, so it will save you a couple minutes of work (and any typos as well — typos will prevent X from booting!). After that, it’s just a matter of tweaking the xorg.conf file to suit your needs. (BTW, the reason why the right monitor looks like it’s not aligned vertically correctly with the one on the left is because of a manual adjustment — it’s the 333 pixel shift adjustment I made; read on below for more on that).

Here is my current, working xorg.conf with just 1 monitor rotated:

Section "ServerLayout"
Identifier     "Layout0"
#Screen      0  "Screen0" RightOf "Screen1" # put it on the RIGHT (other options are Below, Above, LeftOf, RightOf;
# alternatively, you can put an absolute, pixel X and Y offset (so RightOf
# would be 1680 0
Screen      0  "Screen0" 1680 0 # NOTE: Screen 0 MUST be defined BEFORE Screen 1!!!
Screen      1  "Screen1" 0 333 # put this screen on the top left, but adjust it down a little bit to match the portrait screen on the right
InputDevice    "Keyboard0" "CoreKeyboard"
InputDevice    "Mouse0" "CorePointer"
EndSection

Section "Files"
EndSection

Section "Module"
Load           "dbe"
Load           "extmod"
Load           "type1"
Load           "freetype"
Load           "glx"
EndSection

Section "ServerFlags"
Option         "AutoAddDevices" "False"
Option         "Xinerama" "1"
EndSection

Section "InputDevice"

# generated from default
Identifier     "Mouse0"
Driver         "mouse"
Option         "Protocol" "auto"
Option         "Device" "/dev/psaux"
Option         "Emulate3Buttons" "no"
#Option         "ZAxisMapping" "4 5" # for the Logitech MX 400
EndSection

Section "InputDevice"
Identifier     "Keyboard0"
Driver         "kbd"
Option         "XkbModel" "pc105"
Option         "XkbLayout" "us,fr,de"
Option         "XkbOptions" "grp:shifts_toggle"
EndSection

Section "Monitor"
Identifier     "Monitor0"
VendorName     "Unknown"
ModelName      "Acer X222W"
HorizSync       31.0 - 81.0
VertRefresh     56.0 - 75.0
Option         "DPMS"
Option         "Rotate" "Right" # for portrait mode
EndSection

Section "Monitor"
Identifier     "Monitor1"
VendorName     "Unknown"
ModelName      "Acer X222W"
HorizSync       31.0 - 81.0
VertRefresh     56.0 - 75.0
Option         "DPMS"
EndSection

Section "Device"
Identifier     "Device0"
Driver         "nvidia"
VendorName     "NVIDIA Corporation"
BoardName      "GeForce 8800 GTS"
Option         "RandRRotation" "on"
BusID          "PCI:1:0:0"
Screen          0 # i.e., the monitor on the RIGHT (physically)
EndSection

Section "Device"
Identifier     "Device1"
Driver         "nvidia"
VendorName     "NVIDIA Corporation"
BoardName      "GeForce 8800 GTS"
BusID          "PCI:1:0:0"
Screen          1 # the monitor on the LEFT (physically)
EndSection

Section "Screen"

Identifier     "Screen0"
Device         "Device0"
Monitor        "Monitor0"
DefaultDepth    24
Option         "metamodes" "DFP-0: 1680x1050 +0+0"
SubSection     "Display"
Depth       24
EndSubSection
EndSection

Section "Screen"
Identifier     "Screen1"
Device         "Device1"
Monitor        "Monitor1"
DefaultDepth    24
Option         "metamodes" "DFP-1: 1680x1050 +0+0"
SubSection     "Display"
Depth       24
EndSubSection
EndSection

Probably the most important options are the “Screen” options under the “ServerLayout” section — these define which monitor starts where, and the relationship between the two monitors. The “Screen” options are defined by a X-axis (horizontal) and Y-axis (vertical) offset — you can only use positive numbers, I think, and so this means that if a screen is defined as “0 0”, it is on the top left corner of the imaginary monitor “plane,” so to speak. I.e., increasing the X-axis offset moves your screen to the right, whereas increasing the Y-axis offset moves your screen down. For me, my left monitor is slightly adjusted down by 333 pixels, so that it matches up smoothly with my rotated monitor on my right (my setup, physically, looks like a sideways “T”). I’m not sure if the “RandRRotation” option is necessary — it probably is not — I’m too lazy to check after fiddling with my xorg.conf all day yesterday. The other options should be self-explanatory, along with the comments.

 

Here are some of the not-so-obvious details: for me, my “DFP-1” is my LEFT monitor and “DFP-0” is my RIGHT monitor. Apparently, the “primary display” is by default DFP-o (e.g., in Windows, the Nvidia utility detects DFP-o (my RIGHT monitor) as screen “1 of 2”, so I have to manually set DFP-1 (2 of 2) as my primary screen) — the only reason why I have it like this is because for some reason, my BIOS stuff shows up on DFP-1, and not the default “primary” DFP-0, and I’ve always liked my BIOS to show up on my LEFT screen by default — hence the reason why DFP-1 is on my left and DFP-0 is on my right. I hope that made sense. It probably didn’t, so here is a screenshot:

Each monitor has a resolution of 1680×1050, but now, my virtual desktop has a 2730×1680 resolution (1680 + 1050 = 2730). DFP-0 is physically rotated so that the bottom side sticks out to the far right — i.e., it’s rotated counter-clockwise 90 degrees — so that the clean, button-less bezel of its top area matches up nicely with the unrotated DFP-1. And so, we rotate “Right” under the “Monitor” section for Screen 0. This is probably the most sensible way for most people, since almost all monitors that do have buttons at all (to make an uneven, fatter bezel where the buttons are) have them at the bottom of the monitor.

Here are the advantages that you get with Xinerama in the above setup:

  • Moving the mouse from the right to the left is always continuous and seamless. This is even true when moving from the far edges of the portrait monitor into the widescreen one (see notes in screenshot). Finally, the virtual screen behaves EXACTLY like how the monitors look in the real world. (This behavior is available in Windows; however, there are two shortcomings that are not found in Xinerama: (1) when the mouse is on the top or bottom edge of the portrait monitor, your mouse becomes “stuck” and does not transition smoothly over to the widescreen monitor on the other side (see screenshot above); (2) even though you can adjust the monitors by simply dragging the icons around (which is very user-friendly, I must say), the adjustments are very course and you cannot adjust things down to the last pixel.)
  • Maximizing a window maximizes to the monitor’s area (i.e., the window maximizes up to either the landscape or portrait view), and not the big, virtual landscape of 2730×1680 pixels; even the applications behave intelligently!

A (temporary) disadvantage:

  • Since I’m using Xmonad as my window manager, popup dialog boxes automatically spawn to to the top-left of the virtual screen — i.e., if they’re small enough, they fit entirely into the unviewable area on the top edge. I have to manually flatten the image into the tiled area to see the contents of it. However, this is Xmonad’s fault, and there is probably a hack out there to fix this sort of thing. Even so, since I don’t really use GUI applications that have a lot of popup dialog boxes in the first place, this is a non-issue.

For a long time I thought that Xinerama was an ATI thing, but apparently, it works for Nvidia as well. The xorg.conf layout looks much nicer, and simpler with Xinerama, and is much more flexible with it (e.g., the 333 pixel shift). If you change the few lines in my xorg.conf above that deal with rotations, you could even do without TwinView as well and just use Xinerama for a basic dual-head setup without any rotated screens.

Minor Update, February 25, 2010: A comment in the screencap was incorrect. Thanks Bela!

(Belated) Update November 4, 2010: Removed obsolete bugs and workarounds (In short, commit 21ed660f30a3f96c787ab00a16499e0fb034b2ad was introduced in into the xserver code in the spring of 2010, and fixed this issue of left vs. right monitors b). Xorg 1.8.1.902 works perfectly fine with either monitor being rotated into portrait mode.

Update June 20, 2012: Nvidia driver version 302.17 has made some changes to how you describe which monitor to rotate. Here is my current Xorg file, called “10-dual-monitor-hybrid.conf” which lives under /etc/X11/xorg.conf.d:

Section "ServerLayout"
    Identifier     "Layout0"
    Screen      0  "Screen0" 0 0 # NOTE: Screen 0 MUST be defined BEFORE Screen 1!!!
    Screen      1  "Screen1" 1050 295 # push this screen down (vertically) 295 pixels from the top to match the portrait monitor on the left
    Option         "Xinerama" "1" # dual-head won't work properly without this!
EndSection

Section "Monitor"
    Identifier     "Monitor0"
    VendorName     "Unknown"
    ModelName      "Acer X222W"
    HorizSync       31.0 - 81.0
    VertRefresh     56.0 - 75.0
    Option         "DPMS"
EndSection

Section "Monitor"
    Identifier     "Monitor1"
    VendorName     "Unknown"
    ModelName      "Acer X222W"
    HorizSync       31.0 - 81.0
    VertRefresh     56.0 - 75.0
    Option         "DPMS"
EndSection

Section "Device"
    Identifier     "Device0"
    Driver         "nvidia"
    VendorName     "NVIDIA Corporation"
    BoardName      "GeForce 8800 GTS"
    BusID          "PCI:1:0:0"
    Screen          0 # i.e., the monitor on the LEFT (physically)
    Option "NoLogo" "1"
EndSection

Section "Device"
    Identifier     "Device1"
    Driver         "nvidia"
    VendorName     "NVIDIA Corporation"
    BoardName      "GeForce 8800 GTS"
    BusID          "PCI:1:0:0"
    Screen          1 # the monitor on the RIGHT (physically)
    Option "NoLogo" "1"
EndSection

Section "Screen"

    Identifier     "Screen0"
    Device         "Device0"
    Monitor        "Monitor0"
    DefaultDepth    24
    Option         "metamodes" "DFP-0: 1680x1050 +0+0 { Rotation=left }"
    SubSection     "Display"
        Depth       24
    EndSubSection
EndSection

Section "Screen"
    Identifier     "Screen1"
    Device         "Device1"
    Monitor        "Monitor1"
    DefaultDepth    24
    Option         "metamodes" "DFP-1: 1680x1050 +0+0"
    SubSection     "Display"
        Depth       24
    EndSubSection
EndSection

Notice that the screen rotation settings are now taken care of under the “metamodes” option in the “Screen” section of the monitor you want to rotate. The recent Xorg versions do not use the usual /etc/X11/xorg.conf file any more (it has been like that for many months).