1dfe53cf0SGnoCiYeH use core::sync::atomic::{AtomicU32, Ordering}; 2dfe53cf0SGnoCiYeH 3dfe53cf0SGnoCiYeH use alloc::{ 4dfe53cf0SGnoCiYeH collections::BTreeMap, 5dfe53cf0SGnoCiYeH string::{String, ToString}, 6dfe53cf0SGnoCiYeH sync::{Arc, Weak}, 7dfe53cf0SGnoCiYeH vec::Vec, 8dfe53cf0SGnoCiYeH }; 9dfe53cf0SGnoCiYeH use ida::IdAllocator; 10dfe53cf0SGnoCiYeH use system_error::SystemError; 11dfe53cf0SGnoCiYeH use unified_init::macros::unified_init; 12dfe53cf0SGnoCiYeH 13dfe53cf0SGnoCiYeH use crate::{ 14dfe53cf0SGnoCiYeH driver::{ 15dfe53cf0SGnoCiYeH base::device::{ 16dfe53cf0SGnoCiYeH device_number::{DeviceNumber, Major}, 17dfe53cf0SGnoCiYeH IdTable, 18dfe53cf0SGnoCiYeH }, 19dfe53cf0SGnoCiYeH tty::{ 20dfe53cf0SGnoCiYeH pty::unix98pty::NR_UNIX98_PTY_MAX, 21dfe53cf0SGnoCiYeH tty_device::{PtyType, TtyDevice, TtyType}, 22dfe53cf0SGnoCiYeH }, 23dfe53cf0SGnoCiYeH }, 24dfe53cf0SGnoCiYeH filesystem::vfs::{syscall::ModeType, FileType, ROOT_INODE}, 25dfe53cf0SGnoCiYeH init::initcall::INITCALL_FS, 26dfe53cf0SGnoCiYeH libs::spinlock::{SpinLock, SpinLockGuard}, 27*6fc066acSJomo time::PosixTimeSpec, 28dfe53cf0SGnoCiYeH }; 29dfe53cf0SGnoCiYeH 30dfe53cf0SGnoCiYeH use super::vfs::{ 31dfe53cf0SGnoCiYeH core::generate_inode_id, FilePrivateData, FileSystem, FsInfo, IndexNode, Metadata, 32dfe53cf0SGnoCiYeH }; 33dfe53cf0SGnoCiYeH 34dfe53cf0SGnoCiYeH const DEV_PTYFS_MAX_NAMELEN: usize = 16; 35dfe53cf0SGnoCiYeH 36dfe53cf0SGnoCiYeH #[allow(dead_code)] 37dfe53cf0SGnoCiYeH const PTY_NR_LIMIT: usize = 4096; 38dfe53cf0SGnoCiYeH 39dfe53cf0SGnoCiYeH #[derive(Debug)] 40dfe53cf0SGnoCiYeH pub struct DevPtsFs { 41dfe53cf0SGnoCiYeH /// 根节点 42dfe53cf0SGnoCiYeH root_inode: Arc<LockedDevPtsFSInode>, 43dfe53cf0SGnoCiYeH pts_ida: IdAllocator, 44dfe53cf0SGnoCiYeH pts_count: AtomicU32, 45dfe53cf0SGnoCiYeH } 46dfe53cf0SGnoCiYeH 47dfe53cf0SGnoCiYeH impl DevPtsFs { 48dfe53cf0SGnoCiYeH pub fn new() -> Arc<Self> { 49dfe53cf0SGnoCiYeH let root_inode = Arc::new(LockedDevPtsFSInode::new()); 50dfe53cf0SGnoCiYeH let ret = Arc::new(Self { 51dfe53cf0SGnoCiYeH root_inode, 52dfe53cf0SGnoCiYeH pts_ida: IdAllocator::new(1, NR_UNIX98_PTY_MAX as usize), 53dfe53cf0SGnoCiYeH pts_count: AtomicU32::new(0), 54dfe53cf0SGnoCiYeH }); 55dfe53cf0SGnoCiYeH 56dfe53cf0SGnoCiYeH ret.root_inode.set_fs(Arc::downgrade(&ret)); 57dfe53cf0SGnoCiYeH 58dfe53cf0SGnoCiYeH ret 59dfe53cf0SGnoCiYeH } 60dfe53cf0SGnoCiYeH 61dfe53cf0SGnoCiYeH pub fn alloc_index(&self) -> Result<usize, SystemError> { 62dfe53cf0SGnoCiYeH self.pts_ida.alloc().ok_or(SystemError::ENOSPC) 63dfe53cf0SGnoCiYeH } 64dfe53cf0SGnoCiYeH } 65dfe53cf0SGnoCiYeH 66dfe53cf0SGnoCiYeH impl FileSystem for DevPtsFs { 67dfe53cf0SGnoCiYeH fn root_inode(&self) -> Arc<dyn IndexNode> { 68dfe53cf0SGnoCiYeH self.root_inode.clone() 69dfe53cf0SGnoCiYeH } 70dfe53cf0SGnoCiYeH 71dfe53cf0SGnoCiYeH fn info(&self) -> super::vfs::FsInfo { 72dfe53cf0SGnoCiYeH return FsInfo { 73dfe53cf0SGnoCiYeH blk_dev_id: 0, 74dfe53cf0SGnoCiYeH max_name_len: DEV_PTYFS_MAX_NAMELEN, 75dfe53cf0SGnoCiYeH }; 76dfe53cf0SGnoCiYeH } 77dfe53cf0SGnoCiYeH 78dfe53cf0SGnoCiYeH fn as_any_ref(&self) -> &dyn core::any::Any { 79dfe53cf0SGnoCiYeH self 80dfe53cf0SGnoCiYeH } 81dfe53cf0SGnoCiYeH 82dfe53cf0SGnoCiYeH fn name(&self) -> &str { 83dfe53cf0SGnoCiYeH "devpts" 84dfe53cf0SGnoCiYeH } 85dfe53cf0SGnoCiYeH 86dfe53cf0SGnoCiYeH fn super_block(&self) -> super::vfs::SuperBlock { 87dfe53cf0SGnoCiYeH todo!() 88dfe53cf0SGnoCiYeH } 89dfe53cf0SGnoCiYeH } 90dfe53cf0SGnoCiYeH 91dfe53cf0SGnoCiYeH #[derive(Debug)] 92dfe53cf0SGnoCiYeH pub struct LockedDevPtsFSInode { 93dfe53cf0SGnoCiYeH inner: SpinLock<PtsDevInode>, 94dfe53cf0SGnoCiYeH } 95dfe53cf0SGnoCiYeH 96dfe53cf0SGnoCiYeH impl LockedDevPtsFSInode { 97dfe53cf0SGnoCiYeH pub fn new() -> Self { 98dfe53cf0SGnoCiYeH Self { 99dfe53cf0SGnoCiYeH inner: SpinLock::new(PtsDevInode { 100dfe53cf0SGnoCiYeH fs: Weak::new(), 101dfe53cf0SGnoCiYeH children: Some(BTreeMap::new()), 102dfe53cf0SGnoCiYeH metadata: Metadata { 103dfe53cf0SGnoCiYeH dev_id: 0, 104dfe53cf0SGnoCiYeH inode_id: generate_inode_id(), 105dfe53cf0SGnoCiYeH size: 0, 106dfe53cf0SGnoCiYeH blk_size: 0, 107dfe53cf0SGnoCiYeH blocks: 0, 108*6fc066acSJomo atime: PosixTimeSpec::default(), 109*6fc066acSJomo mtime: PosixTimeSpec::default(), 110*6fc066acSJomo ctime: PosixTimeSpec::default(), 111dfe53cf0SGnoCiYeH file_type: FileType::Dir, 112*6fc066acSJomo mode: ModeType::from_bits_truncate(0o777), 113dfe53cf0SGnoCiYeH nlinks: 1, 114dfe53cf0SGnoCiYeH uid: 0, 115dfe53cf0SGnoCiYeH gid: 0, 116dfe53cf0SGnoCiYeH raw_dev: DeviceNumber::default(), 117dfe53cf0SGnoCiYeH }, 118dfe53cf0SGnoCiYeH }), 119dfe53cf0SGnoCiYeH } 120dfe53cf0SGnoCiYeH } 121dfe53cf0SGnoCiYeH 122dfe53cf0SGnoCiYeH pub fn set_fs(&self, fs: Weak<DevPtsFs>) { 123dfe53cf0SGnoCiYeH self.inner.lock().fs = fs; 124dfe53cf0SGnoCiYeH } 125dfe53cf0SGnoCiYeH } 126dfe53cf0SGnoCiYeH 127dfe53cf0SGnoCiYeH #[derive(Debug)] 128dfe53cf0SGnoCiYeH pub struct PtsDevInode { 129dfe53cf0SGnoCiYeH fs: Weak<DevPtsFs>, 130dfe53cf0SGnoCiYeH children: Option<BTreeMap<String, Arc<TtyDevice>>>, 131dfe53cf0SGnoCiYeH metadata: Metadata, 132dfe53cf0SGnoCiYeH } 133dfe53cf0SGnoCiYeH 134dfe53cf0SGnoCiYeH impl PtsDevInode { 135dfe53cf0SGnoCiYeH pub fn children_unchecked(&self) -> &BTreeMap<String, Arc<TtyDevice>> { 136dfe53cf0SGnoCiYeH self.children.as_ref().unwrap() 137dfe53cf0SGnoCiYeH } 138dfe53cf0SGnoCiYeH 139dfe53cf0SGnoCiYeH pub fn children_unchecked_mut(&mut self) -> &mut BTreeMap<String, Arc<TtyDevice>> { 140dfe53cf0SGnoCiYeH self.children.as_mut().unwrap() 141dfe53cf0SGnoCiYeH } 142dfe53cf0SGnoCiYeH } 143dfe53cf0SGnoCiYeH 144dfe53cf0SGnoCiYeH impl IndexNode for LockedDevPtsFSInode { 145dfe53cf0SGnoCiYeH fn open( 146dfe53cf0SGnoCiYeH &self, 147dfe53cf0SGnoCiYeH _data: SpinLockGuard<FilePrivateData>, 148dfe53cf0SGnoCiYeH _mode: &super::vfs::file::FileMode, 149dfe53cf0SGnoCiYeH ) -> Result<(), SystemError> { 150dfe53cf0SGnoCiYeH Ok(()) 151dfe53cf0SGnoCiYeH } 152dfe53cf0SGnoCiYeH 153dfe53cf0SGnoCiYeH fn metadata(&self) -> Result<super::vfs::Metadata, SystemError> { 154dfe53cf0SGnoCiYeH let inode = self.inner.lock(); 155dfe53cf0SGnoCiYeH let metadata = inode.metadata.clone(); 156dfe53cf0SGnoCiYeH 157dfe53cf0SGnoCiYeH return Ok(metadata); 158dfe53cf0SGnoCiYeH } 159dfe53cf0SGnoCiYeH 160dfe53cf0SGnoCiYeH fn close(&self, _data: SpinLockGuard<FilePrivateData>) -> Result<(), SystemError> { 161dfe53cf0SGnoCiYeH // TODO: 回收 162dfe53cf0SGnoCiYeH Ok(()) 163dfe53cf0SGnoCiYeH } 164dfe53cf0SGnoCiYeH 165dfe53cf0SGnoCiYeH fn read_at( 166dfe53cf0SGnoCiYeH &self, 167dfe53cf0SGnoCiYeH _offset: usize, 168dfe53cf0SGnoCiYeH _len: usize, 169dfe53cf0SGnoCiYeH _buf: &mut [u8], 170dfe53cf0SGnoCiYeH _data: SpinLockGuard<FilePrivateData>, 171dfe53cf0SGnoCiYeH ) -> Result<usize, system_error::SystemError> { 172dfe53cf0SGnoCiYeH todo!() 173dfe53cf0SGnoCiYeH } 174dfe53cf0SGnoCiYeH 175dfe53cf0SGnoCiYeH fn write_at( 176dfe53cf0SGnoCiYeH &self, 177dfe53cf0SGnoCiYeH _offset: usize, 178dfe53cf0SGnoCiYeH _len: usize, 179dfe53cf0SGnoCiYeH _buf: &[u8], 180dfe53cf0SGnoCiYeH _data: SpinLockGuard<FilePrivateData>, 181dfe53cf0SGnoCiYeH ) -> Result<usize, system_error::SystemError> { 182dfe53cf0SGnoCiYeH todo!() 183dfe53cf0SGnoCiYeH } 184dfe53cf0SGnoCiYeH 185dfe53cf0SGnoCiYeH fn fs(&self) -> alloc::sync::Arc<dyn super::vfs::FileSystem> { 186dfe53cf0SGnoCiYeH self.inner.lock().fs.upgrade().unwrap() 187dfe53cf0SGnoCiYeH } 188dfe53cf0SGnoCiYeH 189dfe53cf0SGnoCiYeH fn as_any_ref(&self) -> &dyn core::any::Any { 190dfe53cf0SGnoCiYeH todo!() 191dfe53cf0SGnoCiYeH } 192dfe53cf0SGnoCiYeH 193dfe53cf0SGnoCiYeH fn list(&self) -> Result<alloc::vec::Vec<alloc::string::String>, system_error::SystemError> { 194dfe53cf0SGnoCiYeH let info = self.metadata()?; 195dfe53cf0SGnoCiYeH if info.file_type != FileType::Dir { 196dfe53cf0SGnoCiYeH return Err(SystemError::ENOTDIR); 197dfe53cf0SGnoCiYeH } 198dfe53cf0SGnoCiYeH 199dfe53cf0SGnoCiYeH let mut keys: Vec<String> = Vec::new(); 200dfe53cf0SGnoCiYeH keys.push(String::from(".")); 201dfe53cf0SGnoCiYeH keys.push(String::from("..")); 202dfe53cf0SGnoCiYeH keys.append( 203dfe53cf0SGnoCiYeH &mut self 204dfe53cf0SGnoCiYeH .inner 205dfe53cf0SGnoCiYeH .lock() 206dfe53cf0SGnoCiYeH .children_unchecked() 207dfe53cf0SGnoCiYeH .keys() 208dfe53cf0SGnoCiYeH .cloned() 209dfe53cf0SGnoCiYeH .collect(), 210dfe53cf0SGnoCiYeH ); 211dfe53cf0SGnoCiYeH 212dfe53cf0SGnoCiYeH return Ok(keys); 213dfe53cf0SGnoCiYeH } 214dfe53cf0SGnoCiYeH 215dfe53cf0SGnoCiYeH fn create_with_data( 216dfe53cf0SGnoCiYeH &self, 217dfe53cf0SGnoCiYeH name: &str, 218dfe53cf0SGnoCiYeH file_type: FileType, 219dfe53cf0SGnoCiYeH _mode: super::vfs::syscall::ModeType, 220dfe53cf0SGnoCiYeH _data: usize, 221dfe53cf0SGnoCiYeH ) -> Result<Arc<dyn IndexNode>, SystemError> { 222dfe53cf0SGnoCiYeH if file_type != FileType::CharDevice { 223dfe53cf0SGnoCiYeH return Err(SystemError::ENOSYS); 224dfe53cf0SGnoCiYeH } 225dfe53cf0SGnoCiYeH 226dfe53cf0SGnoCiYeH let mut guard = self.inner.lock(); 227dfe53cf0SGnoCiYeH 228dfe53cf0SGnoCiYeH if guard.children_unchecked_mut().contains_key(name) { 229dfe53cf0SGnoCiYeH return Err(SystemError::EEXIST); 230dfe53cf0SGnoCiYeH } 231dfe53cf0SGnoCiYeH 232dfe53cf0SGnoCiYeH let fs = guard.fs.upgrade().unwrap(); 233dfe53cf0SGnoCiYeH 234dfe53cf0SGnoCiYeH let result = TtyDevice::new( 235dfe53cf0SGnoCiYeH name.to_string(), 236dfe53cf0SGnoCiYeH IdTable::new(name.to_string(), None), 237dfe53cf0SGnoCiYeH TtyType::Pty(PtyType::Pts), 238dfe53cf0SGnoCiYeH ); 239dfe53cf0SGnoCiYeH 240dfe53cf0SGnoCiYeH let mut metadata = result.metadata()?; 241dfe53cf0SGnoCiYeH 242dfe53cf0SGnoCiYeH metadata.mode.insert(ModeType::S_IFCHR); 243dfe53cf0SGnoCiYeH metadata.raw_dev = 244dfe53cf0SGnoCiYeH DeviceNumber::new(Major::UNIX98_PTY_SLAVE_MAJOR, name.parse::<u32>().unwrap()); 245dfe53cf0SGnoCiYeH 246dfe53cf0SGnoCiYeH result.set_metadata(&metadata)?; 247dfe53cf0SGnoCiYeH 248dfe53cf0SGnoCiYeH guard 249dfe53cf0SGnoCiYeH .children_unchecked_mut() 250dfe53cf0SGnoCiYeH .insert(name.to_string(), result.clone()); 251dfe53cf0SGnoCiYeH 252dfe53cf0SGnoCiYeH fs.pts_count.fetch_add(1, Ordering::SeqCst); 253dfe53cf0SGnoCiYeH 254dfe53cf0SGnoCiYeH Ok(result) 255dfe53cf0SGnoCiYeH } 256dfe53cf0SGnoCiYeH 257dfe53cf0SGnoCiYeH fn find(&self, name: &str) -> Result<Arc<dyn IndexNode>, SystemError> { 258dfe53cf0SGnoCiYeH let guard = self.inner.lock(); 259dfe53cf0SGnoCiYeH 260dfe53cf0SGnoCiYeH if let Some(dev) = guard.children_unchecked().get(name) { 261dfe53cf0SGnoCiYeH Ok(dev.clone() as Arc<dyn IndexNode>) 262dfe53cf0SGnoCiYeH } else { 263dfe53cf0SGnoCiYeH Err(SystemError::ENOENT) 264dfe53cf0SGnoCiYeH } 265dfe53cf0SGnoCiYeH } 266dfe53cf0SGnoCiYeH 267dfe53cf0SGnoCiYeH fn unlink(&self, name: &str) -> Result<(), SystemError> { 268dfe53cf0SGnoCiYeH let mut guard = self.inner.lock(); 269dfe53cf0SGnoCiYeH guard.children_unchecked_mut().remove(name); 270dfe53cf0SGnoCiYeH Ok(()) 271dfe53cf0SGnoCiYeH } 272dfe53cf0SGnoCiYeH } 273dfe53cf0SGnoCiYeH 274dfe53cf0SGnoCiYeH #[unified_init(INITCALL_FS)] 275dfe53cf0SGnoCiYeH #[inline(never)] 276dfe53cf0SGnoCiYeH pub fn devpts_init() -> Result<(), SystemError> { 277dfe53cf0SGnoCiYeH let dev_inode = ROOT_INODE().find("dev")?; 278dfe53cf0SGnoCiYeH 279dfe53cf0SGnoCiYeH let pts_inode = dev_inode.create("pts", FileType::Dir, ModeType::from_bits_truncate(0o755))?; 280dfe53cf0SGnoCiYeH 281dfe53cf0SGnoCiYeH // 创建 devptsfs 实例 282dfe53cf0SGnoCiYeH let ptsfs: Arc<DevPtsFs> = DevPtsFs::new(); 283dfe53cf0SGnoCiYeH 284dfe53cf0SGnoCiYeH // let mountfs = dev_inode.mount(ptsfs).expect("Failed to mount DevPtsFS"); 285dfe53cf0SGnoCiYeH 286dfe53cf0SGnoCiYeH pts_inode.mount(ptsfs).expect("Failed to mount DevPtsFS"); 287dfe53cf0SGnoCiYeH kinfo!("DevPtsFs mounted."); 288dfe53cf0SGnoCiYeH 289dfe53cf0SGnoCiYeH Ok(()) 290dfe53cf0SGnoCiYeH } 291