The following stacktrace show that ~MidiService clears WinRTWrapper singleton instance in the desctructor. The stacktrace also shows that DeviceCallbacksHandler::detach is called later on in the same thread. DeviceCallbacksHandler::detach “deregisters” the callsbacks that are registered in DeviceEnumerationThread::run. Inside the callsbacks there is for example a call to handlerPtr->addDevice (info). handlePtr could be pointing to a BLEDeviceWatcher instance, and in BLEDeviceWatcher::addDevice there is this call
auto deviceID = WinRTWrapper::getInstance()->hStringToString (deviceIDHst);
… and since the singleton is cleared in the dtor of MidiService, the above call could be a nullptr being dereferenced, since the callbacks are deregistered after the WinRTWrapper singleton is cleared.
I’m not sure I follow. The call to clearSingletonInstance() in the MidiService destructor will clear the MidiService singleton, not the WinRTWrapper singleton. Also, calling getInstance() on a JUCE singleton will create the singleton if it doesn’t exist, unlike getInstanceWithoutCreating(), so there’s no likelihood of dereferencing a deleted object.
but there seems to be a problem with the order of destruction. It seems that WinRtWrapper singleton can be destroyed before the call DeviceCallbacksHandler::detach.
If I put a breakpoint where the WindRTWrapper singleton is cleared:
…then that always happen before the call to DeviceCallbacksHandler::detach (see previous stacktrace in the first post. They both come from DeletedAtShutdown::deleteAll()
I see now, thanks. I’ve pushed a fix to the develop branch here which should cope better in the rare situations where the WinRTWrapper gets deleted whilst the MIDI service is cleaning up.