# A simple ThreadPool implemented with an array
class ThreadPool
- private var queue = new ConcurrentList[JoinTask].wrap(new List[JoinTask])
+ private var queue = new ConcurrentList[Task]
private var mutex = new Mutex
private var cond = new NativePthreadCond
private class PoolThread
super Thread
- var queue: ConcurrentList[JoinTask]
+ var queue: ConcurrentList[Task]
var mutex: Mutex
var cond : NativePthreadCond
redef fun main do
loop
- var t: nullable JoinTask = null
+ var t = null
mutex.lock
if queue.is_empty then cond.wait(mutex.native.as(not null))
if not queue.is_empty then
mutex.unlock
if t != null then
t.main
- t.mutex.lock
- t.is_done = true
- var tcond = t.cond
- if tcond != null then tcond.signal
- t.mutex.unlock
+ t.after_main
end
end
end
end
+redef class Task
+ # Additional work executed after `main` from a `ThreadPool`
+ private fun after_main do end
+end
+
# A Task which is joinable, meaning it can return a value and if the value is not set yet, it blocks the execution
class JoinTask
super Task
- # Is `self` done ?
+ # Is `self` done?
var is_done = false
private var mutex = new Mutex
end
mutex.unlock
end
+
+ redef fun after_main do
+ # TODO move this at the end of main so all `JoinTask` can be joined
+ # no matter what calls `main`.
+
+ mutex.lock
+ is_done = true
+ var tcond = cond
+ if tcond != null then tcond.signal
+ mutex.unlock
+ end
end