10d9b7d92SLoGin use num_traits::FromPrimitive; 291e9d4abSLoGin use system_error::SystemError; 30d9b7d92SLoGin 4*6fc066acSJomo use crate::time::PosixTimeSpec; 5be8cdf4bSLoGin 6be8cdf4bSLoGin use super::ProcessControlBlock; 7be8cdf4bSLoGin 8be8cdf4bSLoGin #[derive(Debug, Clone, Copy, PartialEq, Eq, Default)] 9be8cdf4bSLoGin #[repr(C)] 10be8cdf4bSLoGin pub struct RUsage { 11be8cdf4bSLoGin /// User time used 12*6fc066acSJomo pub ru_utime: PosixTimeSpec, 13be8cdf4bSLoGin /// System time used 14*6fc066acSJomo pub ru_stime: PosixTimeSpec, 15be8cdf4bSLoGin 16be8cdf4bSLoGin // 以下是linux的rusage结构体扩展 17be8cdf4bSLoGin /// Maximum resident set size 18be8cdf4bSLoGin pub ru_maxrss: usize, 19be8cdf4bSLoGin /// Integral shared memory size 20be8cdf4bSLoGin pub ru_ixrss: usize, 21be8cdf4bSLoGin /// Integral unshared data size 22be8cdf4bSLoGin pub ru_idrss: usize, 23be8cdf4bSLoGin /// Integral unshared stack size 24be8cdf4bSLoGin pub ru_isrss: usize, 25be8cdf4bSLoGin /// Page reclaims (soft page faults) 26be8cdf4bSLoGin pub ru_minflt: usize, 27be8cdf4bSLoGin /// Page faults (hard page faults) 28be8cdf4bSLoGin pub ru_majflt: usize, 29be8cdf4bSLoGin /// Swaps 30be8cdf4bSLoGin pub ru_nswap: usize, 31be8cdf4bSLoGin /// Block input operations 32be8cdf4bSLoGin pub ru_inblock: usize, 33be8cdf4bSLoGin /// Block output operations 34be8cdf4bSLoGin pub ru_oublock: usize, 35be8cdf4bSLoGin /// IPC messages sent 36be8cdf4bSLoGin pub ru_msgsnd: usize, 37be8cdf4bSLoGin /// IPC messages received 38be8cdf4bSLoGin pub ru_msgrcv: usize, 39be8cdf4bSLoGin /// Signals received 40be8cdf4bSLoGin pub ru_nsignals: usize, 41be8cdf4bSLoGin /// Voluntary context switches 42be8cdf4bSLoGin pub ru_nvcsw: usize, 43be8cdf4bSLoGin /// Involuntary context switches 44be8cdf4bSLoGin pub ru_nivcsw: usize, 45be8cdf4bSLoGin } 46be8cdf4bSLoGin 47be8cdf4bSLoGin /// 48be8cdf4bSLoGin /// Definition of struct rusage taken from BSD 4.3 Reno 49be8cdf4bSLoGin /// 50be8cdf4bSLoGin /// We don't support all of these yet, but we might as well have them.... 51be8cdf4bSLoGin /// Otherwise, each time we add new items, programs which depend on this 52be8cdf4bSLoGin /// structure will lose. This reduces the chances of that happening. 53be8cdf4bSLoGin #[derive(Debug, Clone, Copy, PartialEq, Eq)] 54be8cdf4bSLoGin pub enum RUsageWho { 55be8cdf4bSLoGin RUsageSelf = 0, 56be8cdf4bSLoGin RUsageChildren = -1, 57be8cdf4bSLoGin /// sys_wait4() uses this 58be8cdf4bSLoGin RUsageBoth = -2, 59be8cdf4bSLoGin /// only the calling thread 60be8cdf4bSLoGin RusageThread = 1, 61be8cdf4bSLoGin } 62be8cdf4bSLoGin 63be8cdf4bSLoGin impl TryFrom<i32> for RUsageWho { 64be8cdf4bSLoGin type Error = SystemError; 65be8cdf4bSLoGin try_from(value: i32) -> Result<Self, Self::Error>66be8cdf4bSLoGin fn try_from(value: i32) -> Result<Self, Self::Error> { 67be8cdf4bSLoGin match value { 68be8cdf4bSLoGin 0 => Ok(RUsageWho::RUsageSelf), 69be8cdf4bSLoGin -1 => Ok(RUsageWho::RUsageChildren), 70be8cdf4bSLoGin -2 => Ok(RUsageWho::RUsageBoth), 71be8cdf4bSLoGin 1 => Ok(RUsageWho::RusageThread), 72be8cdf4bSLoGin _ => Err(SystemError::EINVAL), 73be8cdf4bSLoGin } 74be8cdf4bSLoGin } 75be8cdf4bSLoGin } 76be8cdf4bSLoGin 770d9b7d92SLoGin /// Resource limit 780d9b7d92SLoGin #[derive(Debug, Clone, Copy, PartialEq, Eq)] 790d9b7d92SLoGin #[repr(C)] 800d9b7d92SLoGin pub struct RLimit64 { 810d9b7d92SLoGin /// The current (soft) limit 820d9b7d92SLoGin pub rlim_cur: u64, 830d9b7d92SLoGin /// The hard limit 840d9b7d92SLoGin pub rlim_max: u64, 850d9b7d92SLoGin } 860d9b7d92SLoGin 870d9b7d92SLoGin /// Resource limit IDs 880d9b7d92SLoGin /// 890d9b7d92SLoGin /// ## Note 900d9b7d92SLoGin /// 910d9b7d92SLoGin /// 有些架构中,这里[5,9]的值是不同的,我们将来需要在这里增加条件编译 920d9b7d92SLoGin #[derive(Debug, Clone, Copy, PartialEq, Eq, FromPrimitive)] 930d9b7d92SLoGin pub enum RLimitID { 940d9b7d92SLoGin /// CPU time in sec 950d9b7d92SLoGin Cpu = 0, 960d9b7d92SLoGin /// Maximum file size 970d9b7d92SLoGin Fsize = 1, 980d9b7d92SLoGin /// Max data size 990d9b7d92SLoGin Data = 2, 1000d9b7d92SLoGin /// Max stack size 1010d9b7d92SLoGin Stack = 3, 1020d9b7d92SLoGin /// Max core file size 1030d9b7d92SLoGin Core = 4, 1040d9b7d92SLoGin /// Max resident set size 1050d9b7d92SLoGin Rss = 5, 1060d9b7d92SLoGin 1070d9b7d92SLoGin /// Max number of processes 1080d9b7d92SLoGin Nproc = 6, 1090d9b7d92SLoGin /// Max number of open files 1100d9b7d92SLoGin Nofile = 7, 1110d9b7d92SLoGin /// Max locked-in-memory address space 1120d9b7d92SLoGin Memlock = 8, 1130d9b7d92SLoGin /// Address space limit 1140d9b7d92SLoGin As = 9, 1150d9b7d92SLoGin /// Max number of file locks held 1160d9b7d92SLoGin Locks = 10, 1170d9b7d92SLoGin 1180d9b7d92SLoGin /// Max number of pending signals 1190d9b7d92SLoGin Sigpending = 11, 1200d9b7d92SLoGin /// Max bytes in POSIX mqueues 1210d9b7d92SLoGin Msgqueue = 12, 1220d9b7d92SLoGin /// Max nice prio allowed to raise to 1230d9b7d92SLoGin /// 0-39 for nice level 19 .. -20 1240d9b7d92SLoGin Nice = 13, 1250d9b7d92SLoGin /// Max realtime priority 1260d9b7d92SLoGin Rtprio = 14, 1270d9b7d92SLoGin /// Timeout for RT tasks in us 1280d9b7d92SLoGin Rttime = 15, 1290d9b7d92SLoGin Nlimits = 16, 1300d9b7d92SLoGin } 1310d9b7d92SLoGin 1320d9b7d92SLoGin impl TryFrom<usize> for RLimitID { 1330d9b7d92SLoGin type Error = SystemError; 1340d9b7d92SLoGin try_from(value: usize) -> Result<Self, Self::Error>1350d9b7d92SLoGin fn try_from(value: usize) -> Result<Self, Self::Error> { 1360d9b7d92SLoGin <Self as FromPrimitive>::from_usize(value).ok_or(SystemError::EINVAL) 1370d9b7d92SLoGin } 1380d9b7d92SLoGin } 1390d9b7d92SLoGin 140be8cdf4bSLoGin impl ProcessControlBlock { 141be8cdf4bSLoGin /// 获取进程资源使用情况 142be8cdf4bSLoGin /// 143be8cdf4bSLoGin /// ## TODO 144be8cdf4bSLoGin /// 145be8cdf4bSLoGin /// 当前函数尚未实现,只是返回了一个默认的RUsage结构体 get_rusage(&self, _who: RUsageWho) -> Option<RUsage>146be8cdf4bSLoGin pub fn get_rusage(&self, _who: RUsageWho) -> Option<RUsage> { 147be8cdf4bSLoGin let rusage = RUsage::default(); 148be8cdf4bSLoGin 149be8cdf4bSLoGin Some(rusage) 150be8cdf4bSLoGin } 151be8cdf4bSLoGin } 152