Advertisement
Guest User

Untitled

a guest
Mar 17th, 2017
75
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Haxe 3.52 KB | None | 0 0
  1. package;
  2.  
  3. import neko.vm.Mutex;
  4. import neko.vm.Thread;
  5.  
  6. class PoolThread {
  7.     private var _name:String;
  8.     private var _pool:ThreadPool;
  9.    
  10.     private var _thread:Thread;
  11.    
  12.     public function new(name:String, pool:ThreadPool) {
  13.         _name = name;
  14.         _pool = pool;
  15.        
  16.         _thread = Thread.create(run);
  17.         _thread.sendMessage(Thread.current());
  18.         _thread.sendMessage(_pool);
  19.         Thread.readMessage(true);
  20.     }
  21.    
  22.     public function assign(task:ThreadTask) {
  23.         _thread.sendMessage(task);
  24.     }
  25.    
  26.     private var _kill:Bool = false;
  27.     public function kill() {
  28.         _kill = true;
  29.         _thread.sendMessage(null);
  30.     }
  31.    
  32.     @:access(ThreadPool)
  33.     private function run() {
  34.         var callingThread:Thread = Thread.readMessage(true);
  35.         var pool:ThreadPool = Thread.readMessage(true);
  36.         callingThread.sendMessage(null);
  37.        
  38.         while (_kill == false) {
  39.             var message = Thread.readMessage(true);
  40.             if (_kill == true) {
  41.                 break;
  42.             }
  43.            
  44.             if (Std.is(message, ThreadTask)) {
  45.                 var task:ThreadTask = cast(message, ThreadTask);
  46.                 var result = task.task(task.arg);
  47.                 pool.threadTaskComplete(this, task, result);
  48.             }
  49.         }
  50.        
  51.         callingThread.sendMessage(null);
  52.     }
  53. }
  54.  
  55. class ThreadTask {
  56.     public var task:Dynamic->Dynamic;
  57.     public var arg:Dynamic;
  58.     public var onComplete:Dynamic->Void;
  59.    
  60.     public function new(task:Dynamic->Dynamic, arg:Dynamic, onComplete:Dynamic->Void) {
  61.         this.task = task;
  62.         this.arg = arg;
  63.         this.onComplete = onComplete;
  64.     }
  65. }
  66.  
  67. class ThreadPool {
  68.     private var _threads:Array<PoolThread>;
  69.     private var _threadPool:Array<PoolThread>;
  70.     private var _lock:Mutex;
  71.    
  72.     private var _tasks:Array<ThreadTask>;
  73.     private var _activeTasks:Array<ThreadTask>;
  74.    
  75.     public function new(size:Int, namePrefix:String = "thread-") {
  76.         _threads = [];
  77.         _threadPool = [];
  78.         _lock = new Mutex();
  79.        
  80.         _tasks = [];
  81.         _activeTasks = [];
  82.        
  83.         for (i in 0...size) {
  84.             var thread:PoolThread = new PoolThread('${namePrefix}${i}', this);
  85.             _threads.push(thread);
  86.             _threadPool.push(thread);
  87.         }
  88.     }
  89.    
  90.     public function addTask(task:Dynamic->Dynamic, arg:Dynamic, onComplete:Dynamic->Void) {
  91.         _lock.acquire();
  92.         _tasks.push(new ThreadTask(task, arg, onComplete));
  93.         _lock.release();
  94.        
  95.         checkTasks();
  96.     }
  97.    
  98.     public function killAllThreads() {
  99.         for (thread in _threads) {
  100.             thread.kill();
  101.             Thread.readMessage(true);
  102.         }
  103.     }
  104.    
  105.     private function threadTaskComplete(thread:PoolThread, task:ThreadTask, result:Dynamic) {
  106.         _lock.acquire();
  107.         _activeTasks.remove(task);
  108.         _threadPool.push(thread);
  109.         task.onComplete(result);
  110.         _lock.release();
  111.         checkTasks();
  112.     }
  113.    
  114.     private function checkTasks() {
  115.         _lock.acquire();
  116.         var thread:PoolThread = _threadPool.pop();
  117.         _lock.release();
  118.         if (thread == null) {
  119.             return;
  120.         }
  121.        
  122.         if (_tasks.length == 0) {
  123.             return;
  124.         }
  125.        
  126.         _lock.acquire();
  127.         var task = _tasks[0];
  128.         _tasks.remove(task);
  129.         _activeTasks.push(task);
  130.         _lock.release();
  131.        
  132.         thread.assign(task);
  133.     }
  134. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement