Skip to content

Commit

Permalink
rust: thread: Add Thread wrapper
Browse files Browse the repository at this point in the history
Signed-off-by: Boqun Feng <[email protected]>
  • Loading branch information
fbq committed Mar 15, 2021
1 parent 51a196e commit 3851011
Show file tree
Hide file tree
Showing 4 changed files with 64 additions and 0 deletions.
17 changes: 17 additions & 0 deletions drivers/char/rust_example.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ use kernel::{
file_operations::FileOperations,
miscdev, mutex_init, spinlock_init,
sync::{Mutex, SpinLock},
thread::Thread,
};

module! {
Expand Down Expand Up @@ -97,6 +98,22 @@ impl KernelModule for RustExample {
println!("Value: {}", *data.lock());
}

// Test threads.
{
let mut a = 1;

let t1 = Thread::new(
move || {
for _ in 0..20 {
a = a + 1;
println!("Hello Rust Thread {}", a);
}
},
"Rust thread",
);
t1.wake_up();
}

// Including this large variable on the stack will trigger
// stack probing on the supported archs.
// This will verify that stack probing does not lead to
Expand Down
2 changes: 2 additions & 0 deletions rust/kernel/bindings_helper.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@
#include <linux/uaccess.h>
#include <linux/version.h>
#include <linux/miscdevice.h>
#include <linux/kthread.h>
#include <linux/err.h>

// `bindgen` gets confused at certain things
const gfp_t BINDINGS_GFP_KERNEL = GFP_KERNEL;
Expand Down
1 change: 1 addition & 0 deletions rust/kernel/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ pub mod printk;
pub mod random;
mod static_assert;
pub mod sync;
pub mod thread;

#[cfg(CONFIG_SYSCTL)]
pub mod sysctl;
Expand Down
44 changes: 44 additions & 0 deletions rust/kernel/thread.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
// SPDX-License-Identifier: GPL-2.0

use crate::bindings;
use crate::c_types;

use alloc::boxed::Box;
use core::ops::FnOnce;

#[no_mangle]
unsafe extern "C" fn rust_thread_func(data: *mut c_types::c_void) -> c_types::c_int {
Box::from_raw(data as *mut Box<dyn FnOnce()>)();
0
}

pub struct Thread {
task: *mut bindings::task_struct,
}

impl Thread {
pub fn new<F>(f: F, name: &str) -> Self
where
F: FnOnce(),
F: Send + 'static,
{
let bf: Box<dyn FnOnce() + 'static> = Box::new(f);

unsafe {
let task = bindings::kthread_create_on_node(
Some(rust_thread_func),
Box::into_raw(Box::new(bf)) as *mut _,
bindings::NUMA_NO_NODE,
"%s".as_ptr() as *const c_types::c_char,
name.as_ptr(),
);
Thread { task: task }
}
}

pub fn wake_up(&self) {
unsafe {
bindings::wake_up_process(self.task);
}
}
}

0 comments on commit 3851011

Please sign in to comment.