Last week I decided to get myself a dashboard camera to record crazy things I see on the road while driving. After lots of reading and comparing different cameras, I decided to buy the Itronics ITB-100HD.
There are a couple things about the camera that I’d like to change.
- The onscreen speed output it written in km/h. Since I’m in the USA that doesn’t mean anything to me and I’d rather have it in MPH.
- All video files are saved to the root of the attached SD card. This isn’t really so much a problem as it is an unfortunate implementation detail. I’d like to use an Eye-Fi card with the device so that I can automatically transfer files to my home network when I pull into the garage. More on this later.
I had seen online that there was a guy that spent some time working to make the device display in mi/h instead of km/h. He did some great work, but ended up selling the patched image on ebay rather than sharing the binary with other folks who wanted to do the same thing. Also mi/h, while technically correct is not what I expect when I see a speed. I much prefer MPH since that is how speedometers are typically labeled.
I decided to see if I could reproduce the same type of mod to the firmware that the other guy did, but do it without paying for it, and then share it with anyone else who wanted to do the same.
The device has the ability to update its firmware from the attached SD card slot. It’s as simple as putting the binary on the SD card and booting up the device. I figured that would be a good place to start, so I downloaded the latest v2.1 firmware and got to work. What I found was pretty interesting. I spent some time looking at the binary to see if it was a well known format. It turns out it was a gzip file, which contained a tar file, which contained to gzip files, which contained more tar files. I’ve drawn the structure below to make it a bit easier.
Once you get through the layers of the onion you find out there are a bunch of files in the ipnc folder within the itb100_fw file. Using IDA I was able to disassemble the binaries in this folder and find that there was actually a lot of symbol information in the files, which made it a lot easier. It took me a while to find what I was looking for, but eventually I found a function called AVSERVER_getCurrentSpeed. This seemed like a good place to start and after a bit of time I followed the logic and figured out what I had to do.
If you look at the above code you can see that the getCurrentSpeed function is called from within swosdDisplay. At that point it does some flag check and then prints the current speed. The flag appears to be the flag that sets if the speed is printed on the video or not. I figured I didn’t need that and could steal that code space from 00025F1C -> 00025F28. My goal was to apply a simple medication to the km value that was returned from getCurrentSpeed prior to when it’s used in sprintf. After some quick google searching I found the conversion 1 kilometer = 0.621371192 miles. I just needed to write some new code that multiplied the km value by 0.62137. Here’s what I came up with.
What this basically does is load 636 into R1, then multiply the km value by R1, then divide it by 1024. This essentially multiplies the value by 0.62109375 which is pretty close to the conversion value. It also fits nicely into the space that the old four instructions were using.
I didn’t have an ARM encoder, but had some friends encode the instructions for me so I could drop it into the original binary. There are several tools to do this, I just hadn’t used them before and I’m glad I knew some people who had. Once I had the raw bytes I was able to modify the binary file directly and replace the old code bytes with the new ones.
I wanted to make sure the bytes were right so I loaded the newly modified binary into IDA again to see if the change resulted in the correct disassembly. I’m happy to say after loading the bytes in the wrong order the first time. A quick fix solved the problem and I had the exact code change that I wanted.
The only thing left to do was to find the constant string that was used in the sprintf, and convert the ascii from “km/h” to “ MPH” I decided to add a space for aesthetic reasons.
The final step was to package the whole thing back up in the reverse order of how I unpacked it. tar->zip->tar->zip. The end result is — MPH instead of — km/h. Hopefully this helps other people who want to make this modification.
Download: http://yakhack.com/downloads/itb100hdfw.bin (itb100hdfw.bin v2.1)
Special thanks to the folks that helped out… You know who you are.