1
0
mirror of https://github.com/tomahawk-player/tomahawk.git synced 2025-08-06 14:16:32 +02:00

Safer locking of id() to prevent deadlocks

This commit is contained in:
Leo Franchi
2012-06-16 11:14:20 +02:00
parent cd3eeb2951
commit 3f2906d4d1
2 changed files with 28 additions and 9 deletions

View File

@@ -29,6 +29,8 @@
#include "utils/Logger.h" #include "utils/Logger.h"
#include <QReadWriteLock>
using namespace Tomahawk; using namespace Tomahawk;
QHash< QString, album_ptr > Album::s_albumsByName = QHash< QString, album_ptr >(); QHash< QString, album_ptr > Album::s_albumsByName = QHash< QString, album_ptr >();
@@ -36,7 +38,7 @@ QHash< unsigned int, album_ptr > Album::s_albumsById = QHash< unsigned int, albu
static QMutex s_nameCacheMutex; static QMutex s_nameCacheMutex;
static QMutex s_idCacheMutex; static QMutex s_idCacheMutex;
static QMutex s_idMutex; static QReadWriteLock s_idMutex;
Album::~Album() Album::~Album()
{ {
@@ -155,18 +157,25 @@ Album::loadId( bool autoCreate )
unsigned int unsigned int
Album::id() const Album::id() const
{ {
QMutexLocker l( &s_idMutex ); s_idMutex.lockForRead();
const bool waiting = m_waitingForId;
unsigned int finalId = m_id;
s_idMutex.unlock();
if ( m_waitingForId ) if ( waiting )
{ {
m_id = m_idFuture.get(); finalId = m_idFuture.get();
s_idMutex.lockForWrite();
m_id = finalId;
m_waitingForId = false; m_waitingForId = false;
if ( m_id > 0 ) if ( m_id > 0 )
s_albumsById[ m_id ] = m_ownRef.toStrongRef(); s_albumsById[ m_id ] = m_ownRef.toStrongRef();
s_idMutex.unlock();
} }
return m_id; return finalId;
} }

View File

@@ -30,6 +30,8 @@
#include "utils/Logger.h" #include "utils/Logger.h"
#include <QReadWriteLock>
using namespace Tomahawk; using namespace Tomahawk;
QHash< QString, artist_ptr > Artist::s_artistsByName = QHash< QString, artist_ptr >(); QHash< QString, artist_ptr > Artist::s_artistsByName = QHash< QString, artist_ptr >();
@@ -37,7 +39,7 @@ QHash< unsigned int, artist_ptr > Artist::s_artistsById = QHash< unsigned int, a
static QMutex s_nameCacheMutex; static QMutex s_nameCacheMutex;
static QMutex s_idCacheMutex; static QMutex s_idCacheMutex;
static QMutex s_idMutex; static QReadWriteLock s_idMutex;
Artist::~Artist() Artist::~Artist()
{ {
@@ -235,14 +237,22 @@ Artist::loadId( bool autoCreate )
unsigned int unsigned int
Artist::id() const Artist::id() const
{ {
QMutexLocker l( &s_idMutex ); s_idMutex.lockForRead();
if ( m_waitingForFuture ) const bool waiting = m_waitingForFuture;
unsigned int finalid = m_id;
s_idMutex.unlock();
if ( waiting )
{ {
m_id = m_idFuture.get(); finalid = m_idFuture.get();
s_idMutex.lockForWrite();
m_id = finalid;
m_waitingForFuture = false; m_waitingForFuture = false;
if ( m_id > 0 ) if ( m_id > 0 )
s_artistsById[ m_id ] = m_ownRef.toStrongRef(); s_artistsById[ m_id ] = m_ownRef.toStrongRef();
s_idMutex.unlock();
} }
return m_id; return m_id;