# HG changeset patch # User Chris Cannam # Date 1287950982 -7200 # Node ID fe83e6e686831db84ee3e97330bc9778652fd8a7 # Parent 84422236db206b2882cd3c40b0c33b5aa36e32ae * Fix crash on document deletion (new session, or application exit) after loading session with alignments diff -r 84422236db20 -r fe83e6e68683 audioio/AudioCallbackPlaySource.cpp --- a/audioio/AudioCallbackPlaySource.cpp Sun Oct 24 17:39:00 2010 +0200 +++ b/audioio/AudioCallbackPlaySource.cpp Sun Oct 24 22:09:42 2010 +0200 @@ -106,7 +106,10 @@ m_exiting = true; if (m_fillThread) { - m_condition.wakeAll(); +#ifdef DEBUG_AUDIO_PLAY_SOURCE + std::cout << "AudioCallbackPlaySource dtor: awakening thread" << std::endl; +#endif + m_condition.wakeAll(); m_fillThread->wait(); delete m_fillThread; } @@ -252,6 +255,10 @@ connect(model, SIGNAL(modelChanged(size_t, size_t)), this, SLOT(modelChanged(size_t, size_t))); +#ifdef DEBUG_AUDIO_PLAY_SOURCE + std::cout << "AudioCallbackPlaySource::addModel: awakening thread" << std::endl; +#endif + m_condition.wakeAll(); } @@ -304,10 +311,10 @@ } m_lastModelEndFrame = lastEnd; + m_audioGenerator->removeModel(model); + m_mutex.unlock(); - m_audioGenerator->removeModel(model); - clearRingBuffers(); } @@ -441,6 +448,11 @@ m_lastRetrievalTimestamp = 0; m_lastCurrentFrame = 0; m_playing = true; + +#ifdef DEBUG_AUDIO_PLAY_SOURCE + std::cout << "AudioCallbackPlaySource::play: awakening thread" << std::endl; +#endif + m_condition.wakeAll(); if (changed) { emit playStatusChanged(m_playing); @@ -453,8 +465,16 @@ void AudioCallbackPlaySource::stop() { +#ifdef DEBUG_AUDIO_PLAY_SOURCE + std::cerr << "AudioCallbackPlaySource::stop()" << std::endl; +#endif bool changed = m_playing; m_playing = false; + +#ifdef DEBUG_AUDIO_PLAY_SOURCE + std::cout << "AudioCallbackPlaySource::stop: awakening thread" << std::endl; +#endif + m_condition.wakeAll(); m_lastRetrievalTimestamp = 0; if (changed) { @@ -1058,6 +1078,10 @@ return 0; } +#ifdef DEBUG_AUDIO_PLAY_SOURCE_PLAYING + std::cerr << "AudioCallbackPlaySource::getSourceSamples: Playing" << std::endl; +#endif + // Ensure that all buffers have at least the amount of data we // need -- else reduce the size of our requests correspondingly @@ -1151,6 +1175,10 @@ applyAuditioningEffect(count, buffer); +#ifdef DEBUG_AUDIO_PLAY_SOURCE + std::cout << "AudioCallbackPlaySource::getSamples: awakening thread" << std::endl; +#endif + m_condition.wakeAll(); return got; @@ -1239,6 +1267,10 @@ applyAuditioningEffect(count, buffer); +#ifdef DEBUG_AUDIO_PLAY_SOURCE + std::cout << "AudioCallbackPlaySource::getSamples [stretched]: awakening thread" << std::endl; +#endif + m_condition.wakeAll(); return count; diff -r 84422236db20 -r fe83e6e68683 framework/Document.cpp --- a/framework/Document.cpp Sun Oct 24 17:39:00 2010 +0200 +++ b/framework/Document.cpp Sun Oct 24 22:09:42 2010 +0200 @@ -31,6 +31,7 @@ #include #include #include +#include // For alignment: #include "data/model/AggregateWaveModel.h" @@ -630,7 +631,8 @@ if (m_layers.find(layer) == m_layers.end()) { std::cerr << "Document::deleteLayer: Layer " - << layer << " does not exist, or has already been deleted " + << layer << " (" << typeid(layer).name() << + ") does not exist, or has already been deleted " << "(this may not be as serious as it sounds)" << std::endl; return; } diff -r 84422236db20 -r fe83e6e68683 framework/SVFileReader.cpp --- a/framework/SVFileReader.cpp Sun Oct 24 17:39:00 2010 +0200 +++ b/framework/SVFileReader.cpp Sun Oct 24 22:09:42 2010 +0200 @@ -412,8 +412,18 @@ for (std::set::iterator i = unaddedModels.begin(); i != unaddedModels.end(); ++i) { - m_document->addImportedModel(*i); - m_addedModels.insert(*i); + Model *model = *i; + // don't want to add these models, because their lifespans + // are entirely dictated by the models that "own" them even + // though they were read independently from the .sv file. + // (pity we don't have a nicer way) + if (!dynamic_cast(model) && + !dynamic_cast(model)) { + m_document->addImportedModel(model); + } + // but we add all models here, so they don't get deleted + // when the file loader is destroyed + m_addedModels.insert(model); } }