1 use core::ops::{Deref, DerefMut}; 2 3 use super::{ 4 device::device_number::{DeviceNumber, Major}, 5 kobject::KObject, 6 }; 7 use crate::libs::spinlock::{SpinLock, SpinLockGuard}; 8 use alloc::{collections::BTreeMap, sync::Arc, vec::Vec}; 9 10 const KOBJMAP_HASH_SIZE: usize = 255; 11 pub(crate) const DEV_MAJOR_HASH_SIZE: u32 = 255; 12 pub(crate) const DEV_MAJOR_MAX: Major = Major::new(512); 13 14 /* Marks the bottom of the first segment of free char majors */ 15 pub(crate) const DEV_MAJOR_DYN_END: Major = Major::new(234); 16 /* Marks the top and bottom of the second segment of free char majors */ 17 pub(crate) const DEV_MAJOR_DYN_EXT_START: Major = Major::new(511); 18 pub(crate) const DEV_MAJOR_DYN_EXT_END: Major = Major::new(384); 19 20 /// @brief: 字符设备与块设备管理结构体 21 #[derive(Debug, Clone)] 22 struct Probe(Arc<dyn KObject>); 23 24 impl Probe { 25 /// @brief: 新建probe实例 26 /// @parameter: data: probe实例 27 /// @return: probe实例 28 pub fn new(data: Arc<dyn KObject>) -> Self { 29 Self(data) 30 } 31 } 32 33 /// @brief: 字符设备和块设备管理实例(锁) 34 #[derive(Debug)] 35 pub struct LockedKObjMap(SpinLock<KObjMap>); 36 37 impl Default for LockedKObjMap { 38 fn default() -> Self { 39 Self(SpinLock::new(KObjMap::default())) 40 } 41 } 42 43 /// @brief: 字符设备和块设备管理实例 44 #[derive(Debug, Clone)] 45 struct KObjMap(Vec<BTreeMap<DeviceNumber, Probe>>); 46 47 impl Default for KObjMap { 48 fn default() -> Self { 49 Self(vec![BTreeMap::new(); KOBJMAP_HASH_SIZE]) 50 } 51 } 52 53 /// @brief: obj设备注册 54 /// @parameter: domain: 管理实例 55 /// dev_t: 设备号 56 /// range: 次设备号范围 57 /// data: 设备实例 58 /// @return: none 59 pub fn kobj_map( 60 domain: Arc<LockedKObjMap>, 61 dev_t: DeviceNumber, 62 range: usize, 63 data: Arc<dyn KObject>, 64 ) { 65 if let Some(map) = domain 66 .0 67 .lock() 68 .0 69 .get_mut((dev_t.major().data() % 255) as usize) 70 { 71 for i in 0..range { 72 map.insert( 73 DeviceNumber::new(dev_t.major(), dev_t.minor() + i as u32), 74 Probe::new(data.clone()), 75 ); 76 } 77 } 78 } 79 80 /// @brief: obj设备注销 81 /// @parameter: domain: 管理实例 82 /// dev_t: 设备号 83 /// range: 次设备号范围 84 /// @return: none 85 pub fn kobj_unmap(domain: Arc<LockedKObjMap>, dev_t: DeviceNumber, range: usize) { 86 if let Some(map) = domain 87 .0 88 .lock() 89 .0 90 .get_mut((dev_t.major().data() % 255) as usize) 91 { 92 for i in 0..range { 93 let rm_dev_t = &DeviceNumber::new(dev_t.major(), dev_t.minor() + i as u32); 94 match map.get(rm_dev_t) { 95 Some(_) => { 96 map.remove(rm_dev_t); 97 } 98 None => {} 99 } 100 } 101 } 102 } 103 104 /// @brief: 设备查找 105 /// @parameter: domain: 管理实例 106 /// dev_t: 设备号 107 /// @return: 查找成功,返回设备实例,否则返回None 108 #[allow(dead_code)] 109 pub fn kobj_lookup(domain: Arc<LockedKObjMap>, dev_t: DeviceNumber) -> Option<Arc<dyn KObject>> { 110 if let Some(map) = domain.0.lock().0.get((dev_t.major().data() % 255) as usize) { 111 match map.get(&dev_t) { 112 Some(value) => { 113 return Some(value.0.clone()); 114 } 115 None => { 116 return None; 117 } 118 } 119 } 120 return None; 121 } 122 123 // 管理字符设备号的map(加锁) 124 pub struct LockedDevsMap(SpinLock<DevsMap>); 125 126 impl Default for LockedDevsMap { 127 fn default() -> Self { 128 LockedDevsMap(SpinLock::new(DevsMap::default())) 129 } 130 } 131 132 impl LockedDevsMap { 133 #[inline(always)] 134 pub fn lock(&self) -> SpinLockGuard<DevsMap> { 135 self.0.lock() 136 } 137 } 138 139 // 管理字符设备号的map 140 #[derive(Debug)] 141 pub struct DevsMap(Vec<Vec<DeviceStruct>>); 142 143 impl Default for DevsMap { 144 fn default() -> Self { 145 DevsMap(vec![Vec::new(); DEV_MAJOR_HASH_SIZE as usize]) 146 } 147 } 148 149 impl Deref for DevsMap { 150 type Target = Vec<Vec<DeviceStruct>>; 151 152 fn deref(&self) -> &Self::Target { 153 &self.0 154 } 155 } 156 157 impl DerefMut for DevsMap { 158 fn deref_mut(&mut self) -> &mut Self::Target { 159 &mut self.0 160 } 161 } 162 163 // 字符设备在系统中的实例,devfs通过该结构与实际字符设备进行联系 164 #[allow(dead_code)] 165 #[derive(Debug, Clone)] 166 pub struct DeviceStruct { 167 dev_t: DeviceNumber, //起始设备号 168 minorct: u32, // 次设备号数量 169 name: &'static str, //字符设备名 170 } 171 172 impl DeviceStruct { 173 /// @brief: 创建实例 174 /// @parameter: dev_t: 设备号 175 /// minorct: 次设备号数量 176 /// name: 字符设备名 177 /// char: 字符设备实例 178 /// @return: 实例 179 /// 180 #[allow(dead_code)] 181 pub fn new(dev_t: DeviceNumber, minorct: u32, name: &'static str) -> Self { 182 Self { 183 dev_t, 184 minorct, 185 name, 186 } 187 } 188 189 /// @brief: 获取起始次设备号 190 /// @parameter: None 191 /// @return: 起始设备号 192 /// 193 #[allow(dead_code)] 194 pub fn device_number(&self) -> DeviceNumber { 195 self.dev_t 196 } 197 198 /// @brief: 获取起始次设备号 199 /// @parameter: None 200 /// @return: 起始设备号 201 /// 202 #[allow(dead_code)] 203 pub fn base_minor(&self) -> u32 { 204 self.dev_t.minor() 205 } 206 207 /// @brief: 获取次设备号数量 208 /// @parameter: None 209 /// @return: 次设备号数量 210 #[allow(dead_code)] 211 pub fn minorct(&self) -> u32 { 212 self.minorct 213 } 214 } 215