Okay, I finally figured this issue out!
I was reading in another thread (
http://www.wreckedgames.com/forum/index.php/topic,904.0.html) where OvermindDL1 said
"Yep, should basically always return true, returning false essentially flushes the buffer of any remaining buffered events." And it occurred to me that that's exactly what's happening.
My application code was sometimes returning false from keyPressed() and keyReleased(), if I didn't process the keystroke. Basically I was returning true if I did something with it, and if it fell through to the end of my handler function I was returning false. It seemed natural and similar to the way CEGUI::System::getSingleton().injectKeyDown(arg.key) returns a bool to tell me if the keystroke was processed. I figured I should be passing that value similarly onward in my keyPressed() function. Looks like I was wrong.

In summary, the "rule" that I've learned is this:
If your input event handler functions (keyPressed(), keyReleased(), mouseMoved(), mousePressed(), mouseReleased()) return false then you are telling OIS to discard the remaining events in the buffer. This should probably only be done when you're quitting your application.
This is not obvious from looking at the simple OISConsole application, and the Ogre demos are similarly built for simplicity. This rule should be clearly stated, perhaps with a source code comment in Win32KeyBoard.cpp, and/or elsewhere.
I have to say this was a very difficult problem to find! I have been searching for over a week now, nearly non-stop. I've debugged, profiled, ripped my code apart, dug into the CEGUI library, etc. It was a painful process, and this is an insidious bug that doesn't show itself except under extreme (and difficult to test) conditions, and even then its effects are intermittent at best.
Anyway, I'm glad this problem is solved! Thanks for the help!