comparison data/fft/FFTDataServer.cpp @ 213:e0e7f6c5fda9

* Make FFT data server more resilient when running out of memory
author Chris Cannam
date Fri, 12 Jan 2007 19:32:55 +0000
parents 05154c7bb90b
children a051929fef3b
comparison
equal deleted inserted replaced
212:fb8ddd00f440 213:e0e7f6c5fda9
568 568
569 QString name = QString("%1-%2").arg(m_fileBaseName).arg(c); 569 QString name = QString("%1-%2").arg(m_fileBaseName).arg(c);
570 570
571 FFTCache *cache = 0; 571 FFTCache *cache = 0;
572 572
573 size_t width = m_cacheWidth;
574 if (c * m_cacheWidth + width > m_width) {
575 width = m_width - c * m_cacheWidth;
576 }
577
573 try { 578 try {
574 579
575 if (m_memoryCache) { 580 if (m_memoryCache) {
576 581
577 cache = new FFTMemoryCache(); 582 cache = new FFTMemoryCache();
586 cache = new FFTFileCache(name, MatrixFile::ReadWrite, 591 cache = new FFTFileCache(name, MatrixFile::ReadWrite,
587 m_polar ? FFTFileCache::Polar : 592 m_polar ? FFTFileCache::Polar :
588 FFTFileCache::Rectangular); 593 FFTFileCache::Rectangular);
589 } 594 }
590 595
591 size_t width = m_cacheWidth;
592 if (c * m_cacheWidth + width > m_width) {
593 width = m_width - c * m_cacheWidth;
594 }
595
596 cache->resize(width, m_height); 596 cache->resize(width, m_height);
597 cache->reset(); 597 cache->reset();
598 598
599 StorageAdviser::notifyDoneAllocation
600 (m_memoryCache ? StorageAdviser::MemoryAllocation :
601 StorageAdviser::DiscAllocation,
602 width * m_height *
603 (m_compactCache ? sizeof(uint16_t) : sizeof(float)) / 1024 + 1);
604
605 } catch (std::bad_alloc) { 599 } catch (std::bad_alloc) {
606 std::cerr << "ERROR: Memory allocation failed in FFTFileCache::resize:" 600
607 << " abandoning this cache" << std::endl; 601 delete cache;
602 cache = 0;
603
604 if (m_memoryCache) {
605
606 std::cerr << "WARNING: Memory allocation failed when resizing"
607 << " FFT memory cache no. " << c << " to " << width
608 << "x" << m_height << " (of total width " << m_width
609 << "): falling back to disc cache" << std::endl;
610
611 try {
612
613 cache = new FFTFileCache(name, MatrixFile::ReadWrite,
614 FFTFileCache::Compact);
615
616 cache->resize(width, m_height);
617 cache->reset();
618
619 } catch (std::bad_alloc) {
620
621 delete cache;
622 cache = 0;
623 }
624 }
625
626 if (cache) {
627 std::cerr << "ERROR: Memory allocation failed when resizing"
628 << " FFT file cache no. " << c << " to " << width
629 << "x" << m_height << " (of total width " << m_width
630 << "): abandoning this cache" << std::endl;
631 }
632
608 //!!! Shouldn't be using QtGui here. Need a better way to report this. 633 //!!! Shouldn't be using QtGui here. Need a better way to report this.
609 QMessageBox::critical 634 QMessageBox::critical
610 (0, QApplication::tr("FFT cache resize failed"), 635 (0, QApplication::tr("FFT cache resize failed"),
611 QApplication::tr 636 QApplication::tr
612 ("Failed to create or resize an FFT model slice.\n" 637 ("Failed to create or resize an FFT model slice.\n"
613 "There may be insufficient memory or disc space to continue.")); 638 "There may be insufficient memory or disc space to continue."));
614 delete cache; 639 }
615 m_caches[c] = 0; 640
616 return 0; 641 StorageAdviser::notifyDoneAllocation
617 } 642 (m_memoryCache ? StorageAdviser::MemoryAllocation :
643 StorageAdviser::DiscAllocation,
644 width * m_height *
645 (m_compactCache ? sizeof(uint16_t) : sizeof(float)) / 1024 + 1);
618 646
619 m_caches[c] = cache; 647 m_caches[c] = cache;
620 m_lastUsedCache = c; 648 m_lastUsedCache = c;
621
622 return cache; 649 return cache;
623 } 650 }
624 651
625 float 652 float
626 FFTDataServer::getMagnitudeAt(size_t x, size_t y) 653 FFTDataServer::getMagnitudeAt(size_t x, size_t y)