-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathManagedTimer.cpp
118 lines (103 loc) · 2.93 KB
/
ManagedTimer.cpp
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
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
#include <memory>
#include <csignal>
#include "ManagedTimer.h"
ManagedTimer::ManagedTimer(const std::function<void(void)>& f)
: is_running_{false}, f_{f}
{}
ManagedTimer::~ManagedTimer()
{
stop();
}
void ManagedTimer::start(size_t time)
{
std::lock_guard<std::mutex> lk(mtx_);
if (is_running_)
{
std::cout << "MangedTimer already running at " << wait_thread_->get_id() << std::endl;
}
else
{
time_ = std::chrono::milliseconds{std::chrono::milliseconds{time}};
is_running_ = true;
std::cout << "starting " << std::endl;
if (!wait_thread_)
{
wait_thread_.reset(new std::thread(std::bind(&ManagedTimer::run, this)));
std::cout << "Resetting the null thread pointer" << std::endl;
}
else
{
wait_thread_.release();
wait_thread_ = std::unique_ptr<std::thread>(new std::thread(std::bind(&ManagedTimer::run, this)));
std::cout << "making a new thread pointer" << std::endl;
}
}
}
void ManagedTimer::stop()
{
{
std::lock_guard<std::mutex> lk(mtx_);
if(is_running_)
{
cpoint_.cancel();
}
cpoint_.reset();
}
std::cout << " Stopping..." << std::endl;
if (wait_thread_)
{
if (wait_thread_->joinable())
{
auto id = wait_thread_->get_id();
wait_thread_->join();
std::cout << "ManagedTimer thread " << id << " was joined!" << std::endl;
wait_thread_.release();
std::cout << "In Stop() after release " << std::boolalpha << (wait_thread_? true:false) << std::endl;
}
{
std::lock_guard<std::mutex> lk(mtx_);
is_running_ = false;
}
}
else
{
std::cout << "Already stopped!" << std::endl;
}
}
void ManagedTimer::run()
{
{
std::lock_guard<std::mutex> lk(mtx_);
if (!is_running_)
is_running_ = true;
}
std::cout << "thread started\n";
try {
long int seconds{};
seconds = std::chrono::duration_cast<std::chrono::seconds>(time_).count();
// std::cout << "ManagedTimer time count in seconds " << seconds << std::endl;
for(long int i{seconds}; i > 0; --i) {
std::cout << "Thread " << wait_thread_->get_id() << " countdown at: " << '\t' << i << std::endl;
cpoint_.wait(1);
}
f_();
} catch (const cancelled_error&) {
std::cout << "thread cancelled, will stop\n";
}
}
void ManagedTimer::handleInterrupt(int signum)
{
switch(signum)
{
case SIGINT:
case SIGTERM:
case SIGILL:
std::cout << " Caught interrupt signal, stopping first." << std::endl;
if(is_running_)
stop();
exit(0);
default:
std::cout << " Unhandled signal, exitting with error." << std::endl;
exit(signum);
}
}