120e3152eSlogin use alloc::{
220e3152eSlogin string::{String, ToString},
320e3152eSlogin sync::{Arc, Weak},
420e3152eSlogin };
591e9d4abSLoGin use system_error::SystemError;
6c566df45SLoGin use unified_init::macros::unified_init;
70d48c3c9Slogin
80d48c3c9Slogin use crate::{
952da9a59SGnoCiYeH arch::ipc::signal::Signal,
1052da9a59SGnoCiYeH driver::{
1152da9a59SGnoCiYeH base::{
1252da9a59SGnoCiYeH char::CharDevice,
130cb80734SLoGin class::Class,
1452da9a59SGnoCiYeH device::{
1552da9a59SGnoCiYeH bus::Bus,
1652da9a59SGnoCiYeH device_number::{DeviceNumber, Major},
1752da9a59SGnoCiYeH device_register,
1852da9a59SGnoCiYeH driver::Driver,
1952da9a59SGnoCiYeH Device, DeviceKObjType, DeviceType, IdTable,
2052da9a59SGnoCiYeH },
2152da9a59SGnoCiYeH kobject::{KObject, LockedKObjectState},
2252da9a59SGnoCiYeH kset::KSet,
2352da9a59SGnoCiYeH },
2452da9a59SGnoCiYeH serial::serial_init,
2552da9a59SGnoCiYeH },
260d48c3c9Slogin filesystem::{
2720e3152eSlogin devfs::{devfs_register, DevFS, DeviceINode},
2852da9a59SGnoCiYeH kernfs::KernFSInode,
2952da9a59SGnoCiYeH vfs::{file::FileMode, syscall::ModeType, FilePrivateData, FileType, IndexNode, Metadata},
300d48c3c9Slogin },
31c566df45SLoGin init::initcall::INITCALL_DEVICE,
32dfe53cf0SGnoCiYeH libs::{
33dfe53cf0SGnoCiYeH rwlock::{RwLock, RwLockWriteGuard},
34dfe53cf0SGnoCiYeH spinlock::SpinLockGuard,
35dfe53cf0SGnoCiYeH },
3652da9a59SGnoCiYeH mm::VirtAddr,
37415e14e9Slaokengwt net::event_poll::{EPollItem, KernelIoctlData},
3852da9a59SGnoCiYeH process::ProcessManager,
3952bcb59eSGnoCiYeH syscall::user_access::{UserBufferReader, UserBufferWriter},
400d48c3c9Slogin };
410d48c3c9Slogin
4252da9a59SGnoCiYeH use super::{
4359fdb447SLoGin kthread::tty_flush_thread_init,
44dfe53cf0SGnoCiYeH pty::unix98pty::ptmx_open,
450cb80734SLoGin sysfs::sys_class_tty_instance,
4652da9a59SGnoCiYeH termios::WindowSize,
4752da9a59SGnoCiYeH tty_core::{TtyCore, TtyFlag, TtyIoctlCmd},
48dfe53cf0SGnoCiYeH tty_driver::{TtyDriver, TtyDriverManager, TtyDriverSubType, TtyDriverType, TtyOperation},
4952da9a59SGnoCiYeH tty_job_control::TtyJobCtrlManager,
5052da9a59SGnoCiYeH virtual_terminal::vty_init,
5152da9a59SGnoCiYeH };
520d48c3c9Slogin
5352da9a59SGnoCiYeH #[derive(Debug)]
5452da9a59SGnoCiYeH pub struct InnerTtyDevice {
5552da9a59SGnoCiYeH /// 当前设备所述的kset
5652da9a59SGnoCiYeH kset: Option<Arc<KSet>>,
5752da9a59SGnoCiYeH parent_kobj: Option<Weak<dyn KObject>>,
5852da9a59SGnoCiYeH /// 当前设备所述的总线
5952da9a59SGnoCiYeH bus: Option<Weak<dyn Bus>>,
6052da9a59SGnoCiYeH inode: Option<Arc<KernFSInode>>,
6152da9a59SGnoCiYeH driver: Option<Weak<dyn Driver>>,
6252da9a59SGnoCiYeH can_match: bool,
6352da9a59SGnoCiYeH
6452da9a59SGnoCiYeH metadata: Metadata,
6520e3152eSlogin }
6620e3152eSlogin
6752da9a59SGnoCiYeH impl InnerTtyDevice {
new() -> Self6852da9a59SGnoCiYeH pub fn new() -> Self {
6952da9a59SGnoCiYeH Self {
7052da9a59SGnoCiYeH kset: None,
7152da9a59SGnoCiYeH parent_kobj: None,
7252da9a59SGnoCiYeH bus: None,
7352da9a59SGnoCiYeH inode: None,
7452da9a59SGnoCiYeH driver: None,
7552da9a59SGnoCiYeH can_match: false,
7652da9a59SGnoCiYeH metadata: Metadata::new(FileType::CharDevice, ModeType::from_bits_truncate(0o755)),
7752da9a59SGnoCiYeH }
7852da9a59SGnoCiYeH }
79dfe53cf0SGnoCiYeH
metadata_mut(&mut self) -> &mut Metadata80dfe53cf0SGnoCiYeH pub fn metadata_mut(&mut self) -> &mut Metadata {
81dfe53cf0SGnoCiYeH &mut self.metadata
82dfe53cf0SGnoCiYeH }
83dfe53cf0SGnoCiYeH }
84dfe53cf0SGnoCiYeH
85dfe53cf0SGnoCiYeH #[derive(Debug, PartialEq)]
86dfe53cf0SGnoCiYeH pub enum TtyType {
87dfe53cf0SGnoCiYeH Tty,
88dfe53cf0SGnoCiYeH Pty(PtyType),
89dfe53cf0SGnoCiYeH }
90dfe53cf0SGnoCiYeH
91dfe53cf0SGnoCiYeH #[derive(Debug, PartialEq)]
92dfe53cf0SGnoCiYeH pub enum PtyType {
93dfe53cf0SGnoCiYeH Ptm,
94dfe53cf0SGnoCiYeH Pts,
9552da9a59SGnoCiYeH }
9652da9a59SGnoCiYeH
970d48c3c9Slogin #[derive(Debug)]
9852da9a59SGnoCiYeH #[cast_to([sync] Device)]
990d48c3c9Slogin pub struct TtyDevice {
100dfe53cf0SGnoCiYeH name: String,
10152da9a59SGnoCiYeH id_table: IdTable,
102dfe53cf0SGnoCiYeH tty_type: TtyType,
10352da9a59SGnoCiYeH inner: RwLock<InnerTtyDevice>,
10452da9a59SGnoCiYeH kobj_state: LockedKObjectState,
10520e3152eSlogin /// TTY所属的文件系统
10620e3152eSlogin fs: RwLock<Weak<DevFS>>,
1070d48c3c9Slogin }
1080d48c3c9Slogin
1090d48c3c9Slogin impl TtyDevice {
new(name: String, id_table: IdTable, tty_type: TtyType) -> Arc<TtyDevice>110dfe53cf0SGnoCiYeH pub fn new(name: String, id_table: IdTable, tty_type: TtyType) -> Arc<TtyDevice> {
11152da9a59SGnoCiYeH let dev_num = id_table.device_number();
11252da9a59SGnoCiYeH let dev = TtyDevice {
11352da9a59SGnoCiYeH name,
11452da9a59SGnoCiYeH id_table,
11552da9a59SGnoCiYeH inner: RwLock::new(InnerTtyDevice::new()),
11652da9a59SGnoCiYeH kobj_state: LockedKObjectState::new(None),
1170d48c3c9Slogin fs: RwLock::new(Weak::default()),
118dfe53cf0SGnoCiYeH tty_type,
11952da9a59SGnoCiYeH };
12052da9a59SGnoCiYeH
12152da9a59SGnoCiYeH dev.inner.write().metadata.raw_dev = dev_num;
12252da9a59SGnoCiYeH
12352da9a59SGnoCiYeH Arc::new(dev)
12452da9a59SGnoCiYeH }
125dfe53cf0SGnoCiYeH
inner_write(&self) -> RwLockWriteGuard<InnerTtyDevice>126dfe53cf0SGnoCiYeH pub fn inner_write(&self) -> RwLockWriteGuard<InnerTtyDevice> {
127dfe53cf0SGnoCiYeH self.inner.write()
128dfe53cf0SGnoCiYeH }
1290d48c3c9Slogin }
1300d48c3c9Slogin
13152da9a59SGnoCiYeH impl IndexNode for TtyDevice {
open( &self, mut data: SpinLockGuard<FilePrivateData>, mode: &crate::filesystem::vfs::file::FileMode, ) -> Result<(), SystemError>13252da9a59SGnoCiYeH fn open(
1330d48c3c9Slogin &self,
134dfe53cf0SGnoCiYeH mut data: SpinLockGuard<FilePrivateData>,
13552da9a59SGnoCiYeH mode: &crate::filesystem::vfs::file::FileMode,
13652da9a59SGnoCiYeH ) -> Result<(), SystemError> {
137dfe53cf0SGnoCiYeH if let FilePrivateData::Tty(_) = &*data {
138dfe53cf0SGnoCiYeH return Ok(());
139dfe53cf0SGnoCiYeH }
1409365e801SGnoCiYeH if self.tty_type == TtyType::Pty(PtyType::Ptm) {
141dfe53cf0SGnoCiYeH return ptmx_open(data, mode);
142dfe53cf0SGnoCiYeH }
14352da9a59SGnoCiYeH let dev_num = self.metadata()?.raw_dev;
14452da9a59SGnoCiYeH
145dfe53cf0SGnoCiYeH let (index, driver) =
146dfe53cf0SGnoCiYeH TtyDriverManager::lookup_tty_driver(dev_num).ok_or(SystemError::ENODEV)?;
147dfe53cf0SGnoCiYeH
148dfe53cf0SGnoCiYeH let tty = TtyDriver::open_tty(index, driver)?;
14952da9a59SGnoCiYeH
15052da9a59SGnoCiYeH // 设置privdata
15152da9a59SGnoCiYeH *data = FilePrivateData::Tty(TtyFilePrivateData {
15252da9a59SGnoCiYeH tty: tty.clone(),
15352da9a59SGnoCiYeH mode: *mode,
15452da9a59SGnoCiYeH });
15552da9a59SGnoCiYeH
15652da9a59SGnoCiYeH let ret = tty.open(tty.core());
157b5b571e0SLoGin if let Err(err) = ret {
15852da9a59SGnoCiYeH if err == SystemError::ENOSYS {
15952da9a59SGnoCiYeH return Err(SystemError::ENODEV);
1600d48c3c9Slogin }
16152da9a59SGnoCiYeH return Err(err);
16252da9a59SGnoCiYeH }
16352da9a59SGnoCiYeH
16452da9a59SGnoCiYeH let driver = tty.core().driver();
16552da9a59SGnoCiYeH // 考虑noctty(当前tty)
16652da9a59SGnoCiYeH if !(mode.contains(FileMode::O_NOCTTY) && dev_num == DeviceNumber::new(Major::TTY_MAJOR, 0)
16752da9a59SGnoCiYeH || dev_num == DeviceNumber::new(Major::TTYAUX_MAJOR, 1)
16852da9a59SGnoCiYeH || (driver.tty_driver_type() == TtyDriverType::Pty
16952da9a59SGnoCiYeH && driver.tty_driver_sub_type() == TtyDriverSubType::PtyMaster))
17052da9a59SGnoCiYeH {
17152da9a59SGnoCiYeH let pcb = ProcessManager::current_pcb();
17252bcb59eSGnoCiYeH let pcb_tty = pcb.sig_info_irqsave().tty();
17352da9a59SGnoCiYeH if pcb_tty.is_none() && tty.core().contorl_info_irqsave().session.is_none() {
17452da9a59SGnoCiYeH TtyJobCtrlManager::proc_set_tty(tty);
17552da9a59SGnoCiYeH }
17652da9a59SGnoCiYeH }
17752da9a59SGnoCiYeH
17852da9a59SGnoCiYeH Ok(())
17952da9a59SGnoCiYeH }
18052da9a59SGnoCiYeH
read_at( &self, _offset: usize, len: usize, buf: &mut [u8], data: SpinLockGuard<FilePrivateData>, ) -> Result<usize, system_error::SystemError>18152da9a59SGnoCiYeH fn read_at(
18252da9a59SGnoCiYeH &self,
18352da9a59SGnoCiYeH _offset: usize,
18452da9a59SGnoCiYeH len: usize,
18552da9a59SGnoCiYeH buf: &mut [u8],
186dfe53cf0SGnoCiYeH data: SpinLockGuard<FilePrivateData>,
18752da9a59SGnoCiYeH ) -> Result<usize, system_error::SystemError> {
188dfe53cf0SGnoCiYeH let (tty, mode) = if let FilePrivateData::Tty(tty_priv) = &*data {
189dfe53cf0SGnoCiYeH (tty_priv.tty(), tty_priv.mode)
19052da9a59SGnoCiYeH } else {
191676b8ef6SMork return Err(SystemError::EIO);
19252da9a59SGnoCiYeH };
19352da9a59SGnoCiYeH
194dfe53cf0SGnoCiYeH drop(data);
195dfe53cf0SGnoCiYeH
19652da9a59SGnoCiYeH let ld = tty.ldisc();
19752da9a59SGnoCiYeH let mut offset = 0;
19852da9a59SGnoCiYeH let mut cookie = false;
19952da9a59SGnoCiYeH loop {
20052da9a59SGnoCiYeH let mut size = if len > buf.len() { buf.len() } else { len };
20152da9a59SGnoCiYeH size = ld.read(tty.clone(), buf, size, &mut cookie, offset, mode)?;
20252da9a59SGnoCiYeH // 没有更多数据
20352da9a59SGnoCiYeH if size == 0 {
20452da9a59SGnoCiYeH break;
2050d48c3c9Slogin }
20620e3152eSlogin
20752da9a59SGnoCiYeH offset += size;
20852da9a59SGnoCiYeH
20952da9a59SGnoCiYeH // 缓冲区写满
21052da9a59SGnoCiYeH if offset >= len {
21152da9a59SGnoCiYeH break;
21220e3152eSlogin }
21320e3152eSlogin
21452da9a59SGnoCiYeH // 没有更多数据
21552da9a59SGnoCiYeH if !cookie {
21652da9a59SGnoCiYeH break;
21720e3152eSlogin }
21820e3152eSlogin }
21920e3152eSlogin
22052da9a59SGnoCiYeH return Ok(offset);
22120e3152eSlogin }
22220e3152eSlogin
write_at( &self, _offset: usize, len: usize, buf: &[u8], data: SpinLockGuard<FilePrivateData>, ) -> Result<usize, system_error::SystemError>22352da9a59SGnoCiYeH fn write_at(
22452da9a59SGnoCiYeH &self,
22552da9a59SGnoCiYeH _offset: usize,
22652da9a59SGnoCiYeH len: usize,
22752da9a59SGnoCiYeH buf: &[u8],
228dfe53cf0SGnoCiYeH data: SpinLockGuard<FilePrivateData>,
22952da9a59SGnoCiYeH ) -> Result<usize, system_error::SystemError> {
23052da9a59SGnoCiYeH let mut count = len;
231dfe53cf0SGnoCiYeH let (tty, mode) = if let FilePrivateData::Tty(tty_priv) = &*data {
232dfe53cf0SGnoCiYeH (tty_priv.tty(), tty_priv.mode)
23352da9a59SGnoCiYeH } else {
23452da9a59SGnoCiYeH return Err(SystemError::EIO);
23552da9a59SGnoCiYeH };
236dfe53cf0SGnoCiYeH drop(data);
23752da9a59SGnoCiYeH let ld = tty.ldisc();
23852da9a59SGnoCiYeH let core = tty.core();
23952da9a59SGnoCiYeH let mut chunk = 2048;
24052da9a59SGnoCiYeH if core.flags().contains(TtyFlag::NO_WRITE_SPLIT) {
24152da9a59SGnoCiYeH chunk = 65536;
24252da9a59SGnoCiYeH }
24352da9a59SGnoCiYeH chunk = chunk.min(count);
24452da9a59SGnoCiYeH
24552da9a59SGnoCiYeH let pcb = ProcessManager::current_pcb();
24652da9a59SGnoCiYeH let mut written = 0;
24752da9a59SGnoCiYeH loop {
24852da9a59SGnoCiYeH // 至少需要写多少
24952da9a59SGnoCiYeH let size = chunk.min(count);
25052da9a59SGnoCiYeH
25152da9a59SGnoCiYeH // 将数据从buf拷贝到writebuf
25252da9a59SGnoCiYeH
25352bcb59eSGnoCiYeH let ret = ld.write(tty.clone(), &buf[written..], size, mode)?;
25452da9a59SGnoCiYeH
25552da9a59SGnoCiYeH written += ret;
25652da9a59SGnoCiYeH count -= ret;
25752da9a59SGnoCiYeH
25852da9a59SGnoCiYeH if count == 0 {
25952da9a59SGnoCiYeH break;
26052da9a59SGnoCiYeH }
26152da9a59SGnoCiYeH
26252bcb59eSGnoCiYeH if pcb.sig_info_irqsave().sig_pending().has_pending() {
26352da9a59SGnoCiYeH return Err(SystemError::ERESTARTSYS);
26420e3152eSlogin }
26520e3152eSlogin }
26652da9a59SGnoCiYeH
26752da9a59SGnoCiYeH if written > 0 {
26852da9a59SGnoCiYeH // todo: 更新时间
26952da9a59SGnoCiYeH }
27052da9a59SGnoCiYeH
27152da9a59SGnoCiYeH Ok(written)
27252da9a59SGnoCiYeH }
27352da9a59SGnoCiYeH
fs(&self) -> Arc<dyn crate::filesystem::vfs::FileSystem>27452da9a59SGnoCiYeH fn fs(&self) -> Arc<dyn crate::filesystem::vfs::FileSystem> {
27552da9a59SGnoCiYeH todo!()
27652da9a59SGnoCiYeH }
27752da9a59SGnoCiYeH
as_any_ref(&self) -> &dyn core::any::Any27852da9a59SGnoCiYeH fn as_any_ref(&self) -> &dyn core::any::Any {
279dfe53cf0SGnoCiYeH self
28052da9a59SGnoCiYeH }
28152da9a59SGnoCiYeH
list(&self) -> Result<alloc::vec::Vec<alloc::string::String>, system_error::SystemError>28252da9a59SGnoCiYeH fn list(&self) -> Result<alloc::vec::Vec<alloc::string::String>, system_error::SystemError> {
28352da9a59SGnoCiYeH todo!()
28452da9a59SGnoCiYeH }
28552da9a59SGnoCiYeH
metadata(&self) -> Result<crate::filesystem::vfs::Metadata, SystemError>28652da9a59SGnoCiYeH fn metadata(&self) -> Result<crate::filesystem::vfs::Metadata, SystemError> {
28752da9a59SGnoCiYeH Ok(self.inner.read().metadata.clone())
28852da9a59SGnoCiYeH }
28952da9a59SGnoCiYeH
set_metadata(&self, metadata: &Metadata) -> Result<(), SystemError>290dfe53cf0SGnoCiYeH fn set_metadata(&self, metadata: &Metadata) -> Result<(), SystemError> {
291dfe53cf0SGnoCiYeH let mut guard = self.inner_write();
292dfe53cf0SGnoCiYeH guard.metadata = metadata.clone();
293dfe53cf0SGnoCiYeH
29452da9a59SGnoCiYeH Ok(())
29552da9a59SGnoCiYeH }
29652da9a59SGnoCiYeH
close(&self, data: SpinLockGuard<FilePrivateData>) -> Result<(), SystemError>297dfe53cf0SGnoCiYeH fn close(&self, data: SpinLockGuard<FilePrivateData>) -> Result<(), SystemError> {
298dfe53cf0SGnoCiYeH let (tty, _mode) = if let FilePrivateData::Tty(tty_priv) = &*data {
299dfe53cf0SGnoCiYeH (tty_priv.tty(), tty_priv.mode)
300dfe53cf0SGnoCiYeH } else {
301dfe53cf0SGnoCiYeH return Err(SystemError::EIO);
302dfe53cf0SGnoCiYeH };
303dfe53cf0SGnoCiYeH drop(data);
304dfe53cf0SGnoCiYeH tty.close(tty.clone())
305dfe53cf0SGnoCiYeH }
306dfe53cf0SGnoCiYeH
resize(&self, _len: usize) -> Result<(), SystemError>30752da9a59SGnoCiYeH fn resize(&self, _len: usize) -> Result<(), SystemError> {
30852da9a59SGnoCiYeH Ok(())
30952da9a59SGnoCiYeH }
31052da9a59SGnoCiYeH
kernel_ioctl( &self, arg: Arc<dyn KernelIoctlData>, data: &FilePrivateData, ) -> Result<usize, SystemError>311415e14e9Slaokengwt fn kernel_ioctl(
312415e14e9Slaokengwt &self,
313415e14e9Slaokengwt arg: Arc<dyn KernelIoctlData>,
314415e14e9Slaokengwt data: &FilePrivateData,
315415e14e9Slaokengwt ) -> Result<usize, SystemError> {
316415e14e9Slaokengwt let epitem = arg
317415e14e9Slaokengwt .arc_any()
318415e14e9Slaokengwt .downcast::<EPollItem>()
319415e14e9Slaokengwt .map_err(|_| SystemError::EFAULT)?;
320415e14e9Slaokengwt
321415e14e9Slaokengwt let _ = UserBufferReader::new(
322415e14e9Slaokengwt &epitem as *const Arc<EPollItem>,
323415e14e9Slaokengwt core::mem::size_of::<Arc<EPollItem>>(),
324415e14e9Slaokengwt false,
325415e14e9Slaokengwt )?;
326415e14e9Slaokengwt
327415e14e9Slaokengwt let (tty, _) = if let FilePrivateData::Tty(tty_priv) = data {
328415e14e9Slaokengwt (tty_priv.tty(), tty_priv.mode)
329415e14e9Slaokengwt } else {
330415e14e9Slaokengwt return Err(SystemError::EIO);
331415e14e9Slaokengwt };
332415e14e9Slaokengwt
333415e14e9Slaokengwt let core = tty.core();
334415e14e9Slaokengwt
335415e14e9Slaokengwt core.add_epitem(epitem.clone());
336415e14e9Slaokengwt
337415e14e9Slaokengwt return Ok(0);
338415e14e9Slaokengwt }
339415e14e9Slaokengwt
ioctl(&self, cmd: u32, arg: usize, data: &FilePrivateData) -> Result<usize, SystemError>34052da9a59SGnoCiYeH fn ioctl(&self, cmd: u32, arg: usize, data: &FilePrivateData) -> Result<usize, SystemError> {
34152da9a59SGnoCiYeH let (tty, _) = if let FilePrivateData::Tty(tty_priv) = data {
342dfe53cf0SGnoCiYeH (tty_priv.tty(), tty_priv.mode)
34352da9a59SGnoCiYeH } else {
34452da9a59SGnoCiYeH return Err(SystemError::EIO);
34552da9a59SGnoCiYeH };
34652da9a59SGnoCiYeH
34752da9a59SGnoCiYeH match cmd {
34852da9a59SGnoCiYeH TtyIoctlCmd::TIOCSETD
34952da9a59SGnoCiYeH | TtyIoctlCmd::TIOCSBRK
35052da9a59SGnoCiYeH | TtyIoctlCmd::TIOCCBRK
35152da9a59SGnoCiYeH | TtyIoctlCmd::TCSBRK
35252da9a59SGnoCiYeH | TtyIoctlCmd::TCSBRKP => {
35352da9a59SGnoCiYeH TtyJobCtrlManager::tty_check_change(tty.clone(), Signal::SIGTTOU)?;
35452da9a59SGnoCiYeH if cmd != TtyIoctlCmd::TIOCCBRK {
35552da9a59SGnoCiYeH todo!()
35652da9a59SGnoCiYeH }
35752da9a59SGnoCiYeH }
35852da9a59SGnoCiYeH _ => {}
35952da9a59SGnoCiYeH }
36052da9a59SGnoCiYeH
36152da9a59SGnoCiYeH match cmd {
36252da9a59SGnoCiYeH TtyIoctlCmd::TIOCGWINSZ => {
36352da9a59SGnoCiYeH let core = tty.core();
36452da9a59SGnoCiYeH let winsize = *core.window_size();
36552da9a59SGnoCiYeH
36652da9a59SGnoCiYeH let mut user_writer = UserBufferWriter::new(
36752da9a59SGnoCiYeH VirtAddr::new(arg).as_ptr::<WindowSize>(),
36852da9a59SGnoCiYeH core::mem::size_of::<WindowSize>(),
36952da9a59SGnoCiYeH true,
37052da9a59SGnoCiYeH )?;
37152da9a59SGnoCiYeH
37252da9a59SGnoCiYeH let err = user_writer.copy_one_to_user(&winsize, 0);
37352da9a59SGnoCiYeH if err.is_err() {
37452da9a59SGnoCiYeH return Err(SystemError::EFAULT);
37552da9a59SGnoCiYeH }
37652da9a59SGnoCiYeH return Ok(0);
37752da9a59SGnoCiYeH }
3789365e801SGnoCiYeH TtyIoctlCmd::TIOCSWINSZ => {
3799365e801SGnoCiYeH let reader = UserBufferReader::new(
3809365e801SGnoCiYeH arg as *const (),
3819365e801SGnoCiYeH core::mem::size_of::<WindowSize>(),
3829365e801SGnoCiYeH true,
3839365e801SGnoCiYeH )?;
3849365e801SGnoCiYeH
3859365e801SGnoCiYeH let user_winsize = reader.read_one_from_user::<WindowSize>(0)?;
3869365e801SGnoCiYeH
3879365e801SGnoCiYeH let ret = tty.resize(tty.clone(), *user_winsize);
3889365e801SGnoCiYeH
3899365e801SGnoCiYeH if ret != Err(SystemError::ENOSYS) {
3909365e801SGnoCiYeH return ret.map(|_| 0);
3919365e801SGnoCiYeH } else {
3929365e801SGnoCiYeH return tty.tty_do_resize(*user_winsize).map(|_| 0);
3939365e801SGnoCiYeH }
3949365e801SGnoCiYeH }
39552da9a59SGnoCiYeH _ => match TtyJobCtrlManager::job_ctrl_ioctl(tty.clone(), cmd, arg) {
39652da9a59SGnoCiYeH Ok(_) => {
39752da9a59SGnoCiYeH return Ok(0);
39852da9a59SGnoCiYeH }
39952da9a59SGnoCiYeH Err(e) => {
40052da9a59SGnoCiYeH if e != SystemError::ENOIOCTLCMD {
40152da9a59SGnoCiYeH return Err(e);
40252da9a59SGnoCiYeH }
40352da9a59SGnoCiYeH }
40452da9a59SGnoCiYeH },
40552da9a59SGnoCiYeH }
40652da9a59SGnoCiYeH
40752da9a59SGnoCiYeH match tty.ioctl(tty.clone(), cmd, arg) {
40852da9a59SGnoCiYeH Ok(_) => {
40952da9a59SGnoCiYeH return Ok(0);
41052da9a59SGnoCiYeH }
41152da9a59SGnoCiYeH Err(e) => {
41252da9a59SGnoCiYeH if e != SystemError::ENOIOCTLCMD {
41352da9a59SGnoCiYeH return Err(e);
41452da9a59SGnoCiYeH }
41552da9a59SGnoCiYeH }
41652da9a59SGnoCiYeH }
41752da9a59SGnoCiYeH tty.ldisc().ioctl(tty, cmd, arg)?;
41852da9a59SGnoCiYeH
41952da9a59SGnoCiYeH Ok(0)
42020e3152eSlogin }
42152bcb59eSGnoCiYeH
poll(&self, private_data: &FilePrivateData) -> Result<usize, SystemError>42252bcb59eSGnoCiYeH fn poll(&self, private_data: &FilePrivateData) -> Result<usize, SystemError> {
42352bcb59eSGnoCiYeH let (tty, _) = if let FilePrivateData::Tty(tty_priv) = private_data {
42452bcb59eSGnoCiYeH (tty_priv.tty.clone(), tty_priv.mode)
42552bcb59eSGnoCiYeH } else {
42652bcb59eSGnoCiYeH return Err(SystemError::EIO);
42752bcb59eSGnoCiYeH };
42852bcb59eSGnoCiYeH
42952bcb59eSGnoCiYeH tty.ldisc().poll(tty)
43052bcb59eSGnoCiYeH }
4310d48c3c9Slogin }
4320d48c3c9Slogin
4330d48c3c9Slogin impl DeviceINode for TtyDevice {
set_fs(&self, fs: alloc::sync::Weak<crate::filesystem::devfs::DevFS>)4340d48c3c9Slogin fn set_fs(&self, fs: alloc::sync::Weak<crate::filesystem::devfs::DevFS>) {
4350d48c3c9Slogin *self.fs.write() = fs;
4360d48c3c9Slogin }
4370d48c3c9Slogin }
4380d48c3c9Slogin
43952da9a59SGnoCiYeH impl KObject for TtyDevice {
as_any_ref(&self) -> &dyn core::any::Any4400d48c3c9Slogin fn as_any_ref(&self) -> &dyn core::any::Any {
4410d48c3c9Slogin self
4420d48c3c9Slogin }
4430d48c3c9Slogin
set_inode(&self, inode: Option<Arc<crate::filesystem::kernfs::KernFSInode>>)44452da9a59SGnoCiYeH fn set_inode(&self, inode: Option<Arc<crate::filesystem::kernfs::KernFSInode>>) {
44552da9a59SGnoCiYeH self.inner.write().inode = inode;
4460d48c3c9Slogin }
44720e3152eSlogin
inode(&self) -> Option<Arc<crate::filesystem::kernfs::KernFSInode>>44852da9a59SGnoCiYeH fn inode(&self) -> Option<Arc<crate::filesystem::kernfs::KernFSInode>> {
44952da9a59SGnoCiYeH self.inner.read().inode.clone()
45020e3152eSlogin }
45120e3152eSlogin
parent(&self) -> Option<alloc::sync::Weak<dyn KObject>>45252da9a59SGnoCiYeH fn parent(&self) -> Option<alloc::sync::Weak<dyn KObject>> {
45352da9a59SGnoCiYeH self.inner.read().parent_kobj.clone()
45452da9a59SGnoCiYeH }
45552da9a59SGnoCiYeH
set_parent(&self, parent: Option<alloc::sync::Weak<dyn KObject>>)45652da9a59SGnoCiYeH fn set_parent(&self, parent: Option<alloc::sync::Weak<dyn KObject>>) {
45752da9a59SGnoCiYeH self.inner.write().parent_kobj = parent
45852da9a59SGnoCiYeH }
45952da9a59SGnoCiYeH
kset(&self) -> Option<Arc<crate::driver::base::kset::KSet>>46052da9a59SGnoCiYeH fn kset(&self) -> Option<Arc<crate::driver::base::kset::KSet>> {
46152da9a59SGnoCiYeH self.inner.read().kset.clone()
46252da9a59SGnoCiYeH }
46352da9a59SGnoCiYeH
set_kset(&self, kset: Option<Arc<crate::driver::base::kset::KSet>>)46452da9a59SGnoCiYeH fn set_kset(&self, kset: Option<Arc<crate::driver::base::kset::KSet>>) {
46552da9a59SGnoCiYeH self.inner.write().kset = kset
46652da9a59SGnoCiYeH }
46752da9a59SGnoCiYeH
kobj_type(&self) -> Option<&'static dyn crate::driver::base::kobject::KObjType>46852da9a59SGnoCiYeH fn kobj_type(&self) -> Option<&'static dyn crate::driver::base::kobject::KObjType> {
46952da9a59SGnoCiYeH Some(&DeviceKObjType)
47052da9a59SGnoCiYeH }
47152da9a59SGnoCiYeH
set_kobj_type(&self, _ktype: Option<&'static dyn crate::driver::base::kobject::KObjType>)47252da9a59SGnoCiYeH fn set_kobj_type(&self, _ktype: Option<&'static dyn crate::driver::base::kobject::KObjType>) {}
47352da9a59SGnoCiYeH
name(&self) -> alloc::string::String47452da9a59SGnoCiYeH fn name(&self) -> alloc::string::String {
47552da9a59SGnoCiYeH self.name.to_string()
47652da9a59SGnoCiYeH }
47752da9a59SGnoCiYeH
set_name(&self, _name: alloc::string::String)47852da9a59SGnoCiYeH fn set_name(&self, _name: alloc::string::String) {
47952da9a59SGnoCiYeH // self.name = name
48052da9a59SGnoCiYeH }
48152da9a59SGnoCiYeH
kobj_state( &self, ) -> crate::libs::rwlock::RwLockReadGuard<crate::driver::base::kobject::KObjectState>48252da9a59SGnoCiYeH fn kobj_state(
48352da9a59SGnoCiYeH &self,
48452da9a59SGnoCiYeH ) -> crate::libs::rwlock::RwLockReadGuard<crate::driver::base::kobject::KObjectState> {
48552da9a59SGnoCiYeH self.kobj_state.read()
48652da9a59SGnoCiYeH }
48752da9a59SGnoCiYeH
kobj_state_mut( &self, ) -> crate::libs::rwlock::RwLockWriteGuard<crate::driver::base::kobject::KObjectState>48852da9a59SGnoCiYeH fn kobj_state_mut(
48952da9a59SGnoCiYeH &self,
49052da9a59SGnoCiYeH ) -> crate::libs::rwlock::RwLockWriteGuard<crate::driver::base::kobject::KObjectState> {
49152da9a59SGnoCiYeH self.kobj_state.write()
49252da9a59SGnoCiYeH }
49352da9a59SGnoCiYeH
set_kobj_state(&self, state: crate::driver::base::kobject::KObjectState)49452da9a59SGnoCiYeH fn set_kobj_state(&self, state: crate::driver::base::kobject::KObjectState) {
49552da9a59SGnoCiYeH *self.kobj_state.write() = state
49652da9a59SGnoCiYeH }
49752da9a59SGnoCiYeH }
49852da9a59SGnoCiYeH
49952da9a59SGnoCiYeH impl Device for TtyDevice {
dev_type(&self) -> crate::driver::base::device::DeviceType50052da9a59SGnoCiYeH fn dev_type(&self) -> crate::driver::base::device::DeviceType {
50152da9a59SGnoCiYeH DeviceType::Char
50252da9a59SGnoCiYeH }
50352da9a59SGnoCiYeH
id_table(&self) -> crate::driver::base::device::IdTable50452da9a59SGnoCiYeH fn id_table(&self) -> crate::driver::base::device::IdTable {
50552da9a59SGnoCiYeH self.id_table.clone()
50652da9a59SGnoCiYeH }
50752da9a59SGnoCiYeH
bus(&self) -> Option<Weak<dyn Bus>>5080cb80734SLoGin fn bus(&self) -> Option<Weak<dyn Bus>> {
5090cb80734SLoGin self.inner.read().bus.clone()
5100cb80734SLoGin }
5110cb80734SLoGin
set_bus(&self, bus: Option<alloc::sync::Weak<dyn crate::driver::base::device::bus::Bus>>)51252da9a59SGnoCiYeH fn set_bus(&self, bus: Option<alloc::sync::Weak<dyn crate::driver::base::device::bus::Bus>>) {
51352da9a59SGnoCiYeH self.inner.write().bus = bus
51452da9a59SGnoCiYeH }
51552da9a59SGnoCiYeH
set_class(&self, _class: Option<Weak<dyn crate::driver::base::class::Class>>)5164256da7fSLoGin fn set_class(&self, _class: Option<Weak<dyn crate::driver::base::class::Class>>) {
5170cb80734SLoGin // do nothing
5180cb80734SLoGin }
5190cb80734SLoGin
class(&self) -> Option<Arc<dyn Class>>5200cb80734SLoGin fn class(&self) -> Option<Arc<dyn Class>> {
5210cb80734SLoGin sys_class_tty_instance()
5220cb80734SLoGin .cloned()
5230cb80734SLoGin .map(|x| x as Arc<dyn Class>)
52452da9a59SGnoCiYeH }
52552da9a59SGnoCiYeH
driver(&self) -> Option<Arc<dyn crate::driver::base::device::driver::Driver>>52652da9a59SGnoCiYeH fn driver(&self) -> Option<Arc<dyn crate::driver::base::device::driver::Driver>> {
52752da9a59SGnoCiYeH self.inner.read().driver.clone()?.upgrade()
52852da9a59SGnoCiYeH }
52952da9a59SGnoCiYeH
set_driver( &self, driver: Option<alloc::sync::Weak<dyn crate::driver::base::device::driver::Driver>>, )53052da9a59SGnoCiYeH fn set_driver(
53152da9a59SGnoCiYeH &self,
53252da9a59SGnoCiYeH driver: Option<alloc::sync::Weak<dyn crate::driver::base::device::driver::Driver>>,
53352da9a59SGnoCiYeH ) {
53452da9a59SGnoCiYeH self.inner.write().driver = driver
53552da9a59SGnoCiYeH }
53652da9a59SGnoCiYeH
is_dead(&self) -> bool53752da9a59SGnoCiYeH fn is_dead(&self) -> bool {
53852da9a59SGnoCiYeH false
53952da9a59SGnoCiYeH }
54052da9a59SGnoCiYeH
can_match(&self) -> bool54152da9a59SGnoCiYeH fn can_match(&self) -> bool {
54252da9a59SGnoCiYeH self.inner.read().can_match
54352da9a59SGnoCiYeH }
54452da9a59SGnoCiYeH
set_can_match(&self, can_match: bool)54552da9a59SGnoCiYeH fn set_can_match(&self, can_match: bool) {
54652da9a59SGnoCiYeH self.inner.write().can_match = can_match
54752da9a59SGnoCiYeH }
54852da9a59SGnoCiYeH
state_synced(&self) -> bool54952da9a59SGnoCiYeH fn state_synced(&self) -> bool {
55052da9a59SGnoCiYeH true
55152da9a59SGnoCiYeH }
552*28fe4ad2S黄铭涛
dev_parent(&self) -> Option<alloc::sync::Weak<dyn crate::driver::base::device::Device>>553*28fe4ad2S黄铭涛 fn dev_parent(&self) -> Option<alloc::sync::Weak<dyn crate::driver::base::device::Device>> {
554*28fe4ad2S黄铭涛 None
555*28fe4ad2S黄铭涛 }
556*28fe4ad2S黄铭涛
set_dev_parent( &self, _dev_parent: Option<alloc::sync::Weak<dyn crate::driver::base::device::Device>>, )557*28fe4ad2S黄铭涛 fn set_dev_parent(
558*28fe4ad2S黄铭涛 &self,
559*28fe4ad2S黄铭涛 _dev_parent: Option<alloc::sync::Weak<dyn crate::driver::base::device::Device>>,
560*28fe4ad2S黄铭涛 ) {
561*28fe4ad2S黄铭涛 todo!()
562*28fe4ad2S黄铭涛 }
56352da9a59SGnoCiYeH }
56452da9a59SGnoCiYeH
56552da9a59SGnoCiYeH impl CharDevice for TtyDevice {
read(&self, _len: usize, _buf: &mut [u8]) -> Result<usize, SystemError>56652da9a59SGnoCiYeH fn read(&self, _len: usize, _buf: &mut [u8]) -> Result<usize, SystemError> {
56752da9a59SGnoCiYeH todo!()
56852da9a59SGnoCiYeH }
56952da9a59SGnoCiYeH
write(&self, _len: usize, _buf: &[u8]) -> Result<usize, SystemError>57052da9a59SGnoCiYeH fn write(&self, _len: usize, _buf: &[u8]) -> Result<usize, SystemError> {
57152da9a59SGnoCiYeH todo!()
57220e3152eSlogin }
57320e3152eSlogin
sync(&self) -> Result<(), SystemError>57420e3152eSlogin fn sync(&self) -> Result<(), SystemError> {
57552da9a59SGnoCiYeH todo!()
57611110997Shanjiezhou }
57720e3152eSlogin }
57820e3152eSlogin
57952da9a59SGnoCiYeH #[derive(Debug, Clone)]
58052da9a59SGnoCiYeH pub struct TtyFilePrivateData {
581dfe53cf0SGnoCiYeH pub tty: Arc<TtyCore>,
582dfe53cf0SGnoCiYeH pub mode: FileMode,
583dfe53cf0SGnoCiYeH }
584dfe53cf0SGnoCiYeH
585dfe53cf0SGnoCiYeH impl TtyFilePrivateData {
tty(&self) -> Arc<TtyCore>586dfe53cf0SGnoCiYeH pub fn tty(&self) -> Arc<TtyCore> {
587dfe53cf0SGnoCiYeH self.tty.clone()
588dfe53cf0SGnoCiYeH }
58920e3152eSlogin }
59020e3152eSlogin
59152da9a59SGnoCiYeH /// 初始化tty设备和console子设备
592c566df45SLoGin #[unified_init(INITCALL_DEVICE)]
59352da9a59SGnoCiYeH #[inline(never)]
tty_init() -> Result<(), SystemError>59420e3152eSlogin pub fn tty_init() -> Result<(), SystemError> {
59552da9a59SGnoCiYeH let tty = TtyDevice::new(
596dfe53cf0SGnoCiYeH "tty0".to_string(),
59752da9a59SGnoCiYeH IdTable::new(
59852da9a59SGnoCiYeH String::from("tty0"),
59952da9a59SGnoCiYeH Some(DeviceNumber::new(Major::TTY_MAJOR, 0)),
60052da9a59SGnoCiYeH ),
601dfe53cf0SGnoCiYeH TtyType::Tty,
60252da9a59SGnoCiYeH );
60320e3152eSlogin
60452da9a59SGnoCiYeH let console = TtyDevice::new(
605dfe53cf0SGnoCiYeH "console".to_string(),
60652da9a59SGnoCiYeH IdTable::new(
60752da9a59SGnoCiYeH String::from("console"),
60852da9a59SGnoCiYeH Some(DeviceNumber::new(Major::TTYAUX_MAJOR, 1)),
60952da9a59SGnoCiYeH ),
610dfe53cf0SGnoCiYeH TtyType::Tty,
61152da9a59SGnoCiYeH );
61220e3152eSlogin
61352da9a59SGnoCiYeH // 注册tty设备
61452da9a59SGnoCiYeH // CharDevOps::cdev_add(
61552da9a59SGnoCiYeH // tty.clone() as Arc<dyn CharDevice>,
61652da9a59SGnoCiYeH // IdTable::new(
61752da9a59SGnoCiYeH // String::from("tty0"),
61852da9a59SGnoCiYeH // Some(DeviceNumber::new(Major::TTYAUX_MAJOR, 0)),
61952da9a59SGnoCiYeH // ),
62052da9a59SGnoCiYeH // 1,
62152da9a59SGnoCiYeH // )?;
62220e3152eSlogin
62352da9a59SGnoCiYeH // CharDevOps::register_chardev_region(DeviceNumber::new(Major::TTYAUX_MAJOR, 0), 1, "/dev/tty")?;
62420e3152eSlogin
62552da9a59SGnoCiYeH // 注册console设备
62652da9a59SGnoCiYeH // CharDevOps::cdev_add(
62752da9a59SGnoCiYeH // console.clone() as Arc<dyn CharDevice>,
62852da9a59SGnoCiYeH // IdTable::new(
62952da9a59SGnoCiYeH // String::from("console"),
63052da9a59SGnoCiYeH // Some(DeviceNumber::new(Major::TTYAUX_MAJOR, 1)),
63152da9a59SGnoCiYeH // ),
63252da9a59SGnoCiYeH // 1,
63352da9a59SGnoCiYeH // )?;
63420e3152eSlogin
63552da9a59SGnoCiYeH // CharDevOps::register_chardev_region(DeviceNumber::new(Major::TTYAUX_MAJOR, 1), 1, "/dev/tty")?;
63652da9a59SGnoCiYeH
63752da9a59SGnoCiYeH // 将这两个设备注册到devfs,TODO:这里console设备应该与tty在一个设备group里面
63852da9a59SGnoCiYeH device_register(tty.clone())?;
63952da9a59SGnoCiYeH device_register(console.clone())?;
640dfe53cf0SGnoCiYeH devfs_register(&tty.name.clone(), tty)?;
641dfe53cf0SGnoCiYeH devfs_register(&console.name.clone(), console)?;
64220e3152eSlogin
643a03c4f9dSLoGin serial_init()?;
64459fdb447SLoGin
64559fdb447SLoGin tty_flush_thread_init();
64652da9a59SGnoCiYeH return vty_init();
6470d48c3c9Slogin }
648