145 lines
3.3 KiB
C++
145 lines
3.3 KiB
C++
#include "DownloadManager.h"
|
|
#include "Download.h"
|
|
#include "HTTP.h"
|
|
#include "Config.h"
|
|
#include "Platform.h"
|
|
|
|
DownloadManager::DownloadManager():
|
|
threadStarted(false),
|
|
lastUsed(time(NULL)),
|
|
managerRunning(false),
|
|
managerShutdown(false),
|
|
downloads(NULL),
|
|
downloadsAddQueue(NULL)
|
|
{
|
|
pthread_mutex_init(&downloadLock, NULL);
|
|
pthread_mutex_init(&downloadAddLock, NULL);
|
|
}
|
|
|
|
DownloadManager::~DownloadManager()
|
|
{
|
|
|
|
}
|
|
|
|
void DownloadManager::Shutdown()
|
|
{
|
|
pthread_mutex_lock(&downloadLock);
|
|
pthread_mutex_lock(&downloadAddLock);
|
|
for (std::vector<Download*>::iterator iter = downloads.begin(); iter != downloads.end(); ++iter)
|
|
{
|
|
Download *download = (*iter);
|
|
if (download->http)
|
|
http_force_close(download->http);
|
|
download->downloadCanceled = true;
|
|
delete download;
|
|
}
|
|
downloads.clear();
|
|
downloadsAddQueue.clear();
|
|
managerShutdown = true;
|
|
pthread_mutex_unlock(&downloadAddLock);
|
|
pthread_mutex_unlock(&downloadLock);
|
|
pthread_join(downloadThread, NULL);
|
|
}
|
|
|
|
//helper function for download
|
|
TH_ENTRY_POINT void* DownloadManagerHelper(void* obj)
|
|
{
|
|
DownloadManager *temp = (DownloadManager*)obj;
|
|
temp->Update();
|
|
return NULL;
|
|
}
|
|
|
|
void DownloadManager::Start()
|
|
{
|
|
managerRunning = true;
|
|
lastUsed = time(NULL);
|
|
pthread_create(&downloadThread, NULL, &DownloadManagerHelper, this);
|
|
}
|
|
|
|
void DownloadManager::Update()
|
|
{
|
|
unsigned int numActiveDownloads;
|
|
while (!managerShutdown)
|
|
{
|
|
pthread_mutex_lock(&downloadAddLock);
|
|
if (downloadsAddQueue.size())
|
|
{
|
|
for (size_t i = 0; i < downloadsAddQueue.size(); i++)
|
|
{
|
|
downloads.push_back(downloadsAddQueue[i]);
|
|
}
|
|
downloadsAddQueue.clear();
|
|
}
|
|
pthread_mutex_unlock(&downloadAddLock);
|
|
if (downloads.size())
|
|
{
|
|
numActiveDownloads = 0;
|
|
pthread_mutex_lock(&downloadLock);
|
|
for (size_t i = 0; i < downloads.size(); i++)
|
|
{
|
|
Download *download = downloads[i];
|
|
if (download->downloadCanceled)
|
|
{
|
|
if (download->http && download->downloadStarted)
|
|
http_force_close(download->http);
|
|
delete download;
|
|
downloads.erase(downloads.begin()+i);
|
|
i--;
|
|
}
|
|
else if (download->downloadStarted && !download->downloadFinished)
|
|
{
|
|
if (http_async_req_status(download->http) != 0)
|
|
{
|
|
download->downloadData = http_async_req_stop(download->http, &download->downloadStatus, &download->downloadSize);
|
|
download->downloadFinished = true;
|
|
if (!download->keepAlive)
|
|
download->http = NULL;
|
|
}
|
|
lastUsed = time(NULL);
|
|
numActiveDownloads++;
|
|
}
|
|
}
|
|
pthread_mutex_unlock(&downloadLock);
|
|
}
|
|
if (time(NULL) > lastUsed+http_timeout*2 && !numActiveDownloads)
|
|
{
|
|
pthread_mutex_lock(&downloadLock);
|
|
managerRunning = false;
|
|
pthread_mutex_unlock(&downloadLock);
|
|
return;
|
|
}
|
|
Platform::Millisleep(1);
|
|
}
|
|
}
|
|
|
|
void DownloadManager::EnsureRunning()
|
|
{
|
|
pthread_mutex_lock(&downloadLock);
|
|
if (!managerRunning)
|
|
{
|
|
if (threadStarted)
|
|
pthread_join(downloadThread, NULL);
|
|
else
|
|
threadStarted = true;
|
|
Start();
|
|
}
|
|
pthread_mutex_unlock(&downloadLock);
|
|
}
|
|
|
|
void DownloadManager::AddDownload(Download *download)
|
|
{
|
|
pthread_mutex_lock(&downloadAddLock);
|
|
downloadsAddQueue.push_back(download);
|
|
pthread_mutex_unlock(&downloadAddLock);
|
|
EnsureRunning();
|
|
}
|
|
|
|
void DownloadManager::Lock()
|
|
{
|
|
pthread_mutex_lock(&downloadAddLock);
|
|
}
|
|
|
|
void DownloadManager::Unlock()
|
|
{
|
|
pthread_mutex_unlock(&downloadAddLock);
|
|
} |