use crate::string::IntoCStr; use binaryninjacore_sys::*; use std::ffi::c_void; pub struct WorkerThreadActionExecutor { func: Box, } impl WorkerThreadActionExecutor { unsafe extern "C" fn cb_execute(ctx: *mut c_void) { let f: Box = Box::from_raw(ctx as *mut Self); f.execute(); } pub fn execute(&self) { (self.func)(); } } pub fn execute_on_worker_thread(name: &str, f: F) { let boxed_executor = Box::new(WorkerThreadActionExecutor { func: Box::new(f) }); let raw_executor = Box::into_raw(boxed_executor); let name = name.to_cstr(); unsafe { BNWorkerEnqueueNamed( raw_executor as *mut c_void, Some(WorkerThreadActionExecutor::cb_execute), name.as_ptr(), ) } } pub fn execute_on_worker_thread_priority(name: &str, f: F) { let boxed_executor = Box::new(WorkerThreadActionExecutor { func: Box::new(f) }); let raw_executor = Box::into_raw(boxed_executor); let name = name.to_cstr(); unsafe { BNWorkerPriorityEnqueueNamed( raw_executor as *mut c_void, Some(WorkerThreadActionExecutor::cb_execute), name.as_ptr(), ) } } pub fn execute_on_worker_thread_interactive(name: &str, f: F) { let boxed_executor = Box::new(WorkerThreadActionExecutor { func: Box::new(f) }); let raw_executor = Box::into_raw(boxed_executor); let name = name.to_cstr(); unsafe { BNWorkerInteractiveEnqueueNamed( raw_executor as *mut c_void, Some(WorkerThreadActionExecutor::cb_execute), name.as_ptr(), ) } } /// Returns the number of worker threads that are currently running. /// By default, this is the number of cores on the system minus one /// /// To set the worker thread count use [`set_worker_thread_count`]. pub fn worker_thread_count() -> usize { unsafe { BNGetWorkerThreadCount() } } /// Sets the number of worker threads that are currently running. /// By default, this is the number of cores on the system minus one. pub fn set_worker_thread_count(count: usize) { unsafe { BNSetWorkerThreadCount(count) } }