1*52da9a59SGnoCiYeH use alloc::sync::Arc; 2*52da9a59SGnoCiYeH use system_error::SystemError; 3*52da9a59SGnoCiYeH 4*52da9a59SGnoCiYeH use crate::{ 5*52da9a59SGnoCiYeH arch::ipc::signal::{SigSet, Signal}, 6*52da9a59SGnoCiYeH mm::VirtAddr, 7*52da9a59SGnoCiYeH process::{Pid, ProcessManager}, 8*52da9a59SGnoCiYeH syscall::{user_access::UserBufferWriter, Syscall}, 9*52da9a59SGnoCiYeH }; 10*52da9a59SGnoCiYeH 11*52da9a59SGnoCiYeH use super::tty_core::{TtyCore, TtyIoctlCmd}; 12*52da9a59SGnoCiYeH 13*52da9a59SGnoCiYeH pub struct TtyJobCtrlManager; 14*52da9a59SGnoCiYeH 15*52da9a59SGnoCiYeH impl TtyJobCtrlManager { 16*52da9a59SGnoCiYeH /// ### 设置当前进程的tty 17*52da9a59SGnoCiYeH pub fn proc_set_tty(tty: Arc<TtyCore>) { 18*52da9a59SGnoCiYeH let core = tty.core(); 19*52da9a59SGnoCiYeH let mut ctrl = core.contorl_info_irqsave(); 20*52da9a59SGnoCiYeH let pcb = ProcessManager::current_pcb(); 21*52da9a59SGnoCiYeH 22*52da9a59SGnoCiYeH // todo 目前将pgid设置为pid 23*52da9a59SGnoCiYeH ctrl.pgid = Some(pcb.pid()); 24*52da9a59SGnoCiYeH ctrl.session = Some(pcb.pid()); 25*52da9a59SGnoCiYeH 26*52da9a59SGnoCiYeH assert!(pcb.sig_info_irqsave().tty().is_none()); 27*52da9a59SGnoCiYeH 28*52da9a59SGnoCiYeH let mut singal = pcb.sig_info_mut(); 29*52da9a59SGnoCiYeH drop(ctrl); 30*52da9a59SGnoCiYeH singal.set_tty(tty); 31*52da9a59SGnoCiYeH } 32*52da9a59SGnoCiYeH 33*52da9a59SGnoCiYeH /// ### 检查tty 34*52da9a59SGnoCiYeH pub fn tty_check_change(tty: Arc<TtyCore>, sig: Signal) -> Result<(), SystemError> { 35*52da9a59SGnoCiYeH let pcb = ProcessManager::current_pcb(); 36*52da9a59SGnoCiYeH 37*52da9a59SGnoCiYeH if pcb.sig_info().tty().is_none() || !Arc::ptr_eq(&pcb.sig_info().tty().unwrap(), &tty) { 38*52da9a59SGnoCiYeH return Ok(()); 39*52da9a59SGnoCiYeH } 40*52da9a59SGnoCiYeH 41*52da9a59SGnoCiYeH let core = tty.core(); 42*52da9a59SGnoCiYeH let ctrl = core.contorl_info_irqsave(); 43*52da9a59SGnoCiYeH 44*52da9a59SGnoCiYeH // todo pgid 45*52da9a59SGnoCiYeH let pgid = pcb.pid(); 46*52da9a59SGnoCiYeH let tty_pgid = ctrl.pgid; 47*52da9a59SGnoCiYeH 48*52da9a59SGnoCiYeH if tty_pgid.is_some() && tty_pgid.unwrap() != pgid { 49*52da9a59SGnoCiYeH if pcb 50*52da9a59SGnoCiYeH .sig_info_irqsave() 51*52da9a59SGnoCiYeH .sig_block() 52*52da9a59SGnoCiYeH .contains(SigSet::from_bits_truncate(1 << sig as u64)) 53*52da9a59SGnoCiYeH || pcb.sig_struct_irqsave().handlers[sig as usize].is_ignore() 54*52da9a59SGnoCiYeH { 55*52da9a59SGnoCiYeH // 忽略该信号 56*52da9a59SGnoCiYeH if sig == Signal::SIGTTIN { 57*52da9a59SGnoCiYeH return Err(SystemError::EIO); 58*52da9a59SGnoCiYeH } 59*52da9a59SGnoCiYeH } else { 60*52da9a59SGnoCiYeH // 暂时使用kill而不是killpg 61*52da9a59SGnoCiYeH Syscall::kill(pgid, sig as i32)?; 62*52da9a59SGnoCiYeH return Err(SystemError::ERESTART); 63*52da9a59SGnoCiYeH } 64*52da9a59SGnoCiYeH } 65*52da9a59SGnoCiYeH 66*52da9a59SGnoCiYeH Ok(()) 67*52da9a59SGnoCiYeH } 68*52da9a59SGnoCiYeH 69*52da9a59SGnoCiYeH pub fn job_ctrl_ioctl(tty: Arc<TtyCore>, cmd: u32, arg: usize) -> Result<usize, SystemError> { 70*52da9a59SGnoCiYeH match cmd { 71*52da9a59SGnoCiYeH TtyIoctlCmd::TIOCSPGRP => { 72*52da9a59SGnoCiYeH match Self::tty_check_change(tty.clone(), Signal::SIGTTOU) { 73*52da9a59SGnoCiYeH Ok(_) => {} 74*52da9a59SGnoCiYeH Err(e) => { 75*52da9a59SGnoCiYeH if e == SystemError::EIO { 76*52da9a59SGnoCiYeH return Err(SystemError::ENOTTY); 77*52da9a59SGnoCiYeH } 78*52da9a59SGnoCiYeH return Err(e); 79*52da9a59SGnoCiYeH } 80*52da9a59SGnoCiYeH }; 81*52da9a59SGnoCiYeH 82*52da9a59SGnoCiYeH // let user_reader = UserBufferReader::new( 83*52da9a59SGnoCiYeH // VirtAddr::new(arg).as_ptr::<usize>(), 84*52da9a59SGnoCiYeH // core::mem::size_of::<usize>(), 85*52da9a59SGnoCiYeH // true, 86*52da9a59SGnoCiYeH // )?; 87*52da9a59SGnoCiYeH 88*52da9a59SGnoCiYeH // let pgrp = user_reader.read_one_from_user::<usize>(0)?; 89*52da9a59SGnoCiYeH 90*52da9a59SGnoCiYeH let current = ProcessManager::current_pcb(); 91*52da9a59SGnoCiYeH 92*52da9a59SGnoCiYeH let mut ctrl = tty.core().contorl_info_irqsave(); 93*52da9a59SGnoCiYeH 94*52da9a59SGnoCiYeH if current.sig_info().tty().is_none() 95*52da9a59SGnoCiYeH || !Arc::ptr_eq(¤t.sig_info().tty().clone().unwrap(), &tty) 96*52da9a59SGnoCiYeH || ctrl.session.is_none() 97*52da9a59SGnoCiYeH || ctrl.session.unwrap() != current.pid() 98*52da9a59SGnoCiYeH { 99*52da9a59SGnoCiYeH return Err(SystemError::ENOTTY); 100*52da9a59SGnoCiYeH } 101*52da9a59SGnoCiYeH 102*52da9a59SGnoCiYeH ctrl.pgid = Some(Pid::new(arg)); 103*52da9a59SGnoCiYeH 104*52da9a59SGnoCiYeH return Ok(0); 105*52da9a59SGnoCiYeH } 106*52da9a59SGnoCiYeH 107*52da9a59SGnoCiYeH TtyIoctlCmd::TIOCGPGRP => { 108*52da9a59SGnoCiYeH let current = ProcessManager::current_pcb(); 109*52da9a59SGnoCiYeH if current.sig_info().tty().is_some() 110*52da9a59SGnoCiYeH && !Arc::ptr_eq(¤t.sig_info().tty().unwrap(), &tty) 111*52da9a59SGnoCiYeH { 112*52da9a59SGnoCiYeH return Err(SystemError::ENOTTY); 113*52da9a59SGnoCiYeH } 114*52da9a59SGnoCiYeH 115*52da9a59SGnoCiYeH let mut user_writer = UserBufferWriter::new( 116*52da9a59SGnoCiYeH VirtAddr::new(arg).as_ptr::<i32>(), 117*52da9a59SGnoCiYeH core::mem::size_of::<i32>(), 118*52da9a59SGnoCiYeH true, 119*52da9a59SGnoCiYeH )?; 120*52da9a59SGnoCiYeH 121*52da9a59SGnoCiYeH user_writer.copy_one_to_user( 122*52da9a59SGnoCiYeH &(tty 123*52da9a59SGnoCiYeH .core() 124*52da9a59SGnoCiYeH .contorl_info_irqsave() 125*52da9a59SGnoCiYeH .pgid 126*52da9a59SGnoCiYeH .unwrap_or(Pid::new(0)) 127*52da9a59SGnoCiYeH .data() as i32), 128*52da9a59SGnoCiYeH 0, 129*52da9a59SGnoCiYeH )?; 130*52da9a59SGnoCiYeH 131*52da9a59SGnoCiYeH return Ok(0); 132*52da9a59SGnoCiYeH } 133*52da9a59SGnoCiYeH 134*52da9a59SGnoCiYeH _ => { 135*52da9a59SGnoCiYeH return Err(SystemError::ENOIOCTLCMD); 136*52da9a59SGnoCiYeH } 137*52da9a59SGnoCiYeH } 138*52da9a59SGnoCiYeH } 139*52da9a59SGnoCiYeH } 140