From 5e415c5b9565564c41c4f2f4144c6863c106bc46 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Wed, 13 Aug 2014 12:33:31 +0200 Subject: RankMgr: Fixed multithreading issues. Only one thread is allowed to interact with a SQLite::Database object at a time. Additionally, improved performance of the migration by wrapping the entire thing in a transaction. --- src/RankManager.h | 32 +++++++++++++++++++++++++++++++- 1 file changed, 31 insertions(+), 1 deletion(-) (limited to 'src/RankManager.h') diff --git a/src/RankManager.h b/src/RankManager.h index ffe7638e1..3ccbd2fd4 100644 --- a/src/RankManager.h +++ b/src/RankManager.h @@ -9,6 +9,7 @@ #pragma once #include "SQLiteCpp/Database.h" +#include "SQLiteCpp/Transaction.h" @@ -23,6 +24,29 @@ class cMojangAPI; class cRankManager { public: + /** Acquire this lock to perform mass changes. + Improves performance by wrapping everything into a transaction. + Makes sure that no other thread is accessing the DB. */ + class cMassChangeLock + { + public: + cMassChangeLock(cRankManager & a_RankManager) : + m_Lock(a_RankManager.m_CS), + m_Transaction(a_RankManager.m_DB) + { + } + + ~cMassChangeLock() + { + m_Transaction.commit(); + } + + protected: + cCSLock m_Lock; + SQLite::Transaction m_Transaction; + }; + + /** Creates the rank manager. Needs to be initialized before other use. */ cRankManager(void); @@ -80,6 +104,9 @@ public: /** Adds a new permission group. No action if such a group already exists. */ void AddGroup(const AString & a_GroupName); + /** Bulk-adds groups. Group names that already exist are silently skipped. */ + void AddGroups(const AStringVector & a_GroupNames); + /** Adds the specified permission group to the specified rank. Fails if the rank or group names are not found. Returns true if successful, false on error. */ @@ -163,9 +190,12 @@ public: protected: - /** The database storage for all the data. */ + /** The database storage for all the data. Protected by m_CS. */ SQLite::Database m_DB; + /** The mutex protecting m_DB against multi-threaded access. */ + cCriticalSection m_CS; + /** Set to true once the manager is initialized. */ bool m_IsInitialized; -- cgit v1.2.3