Skip to content

Commit 16083a3

Browse files
committed
samples: rust: add debugfs samples
Add some basic debugfs sample module to show how to use the debugfs API. The sample module is showing: * How to create a directory * How to define and register a debugfs file by implementing file::Operations * How to use the attribute macro to expose simple numerical debugfs values. This is the equivalent of the C macro DEFINE_DEBUGFS_ATTRIBUTE{,_SIGNED} Signed-off-by: Fabien Parent <[email protected]>
1 parent 1498488 commit 16083a3

File tree

3 files changed

+117
-0
lines changed

3 files changed

+117
-0
lines changed

samples/rust/Kconfig

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,16 @@ menuconfig SAMPLES_RUST
1010

1111
if SAMPLES_RUST
1212

13+
config SAMPLE_RUST_DEBUGFS
14+
tristate "Debugfs"
15+
help
16+
This option builds the Rust debugfs module sample.
17+
18+
To compile this as a module, choose M here:
19+
the module will be called rust_debugfs.
20+
21+
If unsure, say N.
22+
1323
config SAMPLE_RUST_MINIMAL
1424
tristate "Minimal"
1525
help

samples/rust/Makefile

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
# SPDX-License-Identifier: GPL-2.0
22

3+
obj-$(CONFIG_SAMPLE_RUST_DEBUGFS) += rust_debugfs.o
34
obj-$(CONFIG_SAMPLE_RUST_MINIMAL) += rust_minimal.o
45
obj-$(CONFIG_SAMPLE_RUST_PRINT) += rust_print.o
56

samples/rust/rust_debugfs.rs

Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
// SPDX-License-Identifier: GPL-2.0
2+
3+
//! Rust debugfs device sample
4+
5+
#![allow(missing_docs)]
6+
7+
use kernel::{
8+
c_str, debugfs, file,
9+
file::File,
10+
io_buffer::IoBufferWriter,
11+
prelude::*,
12+
sync::{Arc, SpinLock},
13+
types::Mode,
14+
};
15+
16+
struct SampleFile;
17+
18+
#[vtable]
19+
impl file::Operations for SampleFile {
20+
fn open(_data: &(), _file: &File) -> Result {
21+
Ok(())
22+
}
23+
24+
fn read(
25+
_data: (),
26+
_file: &File,
27+
writer: &mut impl IoBufferWriter,
28+
offset: u64,
29+
) -> Result<usize> {
30+
let data = b"Sample debugfs file implementing file::Operations\n";
31+
let offset = offset as usize;
32+
33+
if offset > data.len() {
34+
return Ok(0);
35+
}
36+
37+
let len = core::cmp::min(writer.len(), data.len() - offset);
38+
writer.write_slice(&data[offset..(offset + len)])?;
39+
Ok(len)
40+
}
41+
}
42+
43+
#[pin_data]
44+
struct IncAttribute {
45+
#[pin]
46+
data: SpinLock<i64>,
47+
}
48+
49+
impl debugfs::attr::Attribute<i64> for IncAttribute {
50+
fn get(&self) -> Result<i64> {
51+
let mut guard = self.data.lock();
52+
let ret = *guard;
53+
*guard = ret + 1;
54+
Ok(ret)
55+
}
56+
57+
fn set(&self, val: i64) -> Result {
58+
let mut guard = self.data.lock();
59+
*guard = val;
60+
Ok(())
61+
}
62+
}
63+
64+
debugfs::attribute_signed!(IncAttribute, "%#d\n");
65+
66+
struct RustDebugfs {
67+
_sample_file: debugfs::PinnedRegistration,
68+
_inc_attribute: debugfs::PinnedRegistration<Arc<IncAttribute>>,
69+
}
70+
impl kernel::Module for RustDebugfs {
71+
fn init(_module: &'static ThisModule) -> Result<Self> {
72+
let dir = Arc::try_new(debugfs::Registration::register_dir(
73+
c_str!("rust_samples"),
74+
None,
75+
)?)?;
76+
77+
let sample_file = debugfs::Registration::register_file::<SampleFile>(
78+
c_str!("sample"),
79+
Mode::from_int(0444),
80+
(),
81+
Some(dir.clone()),
82+
)?;
83+
84+
let attribute = Arc::pin_init(pin_init!(IncAttribute {
85+
data <- kernel::new_spinlock!(0x42),
86+
}))?;
87+
let inc_attribute = attribute.register(
88+
c_str!("inc_attribute"),
89+
Mode::from_int(0666),
90+
Some(dir.clone()),
91+
)?;
92+
93+
Ok(Self {
94+
_sample_file: sample_file,
95+
_inc_attribute: inc_attribute,
96+
})
97+
}
98+
}
99+
100+
module! {
101+
type: RustDebugfs,
102+
name: "rust_debugfs",
103+
author: "Fabien Parent <[email protected]>",
104+
description: "Rust debugfs sample",
105+
license: "GPL",
106+
}

0 commit comments

Comments
 (0)