From d3f4c08f3324307f42fb33cf2edf37c708159ee7 Mon Sep 17 00:00:00 2001 From: Dietmar Maurer Date: Thu, 11 Apr 2019 07:55:02 +0200 Subject: [PATCH] src/server/worker_task.rs: catch panics in worker threads --- src/server/worker_task.rs | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/src/server/worker_task.rs b/src/server/worker_task.rs index 5abca6e3..67e97fc1 100644 --- a/src/server/worker_task.rs +++ b/src/server/worker_task.rs @@ -9,6 +9,8 @@ use std::collections::HashMap; use std::sync::atomic::{AtomicBool, Ordering}; use std::io::{BufRead, BufReader}; use std::fs::File; +use std::panic::UnwindSafe; + use serde_json::{json, Value}; use super::UPID; @@ -426,7 +428,7 @@ impl WorkerTask { to_stdout: bool, f: F, ) -> Result - where F: Send + 'static + FnOnce(Arc) -> Result<(), Error> + where F: Send + UnwindSafe + 'static + FnOnce(Arc) -> Result<(), Error> { println!("register worker thread"); @@ -437,7 +439,22 @@ impl WorkerTask { let upid_str = worker.upid.to_string(); let _child = std::thread::spawn(move || { - let result = f(worker.clone()); + let worker1 = worker.clone(); + let result = match std::panic::catch_unwind(move || f(worker1)) { + Ok(r) => r, + Err(panic) => { + match panic.downcast::<&str>() { + Ok(panic_msg) => { + Err(format_err!("worker panicked: {}", panic_msg)) + } + Err(_) => { + Err(format_err!("worker panicked: unknown type.")) + } + } + } + }; + + //let result = f(worker.clone()); WORKER_TASK_LIST.lock().unwrap().remove(&task_id); worker.log_result(result); let _ = update_active_workers(None);