Protect your tomcat, protect your business

In a typical Apache / Tomcat configuration with mod_jk, outside of keeping your software stack updated with the latest versions there are a few easy steps you can take to help protect yourself against basic scripting attacks.

1. Disable any Apache modules you are not using.

Usually by default everything is enabled. You can disable unnecessary modules by commenting the LoadModule lines in your httpd.conf which refer to the unwanted modules, and then reload Apache. In particular, disable mod_cgi if you don't need it since it is a popular attack vector. On Ubuntu, there are helper scripts: a2enmod and a2dismod, these add and remove symlinks to the modules in your modules directory which essentially do the same thing as commenting/uncommenting the LoadModule lines.

2. Obfuscate your Server header.

An attacker that doesn't know what webserver or app server you are running is far less likely to be successful in attacking you. The default behaviour in both Apache and Tomcat is to advertise the full name and versions, and there is no need to reveal this information to the big bad Internet.

In a large organisation the topology will probably be many Tomcat instances (maybe hundreds), few Apache servers (probably less than 10), and a single load balancer in front of the Apache servers. So logically, it should take the least amount of administrative effort to rewrite the Server header in the http response as it passes through the load balancer. This could be done on a Netscaler using a lobal rewrite policy as follows:

add rewrite action RW_ACT_ServerHeader replace "http.RES.HEADER(\"Server\")" "\"yourdomain.com Web Server\""
add rewrite policy RW_POL_ServerHeader "http.REQ.HOSTNAME.CONTAINS(\"yourdomain\")" RW_ACT_ServerHeader
bind rewrite global RW_POL_ServerHeader 10 -type REQ_OVERRIDE

Of course this configuration varies wildly between load balancer manufacturers who seem to all like having their own unique syntax and terminology for things. If you don't manage your load balancer you could make some changes to Apache described here to change your header to read "Apache", which is somewhat better.

Using mod_security you can rewrite the Server header to anything you want. Keep in mind though that a really determined hacker will use other tricks to discover your flavour of webserver.

3. Catch bogus requests at the Apache layer and 404 them, instead of letting Tomcat deal with it.

In our logs at work we often see lame hacking attempts consisting of many thousands of requests per hour for nonexistent URLs like:

/phpadmin.php
/wp-admin.php
/admin.cgi?imahacker=true

Our webapp has the ability to handle 404 errors and render a pretty page in the correct language with navigation back to the important parts of the site, but in the case of these brute force URL attacks we don't want to waste CPU cycles on the Tomcat server rendering a nice 404 page. Instead we will catch them on the Apache layer and display a static 404 error page so that Tomcat can carry on with serving the important traffic.

Creating a custom 404 error page with your own branding on it is optional, but nice in case a real customer ever does end up on one, its also another way to disguise that you're running Apache underneath. So the first step is creating the static 404 error page if you don't have one, and dropping it in your DocumentRoot somewhere like /error_pages/404.html, then configure Apache so that it can serve this file. First in the httpd.conf:

ErrorDocument 404 /error_pages/404.html

mod_jk also needs to know that Apache should serve the file, so in your uriworkermap.properties jk unmount it:

!/error_pages/*.html = lb

Once you have reloaded your Apache configuration, this will then become your Apache server's default 404 error page. The last step is to add a rewrite rule to cover some of the common file extensions that hackers look for. You can do this using a RewriteRule sending the requests to the static 404 page, however this will result in a 200 status code. It's better for your log analysis if these are correctly logged as 404s, and that can be done with RedirectMatch (which is part of mod_alias, rather than mod_rewrite), since you're not allowed to use [R=404] in a RewriteRule ... Apache will just ignore the line if it's not a 3xx statuscode:

If the status code is outside the redirect range (300-399), then the Substitution string is dropped and rewriting is stopped as if the L flag was used.

The below RedirectMatch will catch URLs ending in .pl, .php, .exe, .sh etc .... with or without a query string afterwards, and send them to the Apache 404 ErrorDocument:

RedirectMatch 404 ^(.*)\.(pl|php|exe|sh|dll|bat|py|shtml|cgi)(\?.*)?$ 

You may also want to add asx, asmx, and any other types you have never used and never intend to use.

4. If you are not using cgi, disable it.

This was mentioned above with disabling unused modules. At work our Apache logs show we occasionally get bombarded with bogus /cgi-bin/ requests, so we have another rule in place to catch these http requests and send them to the static 404 error page:

RedirectMatch 404 /cgi-bin/(.*)

5. Other clever stuff

Defensive coding is the best thing you can have! By that I mean an application which has sane validation of all input fields, and will safely ignore requests outside of known boundaries without throwing an error 500 or behaving in an unexpected way. Of course, its very difficult for developers to think of all scenarios.

Application firewalls are a good way to go, the obvious one being mod_security for Apache, though if you are going the mod_security route be prepared for a lot of heavy reading for a correct implementation.

Patching known vulnerabilities seems an obvious one to mention, however you may not realise you are vulnerable without some kind of regular penetration testing. If you don't use a third party service for security scans, why not run your own security scans with Metasploit and work from there ... after all that is probably exactly what your neighbourhood hacker is doing.

Enhancing your tomcat init script

Here's a little enhancement you can make to a tomcat startup script, which adds a quick and easy way to get a heap dump from a running instance. Adding this option makes it easy to then direct someone over the phone or over email to dump the heap and restart a tomcat.

heapdump)
 PID=$(/bin/cat $CATALINA_PID 2> /dev/null)
 if [ -z $PID ]; then echo "Error getting the PID, could not dump heap."; exit 1; fi
 echo -n "Trying to dump heap. "
 FILE=/var/tmp/$(basename $0)-${PID}-$(date +%d%m%Y).hprof
 $JAVA_HOME/bin/jmap -dump:file=${FILE} $PID
 if [ -f $FILE ]; then
 echo "Heap dump taken on $(hostname --short) for instance $INST: $FILE" | mail -s "Heap dump successful" youraddr@yourcompany.com
 fi
 ;;
 *)
 echo "Usage: $0 [ start | stop | restart | heapdump ]"

Assumptions: that you have JAVA_HOME and CATALINA_PID defined in your init script, and that /var/tmp/ is a valid location, and that INST is the directory where your tomcat lives. It will also email an address with the location of the hprof file if successful.

Disclaimer:  jmap might not always work as expected if the JVM in question is completely fubared. If you wanted to, an alternative could be having the script dump the heap by invoking the dumpHeap operation in JMX, within the com.sun.management:type=HotSpotDiagnostic mBean. This could be done using a JMX command line client like jmxterm.

Script to check SSL Certificates

A downstream service that was being consumed at work had an expired SSL certificate and it caused complication for our application. The knee jerk reaction once the dust had settled was to make sure that everything was in order with our own certificates.

I wrote a script which uses the openssl tool to check a list of SSL certificates (in certs_to_check.txt) and output the details to a pipe delimited document, which is then imported into Confluence (wiki software) as a table format using their java CLI tools. I've also added some wiki markup in the output document which colorises the page, putting the status in red or green depending on the validity of the certificate. This then becomes a central place to check on the status of our certs, rather than having to remember where each certificate is installed, and assume that some alerts will fire from there when they are near expiry.


#!/bin/bash
echo "||Certificate||Expiry date||Status||Days to expire||" > /usr/vchecker/results
for name in $(cat certs_to_check.txt); do
 cert=/usr/vchecker/working/${name}.cert
 openssl s_client -connect ${name}:443 > $cert <<EOD
^D
EOD
 returncode=$(grep 'return code' $cert)
 if [ "$(echo ${returncode} | grep -c 'ok')" -lt 1 ]; then
 valid="{color:red}Not Valid{color}:${returncode}"
 else
 valid="{color:green}Valid{color}:${returncode}"
 fi
 expiry=$(openssl x509 -in ${cert} -noout -enddate | cut -d'=' -f2 | awk '{print $2 " " $1 " " $4}')

 # figure out number of days until the cert expires
 # convert expiry date to epoch time
 epochExpirydate=$(date -d"${expiry}" +%s)
 epochToday=$(date +%s)
 secondsToExpire=$(echo ${epochExpirydate} - ${epochToday} | bc)
 daysToExpire=$(echo "${secondsToExpire} / 60 / 60 / 24" | bc)
 echo "|${name}|${expiry}|${valid}|${daysToExpire}|" >> /usr/vchecker/results
done

The resulting wiki page looks something like this:

Example wiki page

Example of report uploaded to confluence

If you wanted to you could also add some alerting into the script, for example for certificates with less than 30 days to expiry:

daysToExpire=$(echo "${secondsToExpire} / 60 / 60 / 24" | bc)
if [ "${daysToExpire}" -lt "30" ]; then
 echo "Warning: SSL Certificate ${name} has ${daysToExpire} until expiry." | mail -s "SSL Certificate warning" someone@example.com
fi

However in our case we are feeding the output file into our central monitoring and alerting system where the alerting is handled in a unified way.

Use ProxyPass for simple site NAT

Say you have a web application on your network running on a Linux box which is published on a high port like 8080, but you want users to access it on port 80. Also in this example, you can't change the port on the application - this could be because it doesn't run as root, or it is hardcoded, or you don't have permissions to modify the config, or anything else.

There are a couple of ways to solve this problem. One could be iptables as a NAT router, described here. If you want to use this approach I would advise a bit of background reading on iptables first, as it's quite easy to lock yourself out of your server if you forget to allow 22/SS, or related/established, or have some other config error or typo somewhere in your rules.

A more simple solution could be using Apache and ProxyPass (mod_proxy) and configuring it to proxy requests based on the hostname. On Red Hat you just need to yum install httpd and configure your site as follows. The mod_proxy module should be enabled by default. In Ubuntu just run a2enmod to enable the module.

<VirtualHost *:80>

	RewriteEngine On
        ServerName yourhost.example.com
        ServerAdmin admin@example.com

        DocumentRoot /var/www

        ErrorLog /var/log/httpd/httpd-error.log
        CustomLog /var/log/httpd/httpd-access.log combined
	RewriteLog /var/log/httpd/httpd-rewrite.log

        ProxyPassMatch ^/$ !
        ProxyPassMatch ^/(.*) http://yourhost.example.com:8080/$1
        ProxyPassReverse / http://yourhost.example.com:8080/

</VirtualHost>

You can also chuck a rewrite rule in there if you want users to land on a specific URI when they hit the document root.

Fix completely broken Juniper VPN on Mac OS Lion

My Juniper VPN was utterly screwed. After a connection failure I was no longer able to reach the login page for the Juniper and I would have to reboot to get my network working again. I had this log event in the log viewer (but not much else):

2012-06-16 11:33:30.130 ncproxyd-admintool[p12223.t4355] adminsession.error Failed to add route: Invalid argument (AdminPrivilegedSession.cpp:831)

To fix it I had to uninstall and completly scrub all trace of the Network Connect client, and then reinstall. For added chances of success, I did the installation using sudo to ensure I was not going to run into any permissions errors. Instructions:

  1. Open Finder - Applications, drag Network Connect to the Trash.
  2. Open up a terminal:
    sudo rm -rf /usr/local/juniper
    find ~ -iname "*juniper*"
  3. Delete all of the files found providing none of these belong to your Parallels VM, using
    find ~ -iname "*juniper*" -exec rm -fr "{}" ";"
  4. Open Finder - Applications - Utilities - Java Preferences
    Note: in recent java updates, this item has moved to System Preferences - Java 
  5. Under security, delete references to the Juniper connection
  6. Under Network, click "Delete files ..." to remove all cached files
  7. If you have Safari open, quit the application.
  8. Open Safari with admin privilege. From a terminal:
    sudo open /Applications/Safari.app
  9. Try and connect to the Juniper VPN again. The app will reinstall, hopefully successfully!

Living with a Mac

So, a few months ago I dumped my Windows PC and replaced it with a Macbook Air. Here is a brain dump of my thoughts, emotions, loves and hates with converting a long-time PC user to Mac OS Lion. This is not a review of the Macbook Air - there are plenty of those around the internet already. This is about my transition from Windows and Linux desktops to Mac.

Design, specs, performance
I've got the 13" MacBooc Air. I'm not going to go on about this too much, but I really love the hardware. It's really exceptionally designed and constucted and feels very solid while only being a tad heavier than my netbook. I do occasionally get static electric shocks from it which can't be too good ... however this is nothing compared to my neighbour in the office who is constantly shocked by his Macbook Pro (at least 4 times a day, much to my amusement). As laptops go the Air quite a thing of beauty, the thinness of it is quite incredible. On a few occasions I have had to go back to my old laptop or netbook for something, and the hardware felt like a pile of crap. Apple did an amazing job with the design and build here - end of story.

Internally it has a 120Gb SSD, 4Gb of RAM and an Intel core i5 1.7Ghz CPU. It boots extremely fast - around 10 seconds from cold to being at my desktop. Apps open instantly when launched and things all move around the screen very quickly and smoothly. Generally I'm very pleased with the performance. It is light years ahead of the old Windows 7 machine it replaced. Battery life is pretty good, about 6 hours if I am not running VMware Parallels. Running a VM will knock off a few hours of battery life. I am not really sure where the fans are on this thing. On a few occasions I've heard them ramp up to cope with CPU going crazy. But in day to day use it is almost completely silent.

On Windows and on Linux, sleep (suspend/resume) has always been a bit hit and miss on laptops, particularly the combination of sleep - undock - wake, or sleep - dock - wake, used to be pretty painful on Windows. On the Mac it works perfectly every time and extremely quickly. The suspend literally takes about 2 seconds, and about the same to wake up. It's nice to put the lid down and have confidence it will always resume properly when you turn it back on.

Keyboard
The keyboard on the MBA feels nice and I enjoy typing on it. I love having backlit keys and dedicated buttons for controlling the bightness of the keyboard and screen backlight. I do have some criticisms about the keyboard layout though.

Apple sacrificed a lot of keys for the laptop keyboard, the most important ones being hash (#) and delete (yes really, there is no delete key), end, home, page up, page down. There doesn't seem to be any way at all to delete text without moving the cursor to the end and then using backspace. Some people on the Interwebz suggested cmd+backspace is a shortcut to delete, but this seems to do something different in every application I've tried it in, and it usually does nothing. I'll come back to the inconsistency of the keyboard shortcuts later. On all laptops I've owned there are a lot of dual purpose keys, but there aren't really any on the Mac aside from the usual selection on the number keys.

I found the missing # key to be the most upsetting though, I spend a lot of time in shell scripts where # is used for commenting code, and pressing alt+3 to get a # is frankly a hassle I don't want. Luckily I did find a solution to that, someone has remapped the totally useless '§' key at the top left to draw a '#' instead, and published the keyboard layout file anyone to download and use. I have never, and never will needed to draw either of these symbols:


Figure 1: Useless key

Inconsistent shortcut keys
On the full size usb keyboard you do get page up and page down, and next to them in the usual home/end position you get a keys with diagonal up/down arrows ... which I assumed were home/end. I'm still not sure what these really are intended to be used for since they map to different functions in different applications. For example in iTerm, they do map to home/end, but in Skype they do a page up/down thing and move your position in a conversation to top or bottom. In Outlook for Mac, these keys just make a system beep, and you have to use cmd+left or cmd+right to replicate home/end,yet in iTerm, Sublime (and other apps) cmd+left/right key combos either do nothing or do something entirely unexpepected. Blah blah etc etc, so basically, forget about home/end keys, unless you want to learn a special key combination for every application. Also forget about delete unless you want to buy the USB keyboard for £50, on and also forget about using ctrl for anything, since the cmd key has replaced it for almost everything.

Apple did helpfully publish a guide to this kind of stuff, but unfortuntely it is just totally wrong and should not be read by anyone.

With Apple's reputation for focus on user experience, I'm surprised by how scatty this is. The shortcut keys should be managed at OS level, not at the application level.

close,minimise,maximise
I also have some things to say about these buttons.


Figure 2: Traffic lights

It doesn't bother me at all that these buttons are in the wrong order and at the left side (the wrong side) of the window. I adapted the new locations pretty easily. What does bother me is the behaviour of the buttons. Close and Minimise seem to do exactly the same thing, ie. Close doesn't actually close the running application, it just closes the window leaving the task running in the background. To really exit an application you have to use cmd+q, otherwise it will just 'live' on the dock in some kind of semi-open state. Minimise seems to do exactly the same thing, only with an animation which shows it shrinking into the dock. One of these buttons could surely be removed.

In Windows I used alt+tab a lot to cycle through all open windows. In Mac OS you use cmd+tab and it cycles through running programs, rather than open windows (much like the new behaviour in Unity and Gnome 3). However, if you have minimised a program, when you cmd+tab and select it, nothing happens. I can't really fathom this out, the cmd+tab seems to be a bit pointless to me - if you select it but not activate it with cmd+tab, it should just be removed as an option in the list. Apple have given you some other ways of viewing and managing open tasks though, through the 'expose' view (4 fingers up on the trackpad), and Mission Control which shows you all open Windows for the application currently in focus (4 fingers down on the trackpad). There are also shortcut keys for these on the full size USB keyboard.

Maximise doesn't really maximise windows either, sometimes it will make your window full screen but usually it will only maximise vertically and not sideways, which is really annoying (I'm not the only one who is bugged by this behaviour). In Lion there is a 'full screen' button in the top right of every window, but this is a bit different from Maximise as it really does take your entire screen, making the dock and top menu bar and window controls disappear. Also if you have a second monitor attached, the app becomes full screened on your primary screen, and your secondary monitor becomes useless as it can only show the desktop wallpaper. When you press the maximise button in iTunes, something very unexpected happens that isn't what I wanted when I was watching a video:


Figure 3:
iTunes when maximised

From what I've seen, my complaints about the window buttons are fairly common grumbles from Windows users migrating to Mac. I'll just have to get used to it. Full screen mode is crap until I can use my second monitor for something else.

Software
As a Linux user (and Android) I am used to having a repository full of free software at my fingertips. I kind of had an expectation that the App Store might have a lot of free software in it too. Unfortunately this is not the case. Almost nothing is free. Compared to Windows it can actually be quite hard to find free software for Mac. You will have to hunt around in places like sourceforge to get things that should be free - like VNC clients, simple image editors, etc.

In general I wold say I really enjoy using the OS, but some of the software is not as good as the Windows counterparts. Skype for Windows is better for example. Google Chrome is identical, but often freezes up and requires a 'force quit' after a reboot. Flash plugin sucks and crashes frequently. Outlook for Mac sucks on many levels...  Most of the basic functionality is there, but many key things are missing, like being able to manage mailbox rules, auto archive, book meeting rooms, browse the global address list.

Some apps can be awesome though, Twitter for Mac being one example. A really stylish app which has a nice visual flair.

Time to wrap-up
How could I summarise my transition to a Mac? It really wasn't very hard to migrate. The laptop itself is great. One thing I didn't touch on above is the touchpad, the multi touch gestures you can do on it really enhance the experience, and again, going back to a normal laptop afterwards makes you realise that.

Is a Mac worth the money? I don't know about that. I really like the slim form factor. I would probably be just as happy with a Windows ultrabook. But I am a bit surprised by how much I like Mac OS. Its very pleasant to use despite the criticisms. It's a coherent experience and everything works well, although in a few places the interface is simplified a little too much ... one example being wireless networking. If I could get something more detailed than 'network timeout' when I can't connect to a wireless network it would really improve it, since the Macbook Air doesn't have an ethernet port and debugging broken wireless is critical to getting the laptop working properly.

What about comparison to Linux desktop environments? Well, in my opinion Linux is in kind of a dodgy state at the moment. Compared to Mac OS, both Gnome 3 and Unity are newcomers lacking polish and do not feel refined. Gnome 3 still feels experimental to me, and it seems little thought has gone into the design of it. They seem to have focused more on re-engineering the way you work rather than making it look really nice - the stock themes feel chunky and childish, and the system settings are sparse. I can't really comment on KDE since I was never a massive KDE user, but each time I tried it I never found it very reliable. Mac OS seems to win in a desktop war if I was to pit them against each other in their current forms.

I guess I would be a bit gutted if I had to hand back my Macbook Air now. There are few odd quirks but mostly it was a great exchange. And working from a Unix based platform does make me a little bit happier than using Windows 7.

Improving Skype notifications on Linux

Continuing from the preview blog post on Gmail notifications, I wondered if there was a way to link Skype into libnotify. Skype uses its own notification system by default which doesn't fit with the Gnome / Unity desktop, and looks kind of crappy. I could start a rant about Skype now, and the fact the Linux client never gets updated, seems to silently crash when open for longer than an hour, and is generally a shoddy counterpart to the Windows and Mac versions ... then again since it's been acquired by Microsoft I can't see that this situation is going to ever improve now. Anyway, in the Options, under Notifications, if you select an event and then click Advanced, you can then clear the box that says "send a notification", and select to run a script instead.

Advanced notification options
Advanced notification options

Using the 'Contact came online' event as an example, if you run the following as your 'script', inserting the name of a contact using the %sname variable, it looks like this:

notify-send "%sname is now online" -i skype

And for messages, you can use %smessage to insert the Skype message into a notification popup.

notify-send "%sname" "%smessage" -i skype

Skype message received
Skype message received

Much better!

A list of available variables is here.

Pretty Gmail notifications for Ubuntu

I've recently gone back to Ubuntu (10.11), and in my new installation wondered if there was an app I could install which gave me Gmail notifications via the default notification system (libnotify). I was a bit surprised to find that there wasn't, so I wrote a script in bash that does it:

gmalpopupgmailpopup 

My script also stores your password hashed (unlike some of the alternatives in Software Centre), in a hidden file in your /home.

Installation

To install, run the following:

sudo apt-get install curl gnome-gmail
wget -q -O ~/gmailpopup http://ukstokes.com/scripts/gmailpopup
chmod +x ~/gmailpopup
sudo cp ~/gmailpopup /usr/bin

To configure it just type gmailpopup in a terminal and enter your Gmail address (GApps domains also supported) and password. If you have accidentally fat fingered the password and get an error, you can start again with gmailpopup --reconfigure. On subsequent runs you won't get a popup unless your unread email is different from last time.

This doesn't seem to run if inserted into the crontab. But it works fine if this is added as a startup application:

while true; do ~/bin/gmailpopup && sleep 1m; done &

Of course, this doesn't just work on Ubuntu. Any distro which uses libnotify will do. By the way the gnome-gmail package is just required for the Gmail icon. There is probably a better way of doing that, which I'll have a think about, but installing gnome-gmail has the added advantage of making Gmail your default mail client for mailto links etc. If that is not what you want, go to the "Default Applications" in "System Info" to set it back.

Thats it. Leave me a comment and let me know what you think!

Living with Gnome 3

Here are some tips on how to make Gnome 3 behave a bit more like Gnome 2, to help you transition into this new and unfamiliar territory. Most of them are from this thread on Fedora Forums.

Tip 1: Maximise and Minimise

If you thought Ubuntu were naughty moving the buttons to the left, you aint seen nothing. Gnome completely removed the maximise and minimise buttons. To get them back run the following (as you, not using sudo or su):

gconftool-2 -s -t string /desktop/gnome/shell/windows/button_layout ":minimize,maximize,close"

To see the changes press ALT+F2, press 'r', and hit enter. Your shell will reload without closing any apps and the extensions will be applied.

Tip 2: Remove the accessibility icon from the top panel

This is done by installing the following Gnome 3 extension:

su -c 'yum install gnome-shell-extension-remove-accessibility-icon'

Tip 3: Enable 'Power off' in the status menu

Usually you have to hold ALT to see this, which is frankly bullshit. Luckily this is also easily remedied by installing an extension.

su -c 'yum install gnome-shell-extensions-alternative-status-menu'

Tip 4: Better window management

I don't really like the 'dock' for managing background applications which appears inside the activities area. My advice is to install Docky. Other docks are available such as avant window manager, but I think Docky is the best.

su -c 'yum install docky'

Edit: Docky crashes A LOT for me, on both F15 machines. I am going to try an alternative.
Tip 5: Add programs to 'startup applications'

The dialog box was removed from the settings screen. You can access it by pressing ALT+F2 and typing gnome-session-properties into the box.

Tip 6: Enable desktop icons/shortcuts

Another classic, you can't create shortcuts ANYWHERE in Gnome 3. WTF. But, there is a nifty program in the yum repos called gnome-tweak-tool that can fix that. Install it and then launch 'Tweak Advanced Settings' from the apps menu, then switch 'Have file manager manage the desktop' to ON.

su -c 'yum install gnome-tweak-tool'

Tip 7: Add icons

You might want to add icons for missing things like the gnome-session-properties tool. If you yum install 'alacarte' you get a menu editor (straight from Gnome 2) to create your missing shortcut items.

Tip 8: Change the ALT+TAB behaviour

Alt+Tab changed slightly in Gnome 3. If you have multiple windows of the same type open, for example 2 terminal windows, when you alt tab you only see one of them. Then when you hover over the item in Alt+Tab, the multiple instances are shown. I am indifferent about this but if you want to restore Window based, rather than Application based Alt+Tab, there is another extension to install:

su -c 'yum install gnome-shell-extensions-alternate-tab'

Edit: This extension causes my shell to crash. I wouldn't recommend it.

HTC, you fail.

I'm the owner of a popular Android phone from yesteryear, the HTC Desire. It's been out for almost exactly one year from today and originally shipped with Eclair (Android 2.1), and was later updated to Froyo (2.2).

HTC Desire

HTC just announced via facebook that they will not be updating the HTC Desire any longer. Apparently it doesn't have enough storage space for Android 2.3 (Gingerbread) + HTC Sense 3.0. There are a few angry ways that users could react to this.

First of all, there is the argument that HTC are only refusing to upgrade the Desire because they want users to upgrade to new handsets. Extending the lifetime of their old phones doesn't make them any money. This is at the cost of customer satisfaction though, and it's sad because most users will have 2 year contracts, and like me, had hoped that updates would at least carry on for the length of your contract since this was one of HTC's flagship phones. I've owned my phone for a whole year already, but I would be pretty pissed off if I had bought it recently to then discover HTC had abandoned it. What version of Android will be out one year from now, and what will the resale value of your Desire be if the Android version is 18 months out of date?

Secondly, the Nexus One, which is basically a Desire in a different shell with a trackball, is quite capable of running Android 2.3. Google pushed it out a few months ago.  So it seems to be clear that the problem is HTC Sense, it has become too bloated and no longer fits on the small storage of the Desire. In an ideal world they should give us the upgrade option of Android 2.3 without Sense.

Thirdly, there are TONS of Android 2.3 roms that include HTC Sense on XDA. The fact that these exist and work perfectly well as a daily rom helps to argue the point that HTC's reasons for abandoning the Desire are a load of crap. Whether you root or not, you can see that this phone is capable of running Gingerbread.

Finally, there are the rooters. They don't care; they have been running Android 2.3 on the Desire for 6 months already. But it's been a tough journey - HTC went out of their way to lock the bootloader and the nand (storage), to make flashing custom roms difficult. Without groups like AlphaRev we would not have freedom to install whatever we like on our Desires and we would be chained to Froyo for the lifetime of our phones. It's sad because shouldn't have to be this way. Normal users will not hack their phones to run CyanogenMod. They will be stuck on Froyo for the remaining lifetime of their phones. They won't get any of the new features of Android, bug fixes, or security updates, and to me that just seems wrong.

Update: Apparently HTC will bring Gingerbread to the Desire after all. We'll see.