Introducing PodSleuth

PodSleuth is a new project I started last May that aims to probe, identify, and expose properties and metadata bound to iPods. It obsoletes libipoddevice, which had the same goals, but due to many reasons ended up being a mess of spaghetti code and hacks due to effectively being obsoleted overnight about a year ago when Apple made a particular firmware release.

PodSleuth takes the many lessons learned from libipoddevice and evolutions of the iPod itself and implements hardware support in a more future proof, yet backwards compatible and easy to maintain way.

The Technical

The core of its design is platform independent, although PodSleuth in its current and complete form is most usable in the context of HAL. A HAL layer is provided that is used now in Banshee, and we would like to see other certain iPod libraries at least optionally support PodSleuth. This layer is implemented as a HAL callout. Because the callout runs as the same user as the HAL daemon (typically root), it is allowed to cleanly perform operations that were implemented as hacks in libipoddevice (like reading from SCSI code pages).

The metadata that PodSleuth collects is then merged into the HAL device as properties. Once the PodSleuth callout ends, HAL finishes probing the device and exposes the iPod on the Global Device List (GDL) where the mount daemon (i.e. gnome-volume-manager) will then mount the iPod in a manner accessible to the user session. The key here is that by the time the iPod is exposed on the GDL, all PodSleuth properties will have been merged into the device. This makes application and user session library support for PodSleuth properties very easy and straight forward. One need only check for org.podsleuth.version on the device to check if PodSleuth ran against the device. If that property exists, other properties will be available that expose iPod metadata.

if (device.PropertyExists ("org.podsleuth.version")) {
    // We have a PodSleuthed iPod, it's ok to expect 
    // at least the minimum set of properties

    Console.WriteLine (String.Join (", ", device.GetPropertyStringList 

One of the most important changes that affects the end user directly is that the iPod will always be supported based on metadata extracted from the plist file located in the SCSI code pages. This means that even if the iPod is not found in the model table, no functional limitations will be imposed. That is, the model table is now only purely cosmetic (for presenting things like shell color and the right icon). This is in contrast to earlier versions of libipoddevice.

Additionally, PodSleuth sets the info.icon property in HAL which means that once we get new icons for the new iPods and update the existing ones to follow the new required naming specification, the proper iPod icon will finally show up in Nautilus and elsewhere (provided you are running a recent enough GNOME). A cute thing indeed.

The Files

PodSleuth will see its first official release within the next week, alongside a new ipod-sharp release, and Banshee 0.13.2. All of these releases spell out support for new iPods (Classics and Nanos), so stay tuned. PodSleuth is developed in GNOME subversion under the podsleuth module.

The Unfortunately Political

The fun part is that PodSleuth is written in C# of course, a detail that I like to think doesn’t matter, but it certainly and most unfortunately offends many for various reasons. There are two lovely facts that I like to point out when opposition to my language of choice for this project arises:

  • Because PodSleuth is not used as a library, any application written in any language with HAL support can benefit from PodSleuth. I could have written PodSleuth in shell, and it would not affect applications wishing to support it.

    Furthermore, PodSleuth requires only the ECMA approved portions of Mono (which is a 100% open source project and has a strict policy to keep patented code out) and Mono.Posix (which is an open source library wrapping POSIX system calls). Therefore there are no patent concerns (although I know the facts don’t matter to the noisy zealots).

    What matters on the technical side of this point is that most modern distributions ship at least this core subset of Mono these days, so I feel the dependency argument falls apart here as well.

  • My favorite argument against PodSleuth because it is Mono-based comes from the crowd that hates Mono for unfounded political reasons, yet require free software support for their iPod.

    Let’s see, the iPod is closed hardware, proprietary software, contains DRM, supports proprietary formats (doesn’t even have any open format support), and just recently added a hashing mechanism against the primary track database to lock out third party clients. I’m not sure if I’ve ever come across a more proprietary device, yet this zealot crowd has the nerve to scream about Mono!

    This theme is unfortunately all too common in our community (“Oh, it’s OK to run a Mac! Just don’t use Windows! The Mac is shiny too!”).

    In response to this very argument a few days ago in the #banshee IRC channel and mocking what could be seen as a double standard, Jorge Castro quipped,

    “I value freedom so I refuse to use Mono, oh look, a new iPod!”

    So true, so sad. On a somewhat related topic, I recently looked at the APSL next to the Ms-PL. Now that’s funny.

The Bottom Line

There is no reason an application or library focused around iPods shouldn’t support PodSleuth. Regardless of political alignment, PodSleuth is designed in such a way to make it very easy to optionally support. Supporting it technically places zero dependencies on a library or application. If a distribution happens to provide PodSleuth, then why not take advantage of the properties that would be readily available to you? They’re just strings in HAL! If the properties exist, use them. If not, fall back to what you’re doing today.

Think of your users! There’s a very small majority of users out there who will actually care about what a PodSleuth is, let alone what it’s written in. They just want their iPod to work, and PodSleuth provides a very solid hardware metadata layer in a clean language and platform agnostic way. Of course, these users should already be using or are already using Banshee, which has provided this experience from the get-go.

People who care about the political issue and oppose the platform shouldn’t be using iPods anyway, lest they be hypocrites.

Harmony 880 Remote on Linux

A few weeks ago I bought the Harmony 880 Remote from Logitech. The thing is amazing. I cannot run my home theater without it now.

You create an online profile and enter all your hardware from their database. Each hardware profile is fully configurable. If a hardware profile is missing a feature, the remote can “learn” from your OEM remote as it has an IR receiver. Essentially any IR device can be configured to work with the 880 remote. You can create virtual keys – 10 of which can be present in any order on the built in LCD at a time and you can page through more functions. Most features you need for home theater are actual keys on the remote and are organized very well.

Harmony 880 Remote

What’s really fantastic about it is the “Activities” feature. Here you create activity profiles. By this I mean, “Watch Cable DVR,” for example. This profile set my audio receiver to Aux 2, my TV to HDMI, turns my cable DVR to my favorite channel, etc. Audio commands are sent to the receiver, DVR commands to the cable DVR, TV commands to the TV. It’s perfect.

The power of the IR transmitter is tremendous. I can keep the remote with me at my desk, facing in the opposite direction of my audio receiver and another room away (granted, I do have a very open floorplan) and control volume levels. I can lay on my couch with the remote and not worry about pointing it anywhere. It has a motion sensor to detect when it should turn on the button and screen backlights. The thing is just nice.

The problem however, is in its update design. To configure all these settings and niceties you log in to your web-based configuration page and go to town. When you’re ready to update the device, you’re asked to download an EZHex file containing your changes in an XML+Binary blob sort of way. Here comes the trouble. You need to be using Windows or a Mac. I get away with this using my XP VMWare install under SLED, but it’s hardly optimal. Once the file is downloaded, you run it in the EZHex sync program, it contacts your remote over USB, and sends the file. Firmware updates are also delivered in the same way. The same program is also used to somehow read IR commands from the built in IR receiver when you ask the web-baesd configuration program to “learn” a command from an OEM device.

I would love to see a program under Linux that at least supports saving the EZHex dump to the remote. It’d be super-sweet if it could also do OEM IR command learning and firmware updates as well (firmware is probably in the same boat as configuration syncing).

So, I’m ready to donate a cash prize of US$75, which is about 1/2 the price of the 880 remote to the first person that can deliver on a Linux program that implements configuration syncing. Another US$15 if the program supports updating firmware on the device, and finally, another US$60 if the program allows OEM IR command learning. It needs to work with the 880 web-based configuration software of course. If all three features are implemented, I’ll essentially be reimbursing you for your 880 remote. I don’t really care about UI. A console program that does the job is fine with me. The code must be GPL, LGPL, or even better, MIT X11.

I suspect that some debugging/listening will reveal a lot, and it can be implemented fairly quickly using libusb or something. I just don’t have the time to really look into it. It would have been nice if the harmony was a mass storage device and you simply copied your configuration profile and firmware updates to it. Oh well. Maybe Logitech can be contacted and specs can be obtained. That’d be sweet.

That said, once you do get your perfect configuration for the remote, you really have no reason to boot Windows again to do anything with it. You will spend a couple of hours setting it up and tweaking though.

Oh well, I’m still a satisfied customer.

Update: The code must be original, and you of course must be the author. If a utility already exists to sync the 880, I’d appreciate the tip, but it won’t qualify for the prize. :-)

Update 2: Paul Cutler has generously offered to match my US$75 prize for step 1. That is, if step 1 is completed, the total prize is now US$150. Completion of steps 2 and 3 leave the total possible amount at US$225. Start hacking – it’s probably a day or two of work for a full 880 reimbursement!

On the Weekends: A Side of Web

I enjoy web-based design work quite a bit, at least in moderation, and find that dabbling in it over the weekends and on some not-so-busy evenings is a nice break from the normal cycle. I have been working mainly on the Banshee Wiki. It has a new tango-esq theme, and validates as XHTML 1.1/CSS2, which I think is fairly unheard of in a Wiki. I also extended my release monitor extension, which allows pages to have custom tags that expand with information about a tarball release on a given project.

I am working on MediaWiki+WordPress integration for Springboard. Since we use MediaWiki so much, I thought it was only fair to switch my personal site to this same platform combination. My blog is now powered by, *sigh*, yet another WordPress install – but I guess there’s a good reason for its popularity. I am still working on the wiki side of things, but the WordPress theme now pulls in its elements from the common theme I am working on for MediaWiki. This is going to be very nice: two content engines dressed up by a single theme, and sharing data. More on this will follow.

Music Box: Moto

What started as a rebuild of my Networked Music Box, will hopefully be turning into a media PC for my Jeep. I plan on having it sync to my music shares over NFS and 802.11g WiFi, when in range (i.e. pull up in the drive way). It will be able to play back video and music on the system. I’ll be installing a small LCD screen over the glove compartment. The PC will be in the back, and I’ll be using an ATI All In Wonder RF remote, for which I have already written software, to drive the system. It will also be a wardriving system. Maybe a motorized pringles can directional antenna will be in the future too.

I’m sure I’ll be writing some kind of software for this system. I just don’t know what yet. But for starters, I purchased a D-Link DWL-G510 802.11g PCI adapter. I didn’t give much thought to it, but when I installed it, there was no support in Linux 2.6.10. Searching for device drivers for “DWL-G510” yeilded no results other than to use ndiswrapper. I was about to go this route, however, when I was configuring the kernel for the new system, I had taken a look at /proc/pci to see what I needed to enable. I noticed that the chipset for the DWL-G510 adapter was from Atheros Communications. So instead, I searched for drivers for “Atheros.” This yeilded something nice! The MADWiFi project is developing a driver for the Atheros chipset. It’s currently only available through CVS, but I checked the sources out and built the driver without problem. After a little tinkering with interface commands and wifi tools in Linux, I had working WiFi support with the card.

The new system is Slackware 10.1 on top of a custom 2.6.10 kernel. I don’t like the provided rc.wireless RC script, so I wrote a simpler one, tailored to my (basic, current) needs. It may be useful to you!

<br /> #!/bin/sh</p> <p>INTERFACE=&#8221;ath0&#8243;<br /> ESSID=&#8221;My Network&#8221;<br /> CHANNEL=6<br /> KEY=&#8221;FFFFFF&#8221;</p> <p>function start {<br /> echo &#8220;Bringing up wireless interface $INTERFACE ($ESSID)&#8221;<br /> modprobe ath_pci<br /> ifconfig $INTERFACE down<br /> ifconfig $INTERFACE up<br /> iwconfig $INTERFACE channel $CHANNEL essid &#8220;$ESSID&#8221; key $KEY<br /> dhcpcd $INTERFACE<br /> }</p> <p>function stop {<br /> echo &#8220;Bringing down wireless interface $INTERFACE ($ESSID)&#8221;<br /> ifconfig $INTERFACE down<br /> }</p> <p>function restart {<br /> stop<br /> start<br /> }</p> <p>case &#8220;edit_entry&#8221; in<br /> &#8216;start&#8217;)<br /> start;<br /> ;;<br /> &#8216;stop&#8217;)<br /> stop;<br /> ;;<br /> &#8216;restart&#8217;)<br /> restart;<br /> ;;<br /> *)<br /> echo &#8220;usage start|stop|restart&#8221;<br /> esac<br />