xref: /DragonOS/kernel/src/filesystem/sysfs/mod.rs (revision 6b4e7a2972cc06663754c0e35a0e541987006fa4)
1*6b4e7a29SLoGin use core::fmt::Debug;
2*6b4e7a29SLoGin 
3*6b4e7a29SLoGin use self::{dir::SysKernDirPriv, file::SysKernFilePriv};
4*6b4e7a29SLoGin 
5dd9f1fc1STingHuang use super::vfs::{
6*6b4e7a29SLoGin     core::generate_inode_id, file::FileMode, syscall::ModeType, FileSystem, FileType, FsInfo,
7*6b4e7a29SLoGin     IndexNode, Metadata, PollStatus,
8dd9f1fc1STingHuang };
9dd9f1fc1STingHuang use crate::{
10*6b4e7a29SLoGin     driver::base::{device::KObject, platform::platform_bus_init},
11b087521eSChiichen     filesystem::{sysfs::bus::sys_bus_init, vfs::ROOT_INODE},
12b087521eSChiichen     kdebug, kinfo,
13b087521eSChiichen     libs::{
14b087521eSChiichen         once::Once,
15b087521eSChiichen         spinlock::{SpinLock, SpinLockGuard},
16b087521eSChiichen     },
17dd9f1fc1STingHuang     syscall::SystemError,
18dd9f1fc1STingHuang     time::TimeSpec,
19dd9f1fc1STingHuang };
20dd9f1fc1STingHuang use alloc::{
21dd9f1fc1STingHuang     collections::BTreeMap,
22dd9f1fc1STingHuang     string::{String, ToString},
23dd9f1fc1STingHuang     sync::{Arc, Weak},
24dd9f1fc1STingHuang     vec::Vec,
25dd9f1fc1STingHuang };
26dd9f1fc1STingHuang 
27dd9f1fc1STingHuang pub mod bus;
28dd9f1fc1STingHuang pub mod class;
29dd9f1fc1STingHuang pub mod devices;
30*6b4e7a29SLoGin mod dir;
31*6b4e7a29SLoGin mod file;
32dd9f1fc1STingHuang pub mod fs;
33dd9f1fc1STingHuang 
34dd9f1fc1STingHuang const SYSFS_MAX_NAMELEN: usize = 64;
35dd9f1fc1STingHuang 
36ae5ede03SLoGin static mut __SYS_DEVICES_INODE: Option<Arc<dyn IndexNode>> = None;
37ae5ede03SLoGin static mut __SYS_BUS_INODE: Option<Arc<dyn IndexNode>> = None;
38ae5ede03SLoGin static mut __SYS_CLASS_INODE: Option<Arc<dyn IndexNode>> = None;
39ae5ede03SLoGin static mut __SYS_FS_INODE: Option<Arc<dyn IndexNode>> = None;
40dd9f1fc1STingHuang 
41dd9f1fc1STingHuang /// @brief 获取全局的sys/devices节点
42dd9f1fc1STingHuang #[inline(always)]
43dd9f1fc1STingHuang #[allow(non_snake_case)]
44dd9f1fc1STingHuang pub fn SYS_DEVICES_INODE() -> Arc<dyn IndexNode> {
45dd9f1fc1STingHuang     unsafe {
46dd9f1fc1STingHuang         return __SYS_DEVICES_INODE.as_ref().unwrap().clone();
47dd9f1fc1STingHuang     }
48dd9f1fc1STingHuang }
49dd9f1fc1STingHuang 
50dd9f1fc1STingHuang /// @brief 获取全局的sys/bus节点
51dd9f1fc1STingHuang #[inline(always)]
52dd9f1fc1STingHuang #[allow(non_snake_case)]
53dd9f1fc1STingHuang pub fn SYS_BUS_INODE() -> Arc<dyn IndexNode> {
54dd9f1fc1STingHuang     unsafe {
55dd9f1fc1STingHuang         return __SYS_BUS_INODE.as_ref().unwrap().clone();
56dd9f1fc1STingHuang     }
57dd9f1fc1STingHuang }
58dd9f1fc1STingHuang 
59dd9f1fc1STingHuang /// @brief 获取全局的sys/class节点
60dd9f1fc1STingHuang #[inline(always)]
61dd9f1fc1STingHuang #[allow(non_snake_case)]
62dd9f1fc1STingHuang pub fn SYS_CLASS_INODE() -> Arc<dyn IndexNode> {
63dd9f1fc1STingHuang     unsafe {
64dd9f1fc1STingHuang         return __SYS_CLASS_INODE.as_ref().unwrap().clone();
65dd9f1fc1STingHuang     }
66dd9f1fc1STingHuang }
67dd9f1fc1STingHuang 
68dd9f1fc1STingHuang /// @brief 获取全局的sys/fs节点
69dd9f1fc1STingHuang #[inline(always)]
70dd9f1fc1STingHuang #[allow(non_snake_case)]
71dd9f1fc1STingHuang pub fn SYS_FS_INODE() -> Arc<dyn IndexNode> {
72dd9f1fc1STingHuang     unsafe {
73dd9f1fc1STingHuang         return __SYS_FS_INODE.as_ref().unwrap().clone();
74dd9f1fc1STingHuang     }
75dd9f1fc1STingHuang }
76dd9f1fc1STingHuang 
77dd9f1fc1STingHuang /// @brief dev文件系统
78dd9f1fc1STingHuang #[derive(Debug)]
79dd9f1fc1STingHuang pub struct SysFS {
80dd9f1fc1STingHuang     // 文件系统根节点
81dd9f1fc1STingHuang     root_inode: Arc<LockedSysFSInode>,
82dd9f1fc1STingHuang }
83dd9f1fc1STingHuang 
84dd9f1fc1STingHuang impl FileSystem for SysFS {
85dd9f1fc1STingHuang     fn as_any_ref(&self) -> &dyn core::any::Any {
86dd9f1fc1STingHuang         self
87dd9f1fc1STingHuang     }
88dd9f1fc1STingHuang 
89dd9f1fc1STingHuang     fn root_inode(&self) -> Arc<dyn super::vfs::IndexNode> {
90dd9f1fc1STingHuang         return self.root_inode.clone();
91dd9f1fc1STingHuang     }
92dd9f1fc1STingHuang 
93dd9f1fc1STingHuang     fn info(&self) -> super::vfs::FsInfo {
94dd9f1fc1STingHuang         return FsInfo {
95dd9f1fc1STingHuang             blk_dev_id: 0,
96dd9f1fc1STingHuang             max_name_len: SYSFS_MAX_NAMELEN,
97dd9f1fc1STingHuang         };
98dd9f1fc1STingHuang     }
99dd9f1fc1STingHuang }
100dd9f1fc1STingHuang 
101dd9f1fc1STingHuang impl SysFS {
102dd9f1fc1STingHuang     pub fn new() -> Arc<Self> {
103dd9f1fc1STingHuang         // 初始化root inode
104dd9f1fc1STingHuang         let root: Arc<LockedSysFSInode> = Arc::new(LockedSysFSInode(SpinLock::new(
105dd9f1fc1STingHuang             // /sys 的权限设置为 读+执行,root 可以读写
106dd9f1fc1STingHuang             // root 的 parent 是空指针
107*6b4e7a29SLoGin             SysFSInode::new(FileType::Dir, ModeType::from_bits_truncate(0o755), 0),
108dd9f1fc1STingHuang         )));
109dd9f1fc1STingHuang 
110dd9f1fc1STingHuang         let sysfs: Arc<SysFS> = Arc::new(SysFS { root_inode: root });
111dd9f1fc1STingHuang 
112dd9f1fc1STingHuang         // 对root inode加锁,并继续完成初始化工作
113dd9f1fc1STingHuang         let mut root_guard: SpinLockGuard<SysFSInode> = sysfs.root_inode.0.lock();
114dd9f1fc1STingHuang         root_guard.parent = Arc::downgrade(&sysfs.root_inode);
115dd9f1fc1STingHuang         root_guard.self_ref = Arc::downgrade(&sysfs.root_inode);
116dd9f1fc1STingHuang         root_guard.fs = Arc::downgrade(&sysfs);
117dd9f1fc1STingHuang         // 释放锁
118dd9f1fc1STingHuang         drop(root_guard);
119dd9f1fc1STingHuang 
120dd9f1fc1STingHuang         // 创建文件夹
121dd9f1fc1STingHuang         let root: &Arc<LockedSysFSInode> = &sysfs.root_inode;
122dd9f1fc1STingHuang         match root.add_dir("devices") {
123dd9f1fc1STingHuang             Ok(devices) => unsafe {
124ae5ede03SLoGin                 __SYS_DEVICES_INODE = Some(devices);
125dd9f1fc1STingHuang             },
126dd9f1fc1STingHuang             Err(_) => panic!("SysFS: Failed to create /sys/devices"),
127dd9f1fc1STingHuang         }
128dd9f1fc1STingHuang 
129dd9f1fc1STingHuang         match root.add_dir("bus") {
130dd9f1fc1STingHuang             Ok(bus) => unsafe {
131ae5ede03SLoGin                 __SYS_BUS_INODE = Some(bus);
132dd9f1fc1STingHuang             },
133dd9f1fc1STingHuang             Err(_) => panic!("SysFS: Failed to create /sys/bus"),
134dd9f1fc1STingHuang         }
135dd9f1fc1STingHuang 
136dd9f1fc1STingHuang         match root.add_dir("class") {
137dd9f1fc1STingHuang             Ok(class) => unsafe {
138ae5ede03SLoGin                 __SYS_CLASS_INODE = Some(class);
139dd9f1fc1STingHuang             },
140dd9f1fc1STingHuang             Err(_) => panic!("SysFS: Failed to create /sys/class"),
141dd9f1fc1STingHuang         }
142dd9f1fc1STingHuang 
143dd9f1fc1STingHuang         match root.add_dir("fs") {
144dd9f1fc1STingHuang             Ok(fs) => unsafe {
145ae5ede03SLoGin                 __SYS_FS_INODE = Some(fs);
146dd9f1fc1STingHuang             },
147dd9f1fc1STingHuang             Err(_) => panic!("SysFS: Failed to create /sys/fs"),
148dd9f1fc1STingHuang         }
149b087521eSChiichen 
150dd9f1fc1STingHuang         return sysfs;
151dd9f1fc1STingHuang     }
152dd9f1fc1STingHuang }
153dd9f1fc1STingHuang 
154dd9f1fc1STingHuang /// @brief sys文件i节点(锁)
155dd9f1fc1STingHuang #[derive(Debug)]
156dd9f1fc1STingHuang pub struct LockedSysFSInode(SpinLock<SysFSInode>);
157dd9f1fc1STingHuang 
158dd9f1fc1STingHuang impl IndexNode for LockedSysFSInode {
159dd9f1fc1STingHuang     fn as_any_ref(&self) -> &dyn core::any::Any {
160dd9f1fc1STingHuang         self
161dd9f1fc1STingHuang     }
162dd9f1fc1STingHuang 
163ae5ede03SLoGin     fn resize(&self, _len: usize) -> Result<(), SystemError> {
164ae5ede03SLoGin         return Ok(());
165ae5ede03SLoGin     }
166ae5ede03SLoGin 
167ae5ede03SLoGin     fn truncate(&self, _len: usize) -> Result<(), SystemError> {
168ae5ede03SLoGin         return Ok(());
169ae5ede03SLoGin     }
170ae5ede03SLoGin 
171dd9f1fc1STingHuang     fn open(
172dd9f1fc1STingHuang         &self,
173dd9f1fc1STingHuang         _data: &mut super::vfs::FilePrivateData,
174dd9f1fc1STingHuang         _mode: &FileMode,
175dd9f1fc1STingHuang     ) -> Result<(), SystemError> {
176dd9f1fc1STingHuang         return Ok(());
177dd9f1fc1STingHuang     }
178dd9f1fc1STingHuang 
179dd9f1fc1STingHuang     fn close(&self, _data: &mut super::vfs::FilePrivateData) -> Result<(), SystemError> {
180dd9f1fc1STingHuang         return Ok(());
181dd9f1fc1STingHuang     }
182dd9f1fc1STingHuang 
183dd9f1fc1STingHuang     fn read_at(
184dd9f1fc1STingHuang         &self,
185dd9f1fc1STingHuang         _offset: usize,
186dd9f1fc1STingHuang         _len: usize,
187dd9f1fc1STingHuang         _buf: &mut [u8],
188dd9f1fc1STingHuang         _data: &mut super::vfs::FilePrivateData,
189dd9f1fc1STingHuang     ) -> Result<usize, SystemError> {
190dd9f1fc1STingHuang         return Err(SystemError::EOPNOTSUPP_OR_ENOTSUP);
191dd9f1fc1STingHuang     }
192dd9f1fc1STingHuang 
193dd9f1fc1STingHuang     fn write_at(
194dd9f1fc1STingHuang         &self,
195dd9f1fc1STingHuang         _offset: usize,
196dd9f1fc1STingHuang         _len: usize,
197dd9f1fc1STingHuang         _buf: &[u8],
198dd9f1fc1STingHuang         _data: &mut super::vfs::FilePrivateData,
199dd9f1fc1STingHuang     ) -> Result<usize, SystemError> {
200dd9f1fc1STingHuang         return Err(SystemError::EOPNOTSUPP_OR_ENOTSUP);
201dd9f1fc1STingHuang     }
202dd9f1fc1STingHuang 
203dd9f1fc1STingHuang     fn poll(&self) -> Result<super::vfs::PollStatus, SystemError> {
204dd9f1fc1STingHuang         // 加锁
205dd9f1fc1STingHuang         let inode: SpinLockGuard<SysFSInode> = self.0.lock();
206dd9f1fc1STingHuang 
207dd9f1fc1STingHuang         // 检查当前inode是否为一个文件夹,如果是的话,就返回错误
208dd9f1fc1STingHuang         if inode.metadata.file_type == FileType::Dir {
209dd9f1fc1STingHuang             return Err(SystemError::EISDIR);
210dd9f1fc1STingHuang         }
211dd9f1fc1STingHuang 
212dd9f1fc1STingHuang         return Ok(PollStatus::READ | PollStatus::WRITE);
213dd9f1fc1STingHuang     }
214dd9f1fc1STingHuang 
215dd9f1fc1STingHuang     fn metadata(&self) -> Result<Metadata, SystemError> {
216dd9f1fc1STingHuang         return Ok(self.0.lock().metadata.clone());
217dd9f1fc1STingHuang     }
218dd9f1fc1STingHuang 
219dd9f1fc1STingHuang     fn fs(&self) -> Arc<dyn FileSystem> {
220dd9f1fc1STingHuang         return self.0.lock().fs.upgrade().unwrap();
221dd9f1fc1STingHuang     }
222dd9f1fc1STingHuang 
223dd9f1fc1STingHuang     fn get_entry_name(&self, ino: super::vfs::InodeId) -> Result<String, SystemError> {
224dd9f1fc1STingHuang         let inode: SpinLockGuard<SysFSInode> = self.0.lock();
225dd9f1fc1STingHuang         if inode.metadata.file_type != FileType::Dir {
226dd9f1fc1STingHuang             return Err(SystemError::ENOTDIR);
227dd9f1fc1STingHuang         }
228dd9f1fc1STingHuang 
229*6b4e7a29SLoGin         match ino.into() {
230dd9f1fc1STingHuang             0 => {
231dd9f1fc1STingHuang                 return Ok(String::from("."));
232dd9f1fc1STingHuang             }
233dd9f1fc1STingHuang             1 => {
234dd9f1fc1STingHuang                 return Ok(String::from(".."));
235dd9f1fc1STingHuang             }
236dd9f1fc1STingHuang             ino => {
237dd9f1fc1STingHuang                 // 暴力遍历所有的children,判断inode id是否相同
238dd9f1fc1STingHuang                 // TODO: 优化这里,这个地方性能很差!
239dd9f1fc1STingHuang                 let mut key: Vec<String> = inode
240dd9f1fc1STingHuang                     .children
241dd9f1fc1STingHuang                     .keys()
242*6b4e7a29SLoGin                     .filter(|k| {
243*6b4e7a29SLoGin                         inode
244*6b4e7a29SLoGin                             .children
245*6b4e7a29SLoGin                             .get(*k)
246*6b4e7a29SLoGin                             .unwrap()
247*6b4e7a29SLoGin                             .metadata()
248*6b4e7a29SLoGin                             .unwrap()
249*6b4e7a29SLoGin                             .inode_id
250*6b4e7a29SLoGin                             .into()
251*6b4e7a29SLoGin                             == ino
252*6b4e7a29SLoGin                     })
253dd9f1fc1STingHuang                     .cloned()
254dd9f1fc1STingHuang                     .collect();
255dd9f1fc1STingHuang 
256dd9f1fc1STingHuang                 match key.len() {
257dd9f1fc1STingHuang                     0=>{return Err(SystemError::ENOENT);}
258dd9f1fc1STingHuang                     1=>{return Ok(key.remove(0));}
259*6b4e7a29SLoGin                     _ => panic!("Sysfs get_entry_name: key.len()={key_len}>1, current inode_id={inode_id:?}, to find={to_find:?}", key_len=key.len(), inode_id = inode.metadata.inode_id, to_find=ino)
260dd9f1fc1STingHuang                 }
261dd9f1fc1STingHuang             }
262dd9f1fc1STingHuang         }
263dd9f1fc1STingHuang     }
264dd9f1fc1STingHuang 
265dd9f1fc1STingHuang     fn find(&self, name: &str) -> Result<Arc<dyn IndexNode>, SystemError> {
266dd9f1fc1STingHuang         let inode = self.0.lock();
267dd9f1fc1STingHuang 
268dd9f1fc1STingHuang         if inode.metadata.file_type != FileType::Dir {
269dd9f1fc1STingHuang             return Err(SystemError::ENOTDIR);
270dd9f1fc1STingHuang         }
271dd9f1fc1STingHuang 
272dd9f1fc1STingHuang         match name {
273dd9f1fc1STingHuang             "" | "." => {
274dd9f1fc1STingHuang                 return Ok(inode.self_ref.upgrade().ok_or(SystemError::ENOENT)?);
275dd9f1fc1STingHuang             }
276dd9f1fc1STingHuang             ".." => {
277dd9f1fc1STingHuang                 return Ok(inode.parent.upgrade().ok_or(SystemError::ENOENT)?);
278dd9f1fc1STingHuang             }
279dd9f1fc1STingHuang             name => {
280dd9f1fc1STingHuang                 // 在子目录项中查找
281dd9f1fc1STingHuang                 // match inode.children.get(name) {
282dd9f1fc1STingHuang                 //     Some(_) => {}
283dd9f1fc1STingHuang                 //     None => kdebug!("Sysfs find {} error", name),
284dd9f1fc1STingHuang                 // }
285dd9f1fc1STingHuang                 return Ok(inode.children.get(name).ok_or(SystemError::ENOENT)?.clone());
286dd9f1fc1STingHuang             }
287dd9f1fc1STingHuang         }
288dd9f1fc1STingHuang     }
289dd9f1fc1STingHuang 
290dd9f1fc1STingHuang     fn ioctl(&self, _cmd: u32, _data: usize) -> Result<usize, SystemError> {
291dd9f1fc1STingHuang         Err(SystemError::EOPNOTSUPP_OR_ENOTSUP)
292dd9f1fc1STingHuang     }
293dd9f1fc1STingHuang 
294dd9f1fc1STingHuang     fn list(&self) -> Result<Vec<String>, SystemError> {
295dd9f1fc1STingHuang         let info = self.metadata()?;
296dd9f1fc1STingHuang         if info.file_type != FileType::Dir {
297dd9f1fc1STingHuang             return Err(SystemError::ENOTDIR);
298dd9f1fc1STingHuang         }
299dd9f1fc1STingHuang 
300dd9f1fc1STingHuang         let mut keys: Vec<String> = Vec::new();
301dd9f1fc1STingHuang         keys.push(String::from("."));
302dd9f1fc1STingHuang         keys.push(String::from(".."));
303dd9f1fc1STingHuang         keys.append(&mut self.0.lock().children.keys().cloned().collect());
304dd9f1fc1STingHuang 
305dd9f1fc1STingHuang         return Ok(keys);
306dd9f1fc1STingHuang     }
307dd9f1fc1STingHuang }
308dd9f1fc1STingHuang 
309dd9f1fc1STingHuang impl LockedSysFSInode {
310dd9f1fc1STingHuang     fn do_create_with_data(
311dd9f1fc1STingHuang         &self,
312dd9f1fc1STingHuang         mut guard: SpinLockGuard<SysFSInode>,
313*6b4e7a29SLoGin         name: &str,
314*6b4e7a29SLoGin         file_type: FileType,
315*6b4e7a29SLoGin         mode: ModeType,
316*6b4e7a29SLoGin         data: usize,
317dd9f1fc1STingHuang     ) -> Result<Arc<dyn IndexNode>, SystemError> {
318dd9f1fc1STingHuang         if guard.metadata.file_type != FileType::Dir {
319dd9f1fc1STingHuang             return Err(SystemError::ENOTDIR);
320dd9f1fc1STingHuang         }
321dd9f1fc1STingHuang 
322dd9f1fc1STingHuang         // 如果有重名的,则返回
323*6b4e7a29SLoGin         if guard.children.contains_key(name) {
324dd9f1fc1STingHuang             return Err(SystemError::EEXIST);
325dd9f1fc1STingHuang         }
326dd9f1fc1STingHuang 
327dd9f1fc1STingHuang         // 创建inode
328dd9f1fc1STingHuang         let result: Arc<LockedSysFSInode> = Arc::new(LockedSysFSInode(SpinLock::new(SysFSInode {
329dd9f1fc1STingHuang             parent: guard.self_ref.clone(),
330dd9f1fc1STingHuang             self_ref: Weak::default(),
331dd9f1fc1STingHuang             children: BTreeMap::new(),
332dd9f1fc1STingHuang             metadata: Metadata {
333dd9f1fc1STingHuang                 dev_id: 0,
334dd9f1fc1STingHuang                 inode_id: generate_inode_id(),
335dd9f1fc1STingHuang                 size: 0,
336dd9f1fc1STingHuang                 blk_size: 0,
337dd9f1fc1STingHuang                 blocks: 0,
338dd9f1fc1STingHuang                 atime: TimeSpec::default(),
339dd9f1fc1STingHuang                 mtime: TimeSpec::default(),
340dd9f1fc1STingHuang                 ctime: TimeSpec::default(),
341*6b4e7a29SLoGin                 file_type,
342*6b4e7a29SLoGin                 mode,
343dd9f1fc1STingHuang                 nlinks: 1,
344dd9f1fc1STingHuang                 uid: 0,
345dd9f1fc1STingHuang                 gid: 0,
346*6b4e7a29SLoGin                 raw_dev: data,
347dd9f1fc1STingHuang             },
348dd9f1fc1STingHuang             fs: guard.fs.clone(),
349dd9f1fc1STingHuang         })));
350dd9f1fc1STingHuang 
351dd9f1fc1STingHuang         // 初始化inode的自引用的weak指针
352dd9f1fc1STingHuang         result.0.lock().self_ref = Arc::downgrade(&result);
353dd9f1fc1STingHuang 
354dd9f1fc1STingHuang         // 将子inode插入父inode的B树中
355*6b4e7a29SLoGin         guard.children.insert(String::from(name), result.clone());
356dd9f1fc1STingHuang         return Ok(result);
357dd9f1fc1STingHuang     }
358dd9f1fc1STingHuang 
359dd9f1fc1STingHuang     /// @brief 在当前目录下,创建一个目录
360dd9f1fc1STingHuang     /// @param name: 目录名
361dd9f1fc1STingHuang     /// @return 成功返回目录inode, 失败返回Err(错误码)
362dd9f1fc1STingHuang     #[inline]
363dd9f1fc1STingHuang     #[allow(dead_code)]
364dd9f1fc1STingHuang     pub fn add_dir(&self, name: &str) -> Result<Arc<dyn IndexNode>, SystemError> {
365dd9f1fc1STingHuang         let guard: SpinLockGuard<SysFSInode> = self.0.lock();
366dd9f1fc1STingHuang 
367dd9f1fc1STingHuang         if guard.children.contains_key(name) {
368dd9f1fc1STingHuang             return Err(SystemError::EEXIST);
369dd9f1fc1STingHuang         }
370dd9f1fc1STingHuang 
371*6b4e7a29SLoGin         match self.do_create_with_data(
372*6b4e7a29SLoGin             guard,
373*6b4e7a29SLoGin             name,
374*6b4e7a29SLoGin             FileType::Dir,
375*6b4e7a29SLoGin             ModeType::from_bits_truncate(0o755),
376*6b4e7a29SLoGin             0,
377*6b4e7a29SLoGin         ) {
378dd9f1fc1STingHuang             Ok(inode) => return Ok(inode),
379dd9f1fc1STingHuang             Err(err) => {
380dd9f1fc1STingHuang                 return Err(err);
381dd9f1fc1STingHuang             }
382dd9f1fc1STingHuang         };
383dd9f1fc1STingHuang     }
384dd9f1fc1STingHuang 
385dd9f1fc1STingHuang     /// @brief 在当前目录下,创建一个二进制文件
386dd9f1fc1STingHuang     /// @param name: 文件名
387dd9f1fc1STingHuang     /// @return 成功返回Ok(()), 失败返回Err(错误码)
388dd9f1fc1STingHuang     #[inline]
389dd9f1fc1STingHuang     #[allow(dead_code)]
390dd9f1fc1STingHuang     pub fn add_file(&self, name: &str, file: Arc<dyn IndexNode>) -> Result<(), SystemError> {
391dd9f1fc1STingHuang         let mut this = self.0.lock();
392dd9f1fc1STingHuang 
393dd9f1fc1STingHuang         if this.children.contains_key(name) {
394dd9f1fc1STingHuang             return Err(SystemError::EEXIST);
395dd9f1fc1STingHuang         }
396dd9f1fc1STingHuang 
397dd9f1fc1STingHuang         this.children.insert(name.to_string(), file);
398dd9f1fc1STingHuang         return Ok(());
399dd9f1fc1STingHuang     }
400dd9f1fc1STingHuang 
401dd9f1fc1STingHuang     /// @brief 为该inode创建硬链接
402dd9f1fc1STingHuang     /// @param None
403dd9f1fc1STingHuang     /// @return 当前inode强引用
404dd9f1fc1STingHuang     #[inline]
405dd9f1fc1STingHuang     #[allow(dead_code)]
406dd9f1fc1STingHuang     pub fn link(&self) -> Arc<dyn IndexNode> {
407dd9f1fc1STingHuang         return self
408dd9f1fc1STingHuang             .0
409dd9f1fc1STingHuang             .lock()
410dd9f1fc1STingHuang             .self_ref
411dd9f1fc1STingHuang             .clone()
412dd9f1fc1STingHuang             .upgrade()
413dd9f1fc1STingHuang             .ok_or(SystemError::E2BIG)
414dd9f1fc1STingHuang             .unwrap();
415dd9f1fc1STingHuang     }
416dd9f1fc1STingHuang 
417dd9f1fc1STingHuang     pub fn remove(&self, name: &str) -> Result<(), SystemError> {
418dd9f1fc1STingHuang         let x = self
419dd9f1fc1STingHuang             .0
420dd9f1fc1STingHuang             .lock()
421dd9f1fc1STingHuang             .children
422dd9f1fc1STingHuang             .remove(name)
423dd9f1fc1STingHuang             .ok_or(SystemError::ENOENT)?;
424dd9f1fc1STingHuang 
425dd9f1fc1STingHuang         drop(x);
426dd9f1fc1STingHuang         return Ok(());
427dd9f1fc1STingHuang     }
428dd9f1fc1STingHuang }
429dd9f1fc1STingHuang 
430dd9f1fc1STingHuang /// @brief sys文件i节点(无锁)
431dd9f1fc1STingHuang #[derive(Debug)]
432dd9f1fc1STingHuang pub struct SysFSInode {
433dd9f1fc1STingHuang     /// 指向父Inode的弱引用
434dd9f1fc1STingHuang     parent: Weak<LockedSysFSInode>,
435dd9f1fc1STingHuang     /// 指向自身的弱引用
436dd9f1fc1STingHuang     self_ref: Weak<LockedSysFSInode>,
437dd9f1fc1STingHuang     /// 子Inode的B树
438dd9f1fc1STingHuang     children: BTreeMap<String, Arc<dyn IndexNode>>,
439dd9f1fc1STingHuang     /// 指向inode所在的文件系统对象的指针
440dd9f1fc1STingHuang     fs: Weak<SysFS>,
441dd9f1fc1STingHuang     /// INode 元数据
442dd9f1fc1STingHuang     metadata: Metadata,
443dd9f1fc1STingHuang }
444dd9f1fc1STingHuang 
445dd9f1fc1STingHuang impl SysFSInode {
446*6b4e7a29SLoGin     pub fn new(file_type: FileType, mode: ModeType, data_: usize) -> Self {
447*6b4e7a29SLoGin         return Self::new_with_parent(Weak::default(), file_type, mode, data_);
448dd9f1fc1STingHuang     }
449dd9f1fc1STingHuang 
450dd9f1fc1STingHuang     pub fn new_with_parent(
451dd9f1fc1STingHuang         parent: Weak<LockedSysFSInode>,
452*6b4e7a29SLoGin         file_type: FileType,
453*6b4e7a29SLoGin         mode: ModeType,
454dd9f1fc1STingHuang         data_: usize,
455dd9f1fc1STingHuang     ) -> Self {
456dd9f1fc1STingHuang         return SysFSInode {
457dd9f1fc1STingHuang             parent: parent,
458dd9f1fc1STingHuang             self_ref: Weak::default(),
459dd9f1fc1STingHuang             children: BTreeMap::new(),
460dd9f1fc1STingHuang             metadata: Metadata {
461dd9f1fc1STingHuang                 dev_id: 1,
462dd9f1fc1STingHuang                 inode_id: generate_inode_id(),
463dd9f1fc1STingHuang                 size: 0,
464dd9f1fc1STingHuang                 blk_size: 0,
465dd9f1fc1STingHuang                 blocks: 0,
466dd9f1fc1STingHuang                 atime: TimeSpec::default(),
467dd9f1fc1STingHuang                 mtime: TimeSpec::default(),
468dd9f1fc1STingHuang                 ctime: TimeSpec::default(),
469*6b4e7a29SLoGin                 file_type,
470*6b4e7a29SLoGin                 mode,
471dd9f1fc1STingHuang                 nlinks: 1,
472dd9f1fc1STingHuang                 uid: 0,
473dd9f1fc1STingHuang                 gid: 0,
474dd9f1fc1STingHuang                 raw_dev: data_,
475dd9f1fc1STingHuang             },
476dd9f1fc1STingHuang             fs: Weak::default(),
477dd9f1fc1STingHuang         };
478dd9f1fc1STingHuang     }
479dd9f1fc1STingHuang }
480b087521eSChiichen 
481b087521eSChiichen pub fn sysfs_init() -> Result<(), SystemError> {
482b087521eSChiichen     static INIT: Once = Once::new();
483b087521eSChiichen     let mut result = None;
484b087521eSChiichen     INIT.call_once(|| {
485b087521eSChiichen         kinfo!("Initializing SysFS...");
486b087521eSChiichen         // 创建 sysfs 实例
487b087521eSChiichen         let sysfs: Arc<SysFS> = SysFS::new();
488b087521eSChiichen 
489b087521eSChiichen         // sysfs 挂载
490b087521eSChiichen         let _t = ROOT_INODE()
491b087521eSChiichen             .find("sys")
492b087521eSChiichen             .expect("Cannot find /sys")
493b087521eSChiichen             .mount(sysfs)
494b087521eSChiichen             .expect("Failed to mount sysfs");
495b087521eSChiichen         kinfo!("SysFS mounted.");
496b087521eSChiichen 
497b087521eSChiichen         // 初始化platform总线
498b087521eSChiichen         platform_bus_init().expect("platform bus init failed");
499b087521eSChiichen 
500b087521eSChiichen         sys_bus_init(&SYS_BUS_INODE()).unwrap_or_else(|err| {
501b087521eSChiichen             panic!("sys_bus_init failed: {:?}", err);
502b087521eSChiichen         });
503b087521eSChiichen 
504b087521eSChiichen         kdebug!("sys_bus_init result: {:?}", SYS_BUS_INODE().list());
505b087521eSChiichen         result = Some(Ok(()));
506b087521eSChiichen     });
507b087521eSChiichen 
508b087521eSChiichen     return result.unwrap();
509b087521eSChiichen }
510*6b4e7a29SLoGin 
511*6b4e7a29SLoGin /// SysFS在KernFS的inode中的私有信息
512*6b4e7a29SLoGin #[allow(dead_code)]
513*6b4e7a29SLoGin #[derive(Debug)]
514*6b4e7a29SLoGin pub enum SysFSKernPrivateData {
515*6b4e7a29SLoGin     Dir(SysKernDirPriv),
516*6b4e7a29SLoGin     File(SysKernFilePriv),
517*6b4e7a29SLoGin }
518*6b4e7a29SLoGin 
519*6b4e7a29SLoGin /// sysfs文件目录的属性组
520*6b4e7a29SLoGin pub trait AttributeGroup: Debug + Send + Sync {
521*6b4e7a29SLoGin     fn name(&self) -> &str;
522*6b4e7a29SLoGin     fn attrs(&self) -> &[&'static dyn Attribute];
523*6b4e7a29SLoGin     fn is_visible(&self, kobj: Arc<dyn KObject>, attr: &dyn Attribute) -> bool;
524*6b4e7a29SLoGin }
525*6b4e7a29SLoGin 
526*6b4e7a29SLoGin /// sysfs文件的属性
527*6b4e7a29SLoGin pub trait Attribute: Debug + Send + Sync {
528*6b4e7a29SLoGin     fn name(&self) -> &str;
529*6b4e7a29SLoGin     fn mode(&self) -> ModeType;
530*6b4e7a29SLoGin }
531