From be60c929c8285d3050e022aa23312a84129e54b2 Mon Sep 17 00:00:00 2001 From: GnoCiYeH Date: Wed, 28 Feb 2024 20:18:49 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E6=94=B9tty=E5=87=A0=E4=B8=AAbug=20(#?= =?UTF-8?q?549)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * 更改ioctl一处逻辑错误 * 删除不必要的impl * 修改一处bug,并且加入tty的link,为pty做准备 * 修改一处因为vc的pos和x计算错误导致的溢出 --- kernel/src/driver/tty/termios.rs | 3 +- kernel/src/driver/tty/tty_core.rs | 60 +++++++++++-------- kernel/src/driver/tty/tty_ldisc/ntty.rs | 2 +- kernel/src/driver/tty/virtual_terminal/mod.rs | 2 - .../tty/virtual_terminal/virtual_console.rs | 7 ++- 5 files changed, 43 insertions(+), 31 deletions(-) diff --git a/kernel/src/driver/tty/termios.rs b/kernel/src/driver/tty/termios.rs index ef7dee54..67809648 100644 --- a/kernel/src/driver/tty/termios.rs +++ b/kernel/src/driver/tty/termios.rs @@ -26,7 +26,7 @@ pub struct Termios { pub output_speed: u32, } -#[derive(Clone, Copy)] +#[derive(Clone, Copy, Default)] pub struct PosixTermios { pub c_iflag: u32, pub c_oflag: u32, @@ -54,6 +54,7 @@ impl PosixTermios { #[allow(dead_code)] pub fn to_kernel_termios(&self) -> Termios { + // TODO:这里没有考虑非规范模式 Termios { input_mode: InputMode::from_bits_truncate(self.c_iflag), output_mode: OutputMode::from_bits_truncate(self.c_oflag), diff --git a/kernel/src/driver/tty/tty_core.rs b/kernel/src/driver/tty/tty_core.rs index f5bd1d2f..c3a50de9 100644 --- a/kernel/src/driver/tty/tty_core.rs +++ b/kernel/src/driver/tty/tty_core.rs @@ -12,7 +12,7 @@ use crate::{ mm::VirtAddr, net::event_poll::EPollEventType, process::Pid, - syscall::user_access::UserBufferWriter, + syscall::user_access::{UserBufferReader, UserBufferWriter}, }; use super::{ @@ -51,6 +51,7 @@ impl TtyCore { ctrl: SpinLock::new(TtyContorlInfo::default()), closing: AtomicBool::new(false), flow: SpinLock::new(TtyFlowState::default()), + link: None, }; return Arc::new(Self { @@ -128,15 +129,19 @@ impl TtyCore { .wakeup(EPollEventType::EPOLLOUT.bits() as u64); } - pub fn tty_mode_ioctl( - &self, - tty: Arc, - cmd: u32, - arg: usize, - ) -> Result { + pub fn tty_mode_ioctl(tty: Arc, cmd: u32, arg: usize) -> Result { + let real_tty; + let core = tty.core(); + if core.driver().tty_driver_type() == TtyDriverType::Pty + && core.driver().tty_driver_sub_type() == TtyDriverSubType::PtyMaster + { + real_tty = core.link().unwrap(); + } else { + real_tty = tty; + } match cmd { TtyIoctlCmd::TCGETS => { - let termios = PosixTermios::from_kernel_termios(self.core.termios().clone()); + let termios = PosixTermios::from_kernel_termios(real_tty.core.termios().clone()); let mut user_writer = UserBufferWriter::new( VirtAddr::new(arg).as_ptr::(), core::mem::size_of::(), @@ -147,8 +152,8 @@ impl TtyCore { return Ok(0); } TtyIoctlCmd::TCSETSW => { - return self.core_set_termios( - tty, + return TtyCore::core_set_termios( + real_tty, VirtAddr::new(arg), TtySetTermiosOpt::TERMIOS_WAIT | TtySetTermiosOpt::TERMIOS_OLD, ); @@ -160,27 +165,31 @@ impl TtyCore { } pub fn core_set_termios( - &self, tty: Arc, arg: VirtAddr, opt: TtySetTermiosOpt, ) -> Result { - let tmp_termios = self.core().termios().clone(); + #[allow(unused_assignments)] + // TERMIOS_TERMIO下会用到 + let mut tmp_termios = tty.core().termios().clone(); if opt.contains(TtySetTermiosOpt::TERMIOS_TERMIO) { todo!() } else { - let mut user_writer = UserBufferWriter::new( + let user_reader = UserBufferReader::new( arg.as_ptr::(), core::mem::size_of::(), true, )?; - user_writer.copy_one_to_user(&tmp_termios, 0)?; + let mut term = PosixTermios::default(); + user_reader.copy_one_from_user(&mut term, 0)?; + + tmp_termios = term.to_kernel_termios(); } if opt.contains(TtySetTermiosOpt::TERMIOS_FLUSH) { - let ld = self.ldisc(); + let ld = tty.ldisc(); let _ = ld.flush_buffer(tty.clone()); } @@ -188,16 +197,12 @@ impl TtyCore { // TODO } - self.set_termios_next(tty, tmp_termios)?; + TtyCore::set_termios_next(tty, tmp_termios)?; Ok(0) } - pub fn set_termios_next( - &self, - tty: Arc, - new_termios: Termios, - ) -> Result<(), SystemError> { - let mut termios = self.core().termios_write(); + pub fn set_termios_next(tty: Arc, new_termios: Termios) -> Result<(), SystemError> { + let mut termios = tty.core().termios_write(); let old_termios = termios.clone(); @@ -206,7 +211,7 @@ impl TtyCore { let tmp = termios.control_mode; termios.control_mode ^= (tmp ^ old_termios.control_mode) & ControlMode::ADDRB; - let ret = self.set_termios(tty.clone(), old_termios); + let ret = tty.set_termios(tty.clone(), old_termios); if ret.is_err() { termios.control_mode &= ControlMode::HUPCL | ControlMode::CREAD | ControlMode::CLOCAL; termios.control_mode |= old_termios.control_mode @@ -216,7 +221,7 @@ impl TtyCore { } drop(termios); - let ld = self.ldisc(); + let ld = tty.ldisc(); ld.set_termios(tty, Some(old_termios))?; Ok(()) @@ -285,6 +290,8 @@ pub struct TtyCoreData { closing: AtomicBool, /// 流控状态 flow: SpinLock, + /// 链接tty + link: Option>, } impl TtyCoreData { @@ -374,6 +381,11 @@ impl TtyCoreData { pub fn vc_data_irqsave(&self) -> SpinLockGuard { VIRT_CONSOLES[self.index].lock_irqsave() } + + #[inline] + pub fn link(&self) -> Option> { + self.link.clone() + } } /// TTY 核心接口,不同的tty需要各自实现这个trait diff --git a/kernel/src/driver/tty/tty_ldisc/ntty.rs b/kernel/src/driver/tty/tty_ldisc/ntty.rs index 66fd48dc..57495add 100644 --- a/kernel/src/driver/tty/tty_ldisc/ntty.rs +++ b/kernel/src/driver/tty/tty_ldisc/ntty.rs @@ -59,7 +59,7 @@ impl NTtyLinediscipline { todo!() } _ => { - return tty.tty_mode_ioctl(tty.clone(), cmd, arg); + return TtyCore::tty_mode_ioctl(tty.clone(), cmd, arg); } } } diff --git a/kernel/src/driver/tty/virtual_terminal/mod.rs b/kernel/src/driver/tty/virtual_terminal/mod.rs index 9f898329..011d4129 100644 --- a/kernel/src/driver/tty/virtual_terminal/mod.rs +++ b/kernel/src/driver/tty/virtual_terminal/mod.rs @@ -96,8 +96,6 @@ pub struct TtyConsoleDriverInner { console: Arc, } -unsafe impl Sync for TtyConsoleDriverInner {} - impl TtyConsoleDriverInner { pub fn new() -> Result { Ok(Self { diff --git a/kernel/src/driver/tty/virtual_terminal/virtual_console.rs b/kernel/src/driver/tty/virtual_terminal/virtual_console.rs index 7812cbbc..0e7ecdd9 100644 --- a/kernel/src/driver/tty/virtual_terminal/virtual_console.rs +++ b/kernel/src/driver/tty/virtual_terminal/virtual_console.rs @@ -581,7 +581,7 @@ impl VirtualConsoleData { self.state.y = y as usize; } - self.pos = self.state.y * self.cols + (self.state.x << 1); + self.pos = self.state.y * self.cols + self.state.x; self.need_wrap = false; } @@ -1200,12 +1200,13 @@ impl VirtualConsoleData { } } - for i in self.screen_buf[start..(start + count)].iter_mut() { + let max_idx = self.screen_buf.len(); + for i in self.screen_buf[start..max_idx.min(start + count)].iter_mut() { *i = self.erase_char; } if self.should_update() { - self.do_update_region(start, count) + self.do_update_region(start, count.min(max_idx - start)) } self.need_wrap = false;