-
Notifications
You must be signed in to change notification settings - Fork 0
/
Executer.cpp
118 lines (89 loc) · 2.22 KB
/
Executer.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
//
// Executer.cpp
// AysncIO
//
// Created by Yanjiu Huang on 4/8/14.
// Copyright (c) 2014 Yanjiu Huang. All rights reserved.
//
#include <unistd.h>
#include "Executer.h"
Executer::Executer(){
init();
}
Executer::~Executer(){
if(m_task_queue){
delete m_task_queue;
}
if(m_thread){
delete m_thread;
}
}
void Executer::init(){
m_task_queue = new ConcurrentQueue<Task>(256);
std::atomic_init(&m_state, EXECUTER_STATE_NOT_START);
m_delayed_queue = new priority_queue<ScheduledTask>;
}
void Executer::execute(Task& task){
int oldState = atomic_load(&m_state);
if(oldState >= EXECUTER_STATE_SHUTTINGDOWN){
// start the thread again
start();
}
if(atomic_load(&m_state) != EXECUTER_STATE_STARTED){
cerr << "Can't start the Executor!" << endl;
return;
}
addTask(task);
}
void Executer::shutdown(){
atomic_store(&m_state, EXECUTER_STATE_SHUTTINGDOWN);
}
void Executer::start(){
atomic_store(&m_state, EXECUTER_STATE_STARTED);
if(m_thread){
delete m_thread;
}
m_thread = new thread(&Executer::doRun, this);
}
void Executer::doRun(){
if(atomic_load(&m_state) != EXECUTER_STATE_STARTED){
return;
}
for(;;){
if(m_task_queue->isEmpty()){
// just sleep
usleep(1000);
continue;
}
Task t = m_task_queue->wait_to_take();
t.run();
if(atomic_load(&m_state) == EXECUTER_STATE_SHUTTINGDOWN){
if(m_task_queue->isEmpty()){
atomic_store(&m_state, EXECUTER_STATE_SHUTDOWN);
return;
}
}
}
}
void Executer::join(){
if (m_thread && m_thread->joinable()) {
//cout << "Try to join the executer here!" << endl;
m_thread->join();
}
}
void Executer::addTask(Task& t){
if(atomic_load(&m_state) == EXECUTER_STATE_STARTED && m_task_queue){
m_task_queue->wait_to_put(t);
}
}
void Task::run(){
if(m_handle){
m_handle(m_attachment);
}
}
void Task::setAttachment(void *obj){
m_attachment = obj;
}
void Task::setHandle(task_handle_t handle){
m_handle = handle;
}