We have been using shared_ptrs pretty successfully throughout our application, but I have run across something that has just completely stumped me. BTW - this is a Windows .NET 2003 + Intel 8.1 compiler compiling in Debug mode on a multi-processor machine (dual Xeon Dell workstation). The code in question is: void Router::routeEnvelope(shared_ptr<Envelope> envelope) { if(!running || !envelope) return; GUID target = envelope->getTo(); if(target == guid) { // PATH 1 // check to see if it is a failure envelope shared_ptr<EnvelopeFailure> envelopeFailure = shared_dynamic_cast<EnvelopeFailure>(envelope); if(envelopeFailure) { // there was a problem sending the original envelope failedEnvelope(envelopeFailure->getFrom()); } // pass it on up the stack envelopeController.injectEnvelope(envelope); } else { // PATH 2 mutex::scoped_lock lock(envelopeQueueMonitor); envelopeQueue.push(envelope); envelopeReady.notify_all(); } } The first envelope that comes in has a guid that matches target, so it takes code path 1. If I comment out both code path 1 and code path 2, the envelope is released properly, and I can see its destructor get called. Here is where it gets strange--if I uncomment anything in code path 2, and only code path 2, I no longer see the envelope get released, even though that code path is not executed at all. I've been doing this testing on an SMP machine. On a UP machine, the program runs fine without any issues. I am at a complete loss. The original envelope object is created in the function that calls this function, and as far as I can tell , is not touched by any other thread in the application. Thanks for any advice. Cheers, tim