2005-08-29

My favorite bug fix of all time

My favorite bug fix of all time was finding a very subtle bug in a game that I was hired to finish. The developer had written the game, but it was buggy, and the publisher hired me to fix all the bugs. This is about eight years ago.

The original code, which had the biggest section of copy-and-paste coding I had ever seen (that's where someone wants to make a small change without altering the original code, so they copy a whole bunch of code, paste it in, and then make the small change), would crash once in a while.

BTW, the hunk of copied code was so big, that for a long time when I was debugging, I would set a breakpoint in the wrong function, and it took a while for me to realize that there were two GIANT functions, nearly identical to each other.

But ... the best part, which I am proud of, was that the code, which ran under Windows 3.1, had a little pointer which traced through some byte-code language the developer made up. Every once in a while, it returned garbage.

After much thinking, I remembered that on Intel chips (back to the 8086), there is a subtle bug in the actual hardware, where if you move a pointer from one 64k segment to the next, it can sometimes wrap around, and return the wrong value. At the time, nobody had to do this anymore, because Windows 95 was the rage, but when this program had first been written, it was written in 16-bit mode, and it actually tripped over this hardware 'feature'. I'm not even sure why I knew about this bug in the hardware (which I'm sure has been faithfully replicated in every Pentium chip since the original 8086). I must have read about it years before.

So, I tweaked the code slightly to be more careful when crossing a segment boundary, and all was well.

My second favorite bug fix had to do with putting a "Sleep(500)" statement into any program doing Microsoft DirectX processing in a window that was not the main window, just before shutting down the app. This was necessary because DirectX, back in the day, was hacked on top of Windows, and wasn't integrated into Windows. A little program called DDHelp.exe would keep track of which windows were open, and make sure DirectX resources were freed up when your program crashed or shut down, except it frequently screwed up.

Microsoft even published a free program for developers that would kill off DDHelp.exe when things got fubar. This didn't really fix anything, because often times the driver would hang onto to all your texture memory or whatever, but it often allowed you to put off rebooting your machine for awhile.

Anyway, my fix was better. As long as your program didn't flat out crash, by putting in the Sleep statement right after you destroyed your drawing window, you would allow this DDHelp.exe program to notice that you destroyed the window, and clean up. If you didn't give DDHelp.exe time to run, then when it tried to clean up, key information from Windows was already gone, and so, well, no clean up, thus heading you toward an early reboot.

This turned out to be important, because while many games ran in the primary window, any graphic program that, oh say, drew into a browser window, was going to have this problem. In fact, any DirectX program that ran with MFC was going to have this problem.

I wrote an article about it that still gets hits.

I don't know if I have a third most favorite bug. One thing about a favorite bug is that it is important that I didn't create it! It's only cool to fix someone else's subtle screw up.

© 2005 Stephen Clarke-Willson - All Rights Reserved.

No comments:

Post a Comment