diff options
author | Alexander Tkachev | 2016-06-07 16:24:19 +0600 |
---|---|---|
committer | Alexander Tkachev | 2016-08-24 16:07:55 +0600 |
commit | 74a3eba8d67ec5909b950e6b2486ba5e102fb8d0 (patch) | |
tree | 7384b9fa2f2940f08ffca8eb1c15fc98a9b62c8a /backends/networking | |
parent | 505d3764cb9c873b1dbefcb0d7b2cc7b587c6a42 (diff) | |
download | scummvm-rg350-74a3eba8d67ec5909b950e6b2486ba5e102fb8d0.tar.gz scummvm-rg350-74a3eba8d67ec5909b950e6b2486ba5e102fb8d0.tar.bz2 scummvm-rg350-74a3eba8d67ec5909b950e6b2486ba5e102fb8d0.zip |
CLOUD: Fix ConnectionManager
It now keeps newly added Requests in separate array, so iterators don't
break when one adds a Request while ConnMan iterates its array.
The array is also shielded with mutex.
Diffstat (limited to 'backends/networking')
-rw-r--r-- | backends/networking/curl/connectionmanager.cpp | 27 | ||||
-rw-r--r-- | backends/networking/curl/connectionmanager.h | 5 |
2 files changed, 25 insertions, 7 deletions
diff --git a/backends/networking/curl/connectionmanager.cpp b/backends/networking/curl/connectionmanager.cpp index c675d0d91b..edc7e81229 100644 --- a/backends/networking/curl/connectionmanager.cpp +++ b/backends/networking/curl/connectionmanager.cpp @@ -66,8 +66,10 @@ void ConnectionManager::registerEasyHandle(CURL *easy) { } Request *ConnectionManager::addRequest(Request *request, RequestCallback callback) { - _requests.push_back(RequestWithCallback(request, callback)); - if (!_timerStarted) startTimer(); + _addedRequestsMutex.lock(); + _addedRequests.push_back(RequestWithCallback(request, callback)); + if (!_timerStarted) startTimer(); + _addedRequestsMutex.unlock(); return request; } @@ -98,21 +100,36 @@ void ConnectionManager::stopTimer() { _timerStarted = false; } +bool ConnectionManager::hasAddedRequests() { + _addedRequestsMutex.lock(); + bool hasNewRequests = !_addedRequests.empty(); + _addedRequestsMutex.unlock(); + return hasNewRequests; +} + void ConnectionManager::handle() { //lock mutex here (in case another handle() would be called before this one ends) _handleMutex.lock(); ++_frame; if (_frame % CLOUD_PERIOD == 0) interateRequests(); if (_frame % CURL_PERIOD == 0) processTransfers(); - - if (_icon.draw() && _requests.empty()) + + if (_icon.draw() && _requests.empty() && !hasAddedRequests()) stopTimer(); _handleMutex.unlock(); } void ConnectionManager::interateRequests() { + //add new requests + _addedRequestsMutex.lock(); + for (Common::Array<RequestWithCallback>::iterator i = _addedRequests.begin(); i != _addedRequests.end(); ++i) { + _requests.push_back(*i); + } + _addedRequests.clear(); + _addedRequestsMutex.unlock(); + //call handle() of all running requests (so they can do their work) - debug("handling %d request(s)", _requests.size()); + debug("handling %d request(s)", _requests.size()); for (Common::Array<RequestWithCallback>::iterator i = _requests.begin(); i != _requests.end();) { Request *request = i->request; if (request) { diff --git a/backends/networking/curl/connectionmanager.h b/backends/networking/curl/connectionmanager.h index 8b2153a955..66994f0a79 100644 --- a/backends/networking/curl/connectionmanager.h +++ b/backends/networking/curl/connectionmanager.h @@ -77,8 +77,8 @@ class ConnectionManager : public Common::Singleton<ConnectionManager> { CURLM *_multi; bool _timerStarted; - Common::Array<RequestWithCallback> _requests; - Common::Mutex _handleMutex; + Common::Array<RequestWithCallback> _requests, _addedRequests; + Common::Mutex _handleMutex, _addedRequestsMutex; CloudIcon _icon; uint32 _frame; @@ -87,6 +87,7 @@ class ConnectionManager : public Common::Singleton<ConnectionManager> { void handle(); void interateRequests(); void processTransfers(); + bool hasAddedRequests(); public: ConnectionManager(); |