Many years ago, some friends and I decided to build a robot. Dean was the primary hardware guy, and I was in charge of writing most of the software. The robot was a pretty ambitious undertaking that we never finished because most of the development team (four of us) moved away or had to spend our time on other more pressing things.
Early on in the development, Dean was wirewrapping the main logic board (Z-80 based) and I was writing the firmware on a CP/M system. By the time he had the board wirewrapped, I had the first cut of the base code finished. We burned the firmware into an EEPROM, did what bench testing we could, and then plugged the board into robot. After checking all the connections, including the RS-232 cable that we would use to control the robot during this test, we all stepped back and Dean turned on the power.
The robot’s motor came from an electric lawn mower, and the power source was a very high capacity lead-acid battery. We’d done some testing of the drive train earlier and learned that the thing was capable of some rather high speeds. Probably overkill for a little robot, but we figured we’d never tell it to go that fast. Little did we know . . .
Dean turned on the power and the robot took off across the shop like a rocket. 10 feet away from the bench, the RS-232 connector disengaged and the robot continued the rest of the way across the room and smacked into a wall. Where it stayed, its wheels spinning madly while the four of us rolled on the floor, laughing.
After picking ourselves up off the floor and turning off the robot, Dean turned to me and said, “Doesn’t your software turn off the motor at boot like I told you?”
Me: “I thought so!”
Sure enough, we looked at the code, which read:
start:
; turn off the drive motor
xor a
out (DriveMotor),a
Dean’s instructions to me at the time were, “You control the motor’s speed by outputting a value from 0 to 255 to the motor control port.” So I figured that 0 would be the lowest possible speed (i.e. stop), and 255 would be “shoot across the room like a rocket.”
Of course, Dean looked at that code and saw the problem immediately. If he explained to me why he’d designed the logic so that 255 was stop and 0 was “go like a bat out of hell,” I don’t remember the specifics. All I know is that I thought that doing things backwards made little sense.
People often look at me funny when I ask them today for clarification. A music player API, for example, might have a Volume
property that’s documented as taking a number from 0 to 100. When I ask the author if 0 is mute or max, he rolls his eyes and says, “mute, of course.” Usually. But over the years I’ve run into a few backwards APIs similar to the robot’s drive motor, most often when dealing with custom hardware. I’ve learned the hard way that it pays to be sure, even if it does result in some funny looks from time to time.