diff options
author | Christian Ehrlicher <[email protected]> | 2023-04-18 19:40:25 +0200 |
---|---|---|
committer | Christian Ehrlicher <[email protected]> | 2023-05-24 17:27:55 +0200 |
commit | 048a68c1e965350ad9ff7d4ab1fdaac56a2583a0 (patch) | |
tree | a553e36d759b968cd71844c4a58792b8c311ee62 /src/sql/kernel/qsqldatabase.cpp | |
parent | 68f35a571a259cd83490c093af01d8b4e9b0e34a (diff) |
SQL: Make QSqlDatabase::DriverDict creation thread-safe
Make the QSqlDatabase::DriverDict thread-safe and make sure it's
properly cleaned up on destruction.
Pick-to: 6.5 6.2 5.15
Fixes: QTBUG-112961
Change-Id: I1ff70e477579231754ef829fdede944d6042894d
Reviewed-by: Volker Hilsheimer <[email protected]>
Diffstat (limited to 'src/sql/kernel/qsqldatabase.cpp')
-rw-r--r-- | src/sql/kernel/qsqldatabase.cpp | 29 |
1 files changed, 14 insertions, 15 deletions
diff --git a/src/sql/kernel/qsqldatabase.cpp b/src/sql/kernel/qsqldatabase.cpp index 9f306748afa..4a966dcfa7c 100644 --- a/src/sql/kernel/qsqldatabase.cpp +++ b/src/sql/kernel/qsqldatabase.cpp @@ -9,6 +9,7 @@ #include "qsqldriver.h" #include "qsqldriverplugin.h" #include "qsqlindex.h" +#include "QtCore/qapplicationstatic.h" #include "private/qfactoryloader_p.h" #include "private/qsqlnulldriver_p.h" #include "qhash.h" @@ -23,8 +24,6 @@ Q_GLOBAL_STATIC_WITH_ARGS(QFactoryLoader, loader, const char *QSqlDatabase::defaultConnection = "qt_sql_default_connection"; -typedef QHash<QString, QSqlDriverCreatorBase*> DriverDict; - class QConnectionDict: public QHash<QString, QSqlDatabase> { public: @@ -48,6 +47,14 @@ public: }; Q_GLOBAL_STATIC(QConnectionDict, dbDict) +namespace { + struct DriverDict : public QHash<QString, QSqlDriverCreatorBase*> + { + ~DriverDict(); + }; +} +Q_APPLICATION_STATIC(DriverDict, qtDriverDict) + class QSqlDatabasePrivate { public: @@ -120,23 +127,15 @@ void QSqlDatabasePrivate::cleanConnections() dict->clear(); } -static bool qDriverDictInit = false; -static void cleanDriverDict() +DriverDict::~DriverDict() { - qDeleteAll(QSqlDatabasePrivate::driverDict()); - QSqlDatabasePrivate::driverDict().clear(); + qDeleteAll(*this); QSqlDatabasePrivate::cleanConnections(); - qDriverDictInit = false; } DriverDict &QSqlDatabasePrivate::driverDict() { - static DriverDict dict; - if (!qDriverDictInit) { - qDriverDictInit = true; - qAddPostRoutine(cleanDriverDict); - } - return dict; + return *qtDriverDict(); } QSqlDatabasePrivate *QSqlDatabasePrivate::shared_null() @@ -504,7 +503,7 @@ QStringList QSqlDatabase::drivers() } QReadLocker locker(&dbDict()->lock); - const DriverDict dict = QSqlDatabasePrivate::driverDict(); + const DriverDict &dict = QSqlDatabasePrivate::driverDict(); for (const auto &[k, _] : dict.asKeyValueRange()) { if (!list.contains(k)) list << k; @@ -645,7 +644,7 @@ void QSqlDatabasePrivate::init(const QString &type) if (!driver) { QReadLocker locker(&dbDict()->lock); - DriverDict dict = QSqlDatabasePrivate::driverDict(); + const DriverDict &dict = QSqlDatabasePrivate::driverDict(); for (DriverDict::const_iterator it = dict.constBegin(); it != dict.constEnd() && !driver; ++it) { if (type == it.key()) { |