1 use core::intrinsics::size_of; 2 3 use alloc::{ 4 borrow::ToOwned, 5 collections::BTreeMap, 6 format, 7 string::String, 8 sync::{Arc, Weak}, 9 vec::Vec, 10 }; 11 use system_error::SystemError; 12 13 use crate::{ 14 arch::mm::LockedFrameAllocator, 15 driver::base::device::device_number::DeviceNumber, 16 filesystem::vfs::{ 17 core::{generate_inode_id, ROOT_INODE}, 18 FileType, 19 }, 20 kerror, kinfo, 21 libs::{ 22 once::Once, 23 spinlock::{SpinLock, SpinLockGuard}, 24 }, 25 mm::allocator::page_frame::FrameAllocator, 26 process::{Pid, ProcessManager}, 27 time::TimeSpec, 28 }; 29 30 use super::vfs::{ 31 file::{FileMode, FilePrivateData}, 32 syscall::ModeType, 33 FileSystem, FsInfo, IndexNode, InodeId, Metadata, 34 }; 35 36 pub mod kmsg; 37 pub mod log; 38 mod syscall; 39 40 /// @brief 进程文件类型 41 /// @usage 用于定义进程文件夹下的各类文件类型 42 #[derive(Debug)] 43 #[repr(u8)] 44 pub enum ProcFileType { 45 ///展示进程状态信息 46 ProcStatus = 0, 47 /// meminfo 48 ProcMeminfo = 1, 49 /// kmsg 50 ProcKmsg = 2, 51 //todo: 其他文件类型 52 ///默认文件类型 53 Default, 54 } 55 56 impl From<u8> for ProcFileType { 57 fn from(value: u8) -> Self { 58 match value { 59 0 => ProcFileType::ProcStatus, 60 1 => ProcFileType::ProcMeminfo, 61 2 => ProcFileType::ProcKmsg, 62 _ => ProcFileType::Default, 63 } 64 } 65 } 66 /// @brief 节点私有信息结构体 67 /// @usage 用于传入各类文件所需的信息 68 #[derive(Debug)] 69 pub struct InodeInfo { 70 ///进程的pid 71 pid: Pid, 72 ///文件类型 73 ftype: ProcFileType, 74 //其他需要传入的信息在此定义 75 } 76 77 /// @brief procfs的inode名称的最大长度 78 const PROCFS_MAX_NAMELEN: usize = 64; 79 80 /// @brief procfs文件系统的Inode结构体 81 #[derive(Debug)] 82 pub struct LockedProcFSInode(SpinLock<ProcFSInode>); 83 84 /// @brief procfs文件系统结构体 85 #[derive(Debug)] 86 pub struct ProcFS { 87 /// procfs的root inode 88 root_inode: Arc<LockedProcFSInode>, 89 } 90 91 #[derive(Debug, Clone)] 92 pub struct ProcfsFilePrivateData { 93 data: Vec<u8>, 94 } 95 96 impl ProcfsFilePrivateData { 97 pub fn new() -> Self { 98 return ProcfsFilePrivateData { data: Vec::new() }; 99 } 100 } 101 102 /// @brief procfs文件系统的Inode结构体(不包含锁) 103 #[derive(Debug)] 104 pub struct ProcFSInode { 105 /// 指向父Inode的弱引用 106 parent: Weak<LockedProcFSInode>, 107 /// 指向自身的弱引用 108 self_ref: Weak<LockedProcFSInode>, 109 /// 子Inode的B树 110 children: BTreeMap<String, Arc<LockedProcFSInode>>, 111 /// 当前inode的数据部分 112 data: Vec<u8>, 113 /// 当前inode的元数据 114 metadata: Metadata, 115 /// 指向inode所在的文件系统对象的指针 116 fs: Weak<ProcFS>, 117 /// 储存私有信息 118 fdata: InodeInfo, 119 } 120 121 /// 对ProcFSInode实现获取各类文件信息的函数 122 impl ProcFSInode { 123 /// @brief 去除Vec中所有的\0,并在结尾添加\0 124 #[inline] 125 fn trim_string(&self, data: &mut Vec<u8>) { 126 data.retain(|x| *x != 0); 127 128 data.push(0); 129 } 130 // todo:其他数据获取函数实现 131 132 /// @brief 打开status文件 133 /// 134 fn open_status(&self, pdata: &mut ProcfsFilePrivateData) -> Result<i64, SystemError> { 135 // 获取该pid对应的pcb结构体 136 let pid = self.fdata.pid; 137 let pcb = ProcessManager::find(pid); 138 let pcb = if pcb.is_none() { 139 kerror!( 140 "ProcFS: Cannot find pcb for pid {:?} when opening its 'status' file.", 141 pid 142 ); 143 return Err(SystemError::ESRCH); 144 } else { 145 pcb.unwrap() 146 }; 147 // 传入数据 148 let pdata: &mut Vec<u8> = &mut pdata.data; 149 150 pdata.append( 151 &mut format!("Name:\t{}", pcb.basic().name()) 152 .as_bytes() 153 .to_owned(), 154 ); 155 156 let sched_info_guard = pcb.sched_info(); 157 let state = sched_info_guard.inner_lock_read_irqsave().state(); 158 let cpu_id = sched_info_guard 159 .on_cpu() 160 .map(|cpu| cpu.data() as i32) 161 .unwrap_or(-1); 162 163 let priority = sched_info_guard.priority(); 164 let vrtime = sched_info_guard.virtual_runtime(); 165 166 pdata.append(&mut format!("\nState:\t{:?}", state).as_bytes().to_owned()); 167 pdata.append( 168 &mut format!("\nPid:\t{}", pcb.pid().into()) 169 .as_bytes() 170 .to_owned(), 171 ); 172 pdata.append( 173 &mut format!("\nPpid:\t{}", pcb.basic().ppid().into()) 174 .as_bytes() 175 .to_owned(), 176 ); 177 pdata.append(&mut format!("\ncpu_id:\t{}", cpu_id).as_bytes().to_owned()); 178 pdata.append( 179 &mut format!("\npriority:\t{}", priority.data()) 180 .as_bytes() 181 .to_owned(), 182 ); 183 pdata.append( 184 &mut format!("\npreempt:\t{}", pcb.preempt_count()) 185 .as_bytes() 186 .to_owned(), 187 ); 188 pdata.append(&mut format!("\nvrtime:\t{}", vrtime).as_bytes().to_owned()); 189 190 if let Some(user_vm) = pcb.basic().user_vm() { 191 let address_space_guard = user_vm.read(); 192 // todo: 当前进程运行过程中占用内存的峰值 193 let hiwater_vm: u64 = 0; 194 // 进程代码段的大小 195 let text = (address_space_guard.end_code - address_space_guard.start_code) / 1024; 196 // 进程数据段的大小 197 let data = (address_space_guard.end_data - address_space_guard.start_data) / 1024; 198 drop(address_space_guard); 199 pdata.append( 200 &mut format!("\nVmPeak:\t{} kB", hiwater_vm) 201 .as_bytes() 202 .to_owned(), 203 ); 204 pdata.append(&mut format!("\nVmData:\t{} kB", data).as_bytes().to_owned()); 205 pdata.append(&mut format!("\nVmExe:\t{} kB", text).as_bytes().to_owned()); 206 } 207 208 pdata.append( 209 &mut format!("\nflags: {:?}\n", pcb.flags().clone()) 210 .as_bytes() 211 .to_owned(), 212 ); 213 214 // 去除多余的\0 215 self.trim_string(pdata); 216 217 return Ok((pdata.len() * size_of::<u8>()) as i64); 218 } 219 220 /// 打开 meminfo 文件 221 fn open_meminfo(&self, pdata: &mut ProcfsFilePrivateData) -> Result<i64, SystemError> { 222 // 获取内存信息 223 let usage = unsafe { LockedFrameAllocator.usage() }; 224 225 // 传入数据 226 let data: &mut Vec<u8> = &mut pdata.data; 227 228 data.append( 229 &mut format!("MemTotal:\t{} kB\n", usage.total().bytes() >> 10) 230 .as_bytes() 231 .to_owned(), 232 ); 233 234 data.append( 235 &mut format!("MemFree:\t{} kB\n", usage.free().bytes() >> 10) 236 .as_bytes() 237 .to_owned(), 238 ); 239 240 // 去除多余的\0 241 self.trim_string(data); 242 243 return Ok((data.len() * size_of::<u8>()) as i64); 244 } 245 246 /// proc文件系统读取函数 247 fn proc_read( 248 &self, 249 offset: usize, 250 len: usize, 251 buf: &mut [u8], 252 _pdata: &mut ProcfsFilePrivateData, 253 ) -> Result<usize, SystemError> { 254 let start = _pdata.data.len().min(offset); 255 let end = _pdata.data.len().min(offset + len); 256 257 // buffer空间不足 258 if buf.len() < (end - start) { 259 return Err(SystemError::ENOBUFS); 260 } 261 262 // 拷贝数据 263 let src = &_pdata.data[start..end]; 264 buf[0..src.len()].copy_from_slice(src); 265 return Ok(src.len()); 266 } 267 } 268 269 impl FileSystem for ProcFS { 270 fn root_inode(&self) -> Arc<dyn super::vfs::IndexNode> { 271 return self.root_inode.clone(); 272 } 273 274 fn info(&self) -> FsInfo { 275 return FsInfo { 276 blk_dev_id: 0, 277 max_name_len: PROCFS_MAX_NAMELEN, 278 }; 279 } 280 281 fn as_any_ref(&self) -> &dyn core::any::Any { 282 self 283 } 284 fn name(&self) -> &str { 285 "procfs" 286 } 287 } 288 289 impl ProcFS { 290 pub fn new() -> Arc<Self> { 291 // 初始化root inode 292 let root: Arc<LockedProcFSInode> = 293 Arc::new(LockedProcFSInode(SpinLock::new(ProcFSInode { 294 parent: Weak::default(), 295 self_ref: Weak::default(), 296 children: BTreeMap::new(), 297 data: Vec::new(), 298 metadata: Metadata { 299 dev_id: 0, 300 inode_id: generate_inode_id(), 301 size: 0, 302 blk_size: 0, 303 blocks: 0, 304 atime: TimeSpec::default(), 305 mtime: TimeSpec::default(), 306 ctime: TimeSpec::default(), 307 file_type: FileType::Dir, 308 mode: ModeType::from_bits_truncate(0o555), 309 nlinks: 1, 310 uid: 0, 311 gid: 0, 312 raw_dev: DeviceNumber::default(), 313 }, 314 fs: Weak::default(), 315 fdata: InodeInfo { 316 pid: Pid::new(0), 317 ftype: ProcFileType::Default, 318 }, 319 }))); 320 321 let result: Arc<ProcFS> = Arc::new(ProcFS { root_inode: root }); 322 323 // 对root inode加锁,并继续完成初始化工作 324 let mut root_guard: SpinLockGuard<ProcFSInode> = result.root_inode.0.lock(); 325 root_guard.parent = Arc::downgrade(&result.root_inode); 326 root_guard.self_ref = Arc::downgrade(&result.root_inode); 327 root_guard.fs = Arc::downgrade(&result); 328 // 释放锁 329 drop(root_guard); 330 331 // 创建meminfo文件 332 let inode = result.root_inode(); 333 let binding = inode.create( 334 "meminfo", 335 FileType::File, 336 ModeType::from_bits_truncate(0o444), 337 ); 338 if let Ok(meminfo) = binding { 339 let meminfo_file = meminfo 340 .as_any_ref() 341 .downcast_ref::<LockedProcFSInode>() 342 .unwrap(); 343 meminfo_file.0.lock().fdata.pid = Pid::new(0); 344 meminfo_file.0.lock().fdata.ftype = ProcFileType::ProcMeminfo; 345 } else { 346 panic!("create meminfo error"); 347 } 348 349 // 创建kmsg文件 350 let binding = inode.create("kmsg", FileType::File, ModeType::from_bits_truncate(0o444)); 351 if let Ok(kmsg) = binding { 352 let kmsg_file = kmsg 353 .as_any_ref() 354 .downcast_ref::<LockedProcFSInode>() 355 .unwrap(); 356 kmsg_file.0.lock().fdata.pid = Pid::new(1); 357 kmsg_file.0.lock().fdata.ftype = ProcFileType::ProcKmsg; 358 } else { 359 panic!("create ksmg error"); 360 } 361 362 return result; 363 } 364 365 /// @brief 进程注册函数 366 /// @usage 在进程中调用并创建进程对应文件 367 pub fn register_pid(&self, pid: Pid) -> Result<(), SystemError> { 368 // 获取当前inode 369 let inode: Arc<dyn IndexNode> = self.root_inode(); 370 // 创建对应进程文件夹 371 let pid_dir: Arc<dyn IndexNode> = inode.create( 372 &pid.to_string(), 373 FileType::Dir, 374 ModeType::from_bits_truncate(0o555), 375 )?; 376 // 创建相关文件 377 // status文件 378 let binding: Arc<dyn IndexNode> = pid_dir.create( 379 "status", 380 FileType::File, 381 ModeType::from_bits_truncate(0o444), 382 )?; 383 let status_file: &LockedProcFSInode = binding 384 .as_any_ref() 385 .downcast_ref::<LockedProcFSInode>() 386 .unwrap(); 387 status_file.0.lock().fdata.pid = pid; 388 status_file.0.lock().fdata.ftype = ProcFileType::ProcStatus; 389 390 //todo: 创建其他文件 391 392 return Ok(()); 393 } 394 395 /// @brief 解除进程注册 396 /// 397 pub fn unregister_pid(&self, pid: Pid) -> Result<(), SystemError> { 398 // 获取当前inode 399 let proc: Arc<dyn IndexNode> = self.root_inode(); 400 // 获取进程文件夹 401 let pid_dir: Arc<dyn IndexNode> = proc.find(&pid.to_string())?; 402 // 删除进程文件夹下文件 403 pid_dir.unlink("status")?; 404 405 // 查看进程文件是否还存在 406 // let pf= pid_dir.find("status").expect("Cannot find status"); 407 408 // 删除进程文件夹 409 proc.unlink(&pid.to_string())?; 410 411 return Ok(()); 412 } 413 } 414 415 impl IndexNode for LockedProcFSInode { 416 fn open(&self, data: &mut FilePrivateData, _mode: &FileMode) -> Result<(), SystemError> { 417 // 加锁 418 let mut inode: SpinLockGuard<ProcFSInode> = self.0.lock(); 419 420 // 如果inode类型为文件夹,则直接返回成功 421 if let FileType::Dir = inode.metadata.file_type { 422 return Ok(()); 423 } 424 let mut private_data = ProcfsFilePrivateData::new(); 425 // 根据文件类型获取相应数据 426 let file_size = match inode.fdata.ftype { 427 ProcFileType::ProcStatus => inode.open_status(&mut private_data)?, 428 ProcFileType::ProcMeminfo => inode.open_meminfo(&mut private_data)?, 429 _ => { 430 todo!() 431 } 432 }; 433 *data = FilePrivateData::Procfs(private_data); 434 // 更新metadata里面的文件大小数值 435 inode.metadata.size = file_size; 436 437 return Ok(()); 438 } 439 440 fn close(&self, data: &mut FilePrivateData) -> Result<(), SystemError> { 441 let guard: SpinLockGuard<ProcFSInode> = self.0.lock(); 442 // 如果inode类型为文件夹,则直接返回成功 443 if let FileType::Dir = guard.metadata.file_type { 444 return Ok(()); 445 } 446 // 释放data 447 *data = FilePrivateData::Procfs(ProcfsFilePrivateData::new()); 448 449 return Ok(()); 450 } 451 452 fn read_at( 453 &self, 454 offset: usize, 455 len: usize, 456 buf: &mut [u8], 457 data: &mut FilePrivateData, 458 ) -> Result<usize, SystemError> { 459 if buf.len() < len { 460 return Err(SystemError::EINVAL); 461 } 462 // 加锁 463 let inode: SpinLockGuard<ProcFSInode> = self.0.lock(); 464 465 // 检查当前inode是否为一个文件夹,如果是的话,就返回错误 466 if inode.metadata.file_type == FileType::Dir { 467 return Err(SystemError::EISDIR); 468 } 469 470 // 获取数据信息 471 let private_data = match data { 472 FilePrivateData::Procfs(p) => p, 473 _ => { 474 panic!("ProcFS: FilePrivateData mismatch!"); 475 } 476 }; 477 478 // 根据文件类型读取相应数据 479 match inode.fdata.ftype { 480 ProcFileType::ProcStatus => return inode.proc_read(offset, len, buf, private_data), 481 ProcFileType::ProcMeminfo => return inode.proc_read(offset, len, buf, private_data), 482 ProcFileType::ProcKmsg => (), 483 ProcFileType::Default => (), 484 }; 485 486 // 默认读取 487 let start = inode.data.len().min(offset); 488 let end = inode.data.len().min(offset + len); 489 490 // buffer空间不足 491 if buf.len() < (end - start) { 492 return Err(SystemError::ENOBUFS); 493 } 494 495 // 拷贝数据 496 let src = &inode.data[start..end]; 497 buf[0..src.len()].copy_from_slice(src); 498 return Ok(src.len()); 499 } 500 501 fn write_at( 502 &self, 503 _offset: usize, 504 _len: usize, 505 _buf: &[u8], 506 _data: &mut FilePrivateData, 507 ) -> Result<usize, SystemError> { 508 return Err(SystemError::EOPNOTSUPP_OR_ENOTSUP); 509 } 510 511 fn fs(&self) -> Arc<dyn FileSystem> { 512 return self.0.lock().fs.upgrade().unwrap(); 513 } 514 515 fn as_any_ref(&self) -> &dyn core::any::Any { 516 self 517 } 518 519 fn metadata(&self) -> Result<Metadata, SystemError> { 520 let inode = self.0.lock(); 521 let metadata = inode.metadata.clone(); 522 523 return Ok(metadata); 524 } 525 526 fn set_metadata(&self, metadata: &Metadata) -> Result<(), SystemError> { 527 let mut inode = self.0.lock(); 528 inode.metadata.atime = metadata.atime; 529 inode.metadata.mtime = metadata.mtime; 530 inode.metadata.ctime = metadata.ctime; 531 inode.metadata.mode = metadata.mode; 532 inode.metadata.uid = metadata.uid; 533 inode.metadata.gid = metadata.gid; 534 535 return Ok(()); 536 } 537 538 fn resize(&self, len: usize) -> Result<(), SystemError> { 539 let mut inode = self.0.lock(); 540 if inode.metadata.file_type == FileType::File { 541 inode.data.resize(len, 0); 542 return Ok(()); 543 } else { 544 return Err(SystemError::EINVAL); 545 } 546 } 547 548 fn create_with_data( 549 &self, 550 name: &str, 551 file_type: FileType, 552 mode: ModeType, 553 data: usize, 554 ) -> Result<Arc<dyn IndexNode>, SystemError> { 555 // 获取当前inode 556 let mut inode = self.0.lock(); 557 // 如果当前inode不是文件夹,则返回 558 if inode.metadata.file_type != FileType::Dir { 559 return Err(SystemError::ENOTDIR); 560 } 561 // 如果有重名的,则返回 562 if inode.children.contains_key(name) { 563 return Err(SystemError::EEXIST); 564 } 565 566 // 创建inode 567 let result: Arc<LockedProcFSInode> = 568 Arc::new(LockedProcFSInode(SpinLock::new(ProcFSInode { 569 parent: inode.self_ref.clone(), 570 self_ref: Weak::default(), 571 children: BTreeMap::new(), 572 data: Vec::new(), 573 metadata: Metadata { 574 dev_id: 0, 575 inode_id: generate_inode_id(), 576 size: 0, 577 blk_size: 0, 578 blocks: 0, 579 atime: TimeSpec::default(), 580 mtime: TimeSpec::default(), 581 ctime: TimeSpec::default(), 582 file_type: file_type, 583 mode: mode, 584 nlinks: 1, 585 uid: 0, 586 gid: 0, 587 raw_dev: DeviceNumber::from(data as u32), 588 }, 589 fs: inode.fs.clone(), 590 fdata: InodeInfo { 591 pid: Pid::new(0), 592 ftype: ProcFileType::Default, 593 }, 594 }))); 595 596 // 初始化inode的自引用的weak指针 597 result.0.lock().self_ref = Arc::downgrade(&result); 598 599 // 将子inode插入父inode的B树中 600 inode.children.insert(String::from(name), result.clone()); 601 602 return Ok(result); 603 } 604 605 fn link(&self, name: &str, other: &Arc<dyn IndexNode>) -> Result<(), SystemError> { 606 let other: &LockedProcFSInode = other 607 .downcast_ref::<LockedProcFSInode>() 608 .ok_or(SystemError::EPERM)?; 609 let mut inode: SpinLockGuard<ProcFSInode> = self.0.lock(); 610 let mut other_locked: SpinLockGuard<ProcFSInode> = other.0.lock(); 611 612 // 如果当前inode不是文件夹,那么报错 613 if inode.metadata.file_type != FileType::Dir { 614 return Err(SystemError::ENOTDIR); 615 } 616 617 // 如果另一个inode是文件夹,那么也报错 618 if other_locked.metadata.file_type == FileType::Dir { 619 return Err(SystemError::EISDIR); 620 } 621 622 // 如果当前文件夹下已经有同名文件,也报错。 623 if inode.children.contains_key(name) { 624 return Err(SystemError::EEXIST); 625 } 626 627 inode 628 .children 629 .insert(String::from(name), other_locked.self_ref.upgrade().unwrap()); 630 631 // 增加硬链接计数 632 other_locked.metadata.nlinks += 1; 633 return Ok(()); 634 } 635 636 fn unlink(&self, name: &str) -> Result<(), SystemError> { 637 let mut inode: SpinLockGuard<ProcFSInode> = self.0.lock(); 638 // 如果当前inode不是目录,那么也没有子目录/文件的概念了,因此要求当前inode的类型是目录 639 if inode.metadata.file_type != FileType::Dir { 640 return Err(SystemError::ENOTDIR); 641 } 642 643 // 不允许删除当前文件夹,也不允许删除上一个目录 644 if name == "." || name == ".." { 645 return Err(SystemError::ENOTEMPTY); 646 } 647 648 // 获得要删除的文件的inode 649 let to_delete = inode.children.get(name).ok_or(SystemError::ENOENT)?; 650 651 // 减少硬链接计数 652 to_delete.0.lock().metadata.nlinks -= 1; 653 654 // 在当前目录中删除这个子目录项 655 inode.children.remove(name); 656 657 return Ok(()); 658 } 659 660 fn move_to( 661 &self, 662 _old_name: &str, 663 _target: &Arc<dyn IndexNode>, 664 _new_name: &str, 665 ) -> Result<(), SystemError> { 666 return Err(SystemError::EOPNOTSUPP_OR_ENOTSUP); 667 } 668 669 fn find(&self, name: &str) -> Result<Arc<dyn IndexNode>, SystemError> { 670 let inode = self.0.lock(); 671 672 if inode.metadata.file_type != FileType::Dir { 673 return Err(SystemError::ENOTDIR); 674 } 675 676 match name { 677 "" | "." => { 678 return Ok(inode.self_ref.upgrade().ok_or(SystemError::ENOENT)?); 679 } 680 681 ".." => { 682 return Ok(inode.parent.upgrade().ok_or(SystemError::ENOENT)?); 683 } 684 name => { 685 // 在子目录项中查找 686 return Ok(inode.children.get(name).ok_or(SystemError::ENOENT)?.clone()); 687 } 688 } 689 } 690 691 fn get_entry_name(&self, ino: InodeId) -> Result<String, SystemError> { 692 let inode: SpinLockGuard<ProcFSInode> = self.0.lock(); 693 if inode.metadata.file_type != FileType::Dir { 694 return Err(SystemError::ENOTDIR); 695 } 696 697 match ino.into() { 698 0 => { 699 return Ok(String::from(".")); 700 } 701 1 => { 702 return Ok(String::from("..")); 703 } 704 ino => { 705 // 暴力遍历所有的children,判断inode id是否相同 706 // TODO: 优化这里,这个地方性能很差! 707 let mut key: Vec<String> = inode 708 .children 709 .keys() 710 .filter(|k| { 711 inode 712 .children 713 .get(*k) 714 .unwrap() 715 .0 716 .lock() 717 .metadata 718 .inode_id 719 .into() 720 == ino 721 }) 722 .cloned() 723 .collect(); 724 725 match key.len() { 726 0=>{return Err(SystemError::ENOENT);} 727 1=>{return Ok(key.remove(0));} 728 _ => panic!("Procfs 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) 729 } 730 } 731 } 732 } 733 734 fn list(&self) -> Result<Vec<String>, SystemError> { 735 let info = self.metadata()?; 736 if info.file_type != FileType::Dir { 737 return Err(SystemError::ENOTDIR); 738 } 739 740 let mut keys: Vec<String> = Vec::new(); 741 keys.push(String::from(".")); 742 keys.push(String::from("..")); 743 keys.append(&mut self.0.lock().children.keys().cloned().collect()); 744 745 return Ok(keys); 746 } 747 } 748 749 /// @brief 向procfs注册进程 750 pub fn procfs_register_pid(pid: Pid) -> Result<(), SystemError> { 751 let procfs_inode = ROOT_INODE().find("proc")?; 752 753 let procfs_inode = procfs_inode 754 .downcast_ref::<LockedProcFSInode>() 755 .expect("Failed to find procfs' root inode"); 756 let fs = procfs_inode.fs(); 757 let procfs: &ProcFS = fs.as_any_ref().downcast_ref::<ProcFS>().unwrap(); 758 759 // 调用注册函数 760 procfs.register_pid(pid)?; 761 762 return Ok(()); 763 } 764 765 /// @brief 在ProcFS中,解除进程的注册 766 pub fn procfs_unregister_pid(pid: Pid) -> Result<(), SystemError> { 767 // 获取procfs实例 768 let procfs_inode: Arc<dyn IndexNode> = ROOT_INODE().find("proc")?; 769 770 let procfs_inode: &LockedProcFSInode = procfs_inode 771 .downcast_ref::<LockedProcFSInode>() 772 .expect("Failed to find procfs' root inode"); 773 let fs: Arc<dyn FileSystem> = procfs_inode.fs(); 774 let procfs: &ProcFS = fs.as_any_ref().downcast_ref::<ProcFS>().unwrap(); 775 776 // 调用解除注册函数 777 return procfs.unregister_pid(pid); 778 } 779 780 pub fn procfs_init() -> Result<(), SystemError> { 781 static INIT: Once = Once::new(); 782 let mut result = None; 783 INIT.call_once(|| { 784 kinfo!("Initializing ProcFS..."); 785 // 创建 procfs 实例 786 let procfs: Arc<ProcFS> = ProcFS::new(); 787 788 // procfs 挂载 789 let _t = ROOT_INODE() 790 .find("proc") 791 .expect("Cannot find /proc") 792 .mount(procfs) 793 .expect("Failed to mount proc"); 794 kinfo!("ProcFS mounted."); 795 result = Some(Ok(())); 796 }); 797 798 return result.unwrap(); 799 } 800