-
Notifications
You must be signed in to change notification settings - Fork 17
/
Copy pathkeepalive.cc
93 lines (77 loc) · 2.08 KB
/
keepalive.cc
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
#include "keepalive.h"
#include "candy.h"
#include <algorithm>
#include <QSysInfo>
KeepAlive &KeepAlive::instance()
{
static KeepAlive i;
return i;
}
void KeepAlive::add(std::shared_ptr<void> candy)
{
std::lock_guard lock(this->mutex);
this->map[candy.get()] = candy;
}
void KeepAlive::del(std::shared_ptr<void> candy)
{
std::lock_guard lock(this->mutex);
this->map.erase(candy.get());
}
void KeepAlive::restart(std::shared_ptr<void> candy)
{
std::lock_guard lock(this->mutex);
this->list.push_back(candy);
}
KeepAlive::KeepAlive()
{
candy_init();
#ifdef Q_OS_WIN
candy_set_log_path("C:/ProgramData/Cake/logs/candy.txt");
#endif
candy_enable_debug();
running = true;
this->thread = std::thread([&] {
while (running) {
std::shared_ptr<void> candy;
std::this_thread::sleep_for(std::chrono::seconds(1));
if (running) {
std::lock_guard lock(mutex);
if (list.empty()) {
continue;
}
candy = list.front().lock();
list.pop_front();
}
if (candy.use_count() > 1) {
candy_client_shutdown(candy.get());
candy_client_run(candy.get());
}
if (candy.use_count() == 1) {
candy_client_shutdown(candy.get());
}
}
});
candy_client_set_error_cb(candy_error_cb);
}
KeepAlive::~KeepAlive()
{
this->running = false;
if (this->thread.joinable()) {
this->thread.join();
}
candy_release();
}
void candy_error_cb(void *candy)
{
KeepAlive &instance = KeepAlive::instance();
std::lock_guard lock(instance.mutex);
auto it = instance.map.find(candy);
if (it == instance.map.end()) {
return;
}
auto equal = [&](std::weak_ptr<void> ptr) { return !ptr.owner_before(it->second) && !it->second.owner_before(ptr); };
if (std::find_if(instance.list.begin(), instance.list.end(), equal) != instance.list.end()) {
return;
}
instance.list.push_back(it->second);
}