1b087521eSChiichen /// 引入Module 2ae5ede03SLoGin use crate::{ 3*eb49bb99S曾俊 driver::{ 4*eb49bb99S曾俊 base::{ 5c566df45SLoGin device::{ 6c566df45SLoGin device_number::{DeviceNumber, Major}, 7c566df45SLoGin Device, DeviceError, IdTable, BLOCKDEVS, 8c566df45SLoGin }, 9ae5ede03SLoGin map::{ 10ae5ede03SLoGin DeviceStruct, DEV_MAJOR_DYN_END, DEV_MAJOR_DYN_EXT_END, DEV_MAJOR_DYN_EXT_START, 11c566df45SLoGin DEV_MAJOR_HASH_SIZE, DEV_MAJOR_MAX, 12ae5ede03SLoGin }, 13ae5ede03SLoGin }, 14*eb49bb99S曾俊 block::cache::{cached_block_device::BlockCache, BlockCacheError, BLOCK_SIZE}, 15*eb49bb99S曾俊 }, 16ae5ede03SLoGin kerror, 17ae5ede03SLoGin }; 1891e9d4abSLoGin 19b087521eSChiichen use alloc::{sync::Arc, vec::Vec}; 20b087521eSChiichen use core::any::Any; 2191e9d4abSLoGin use system_error::SystemError; 22b087521eSChiichen 23b087521eSChiichen use super::disk_info::Partition; 24b087521eSChiichen 25b087521eSChiichen /// 该文件定义了 Device 和 BlockDevice 的接口 26b087521eSChiichen /// Notice 设备错误码使用 Posix 规定的 int32_t 的错误码表示,而不是自己定义错误enum 27b087521eSChiichen 28b087521eSChiichen // 使用方法: 29b087521eSChiichen // 假设 blk_dev 是块设备 30b087521eSChiichen // <blk_dev as Device>::read_at() 调用的是Device的函数 31b087521eSChiichen // <blk_dev as BlockDevice>::read_at() 调用的是BlockDevice的函数 32b087521eSChiichen 33b087521eSChiichen /// 定义类型 34b087521eSChiichen pub type BlockId = usize; 35b087521eSChiichen 36b087521eSChiichen /// 定义常量 37b087521eSChiichen pub const BLK_SIZE_LOG2_LIMIT: u8 = 12; // 设定块设备的块大小不能超过 1 << 12. 38b087521eSChiichen /// 在DragonOS中,我们认为磁盘的每个LBA大小均为512字节。(注意,文件系统的1个扇区可能事实上是多个LBA) 39b087521eSChiichen pub const LBA_SIZE: usize = 512; 40b087521eSChiichen 41b087521eSChiichen /// @brief 块设备的迭代器 42b087521eSChiichen /// @usage 某次操作读/写块设备的[L,R]范围内的字节, 43b087521eSChiichen /// 那么可以使用此结构体进行迭代遍历,每次调用next()返回一个BlockRange 44b087521eSChiichen pub struct BlockIter { 45b087521eSChiichen pub begin: usize, // 迭代器的起始位置 -> 块设备的地址 (单位是字节) 46b087521eSChiichen pub end: usize, 47b087521eSChiichen pub blk_size_log2: u8, 48b087521eSChiichen pub multiblock: bool, // 是否启用连续整块同时遍历 49b087521eSChiichen } 50b087521eSChiichen 51b087521eSChiichen /// @brief Range搭配迭代器BlockIter使用,[L,R]区间被分割成多个小的Range 52b087521eSChiichen /// Range要么是整块,要么是一块的某一部分 53b087521eSChiichen /// 细节: range = [begin, end) 左闭右开 54b087521eSChiichen pub struct BlockRange { 55b087521eSChiichen pub lba_start: usize, // 起始块的lba_id 56b087521eSChiichen pub lba_end: usize, // 终止块的lba_id 57b087521eSChiichen pub begin: usize, // 起始位置在块内的偏移量, 如果BlockIter启用Multiblock,则是多个块的偏移量 58b087521eSChiichen pub end: usize, // 结束位置在块内的偏移量,单位是字节 59b087521eSChiichen pub blk_size_log2: u8, 60b087521eSChiichen } 61b087521eSChiichen 62b087521eSChiichen impl BlockIter { 63b087521eSChiichen #[allow(dead_code)] 64b087521eSChiichen pub fn new(start_addr: usize, end_addr: usize, blk_size_log2: u8) -> BlockIter { 65b087521eSChiichen return BlockIter { 66b087521eSChiichen begin: start_addr, 67b087521eSChiichen end: end_addr, 68b5b571e0SLoGin blk_size_log2, 69b087521eSChiichen multiblock: false, 70b087521eSChiichen }; 71b087521eSChiichen } 72b087521eSChiichen pub fn new_multiblock(start_addr: usize, end_addr: usize, blk_size_log2: u8) -> BlockIter { 73b087521eSChiichen return BlockIter { 74b087521eSChiichen begin: start_addr, 75b087521eSChiichen end: end_addr, 76b5b571e0SLoGin 77b5b571e0SLoGin blk_size_log2, 78b087521eSChiichen multiblock: true, 79b087521eSChiichen }; 80b087521eSChiichen } 81b087521eSChiichen 82b087521eSChiichen /// 获取下一个整块或者不完整的块 83b087521eSChiichen pub fn next_block(&mut self) -> BlockRange { 84b087521eSChiichen let blk_size_log2 = self.blk_size_log2; 85b087521eSChiichen let blk_size = 1usize << self.blk_size_log2; 86b087521eSChiichen let lba_id = self.begin / blk_size; 87b087521eSChiichen let begin = self.begin % blk_size; 88b087521eSChiichen let end = if lba_id == self.end / blk_size { 89b087521eSChiichen self.end % blk_size 90b087521eSChiichen } else { 91b087521eSChiichen blk_size 92b087521eSChiichen }; 93b087521eSChiichen 94b087521eSChiichen self.begin += end - begin; 95b087521eSChiichen 96b087521eSChiichen return BlockRange { 97b087521eSChiichen lba_start: lba_id, 98b087521eSChiichen lba_end: lba_id + 1, 99b5b571e0SLoGin begin, 100b5b571e0SLoGin end, 101b5b571e0SLoGin blk_size_log2, 102b087521eSChiichen }; 103b087521eSChiichen } 104b087521eSChiichen 105b087521eSChiichen /// 如果能返回多个连续的整块,则返回;否则调用next_block()返回不完整的块 106b087521eSChiichen pub fn next_multiblock(&mut self) -> BlockRange { 107b087521eSChiichen let blk_size_log2 = self.blk_size_log2; 108b087521eSChiichen let blk_size = 1usize << self.blk_size_log2; 109b087521eSChiichen let lba_start = self.begin / blk_size; 110b087521eSChiichen let lba_end = self.end / blk_size; 111b087521eSChiichen 112b087521eSChiichen // 如果不是整块,先返回非整块的小部分 113b087521eSChiichen if __bytes_to_lba(self.begin, blk_size) 114b087521eSChiichen != __bytes_to_lba(self.begin + blk_size - 1, blk_size) 115b087521eSChiichen || lba_start == lba_end 116b087521eSChiichen { 117b087521eSChiichen return self.next_block(); 118b087521eSChiichen } 119b087521eSChiichen 120b087521eSChiichen let begin = self.begin % blk_size; // 因为是多个整块,这里必然是0 121b087521eSChiichen let end = __lba_to_bytes(lba_end, blk_size) - self.begin; 122b087521eSChiichen 123b087521eSChiichen self.begin += end - begin; 124b087521eSChiichen 125b087521eSChiichen return BlockRange { 126b5b571e0SLoGin lba_start, 127b5b571e0SLoGin lba_end, 128b5b571e0SLoGin begin, 129b5b571e0SLoGin end, 130b5b571e0SLoGin blk_size_log2, 131b087521eSChiichen }; 132b087521eSChiichen } 133b087521eSChiichen } 134b087521eSChiichen 135b087521eSChiichen /// BlockIter 函数实现 136b087521eSChiichen impl Iterator for BlockIter { 137b087521eSChiichen type Item = BlockRange; 138b087521eSChiichen 139b087521eSChiichen fn next(&mut self) -> Option<<Self as Iterator>::Item> { 140b087521eSChiichen if self.begin >= self.end { 141b087521eSChiichen return None; 142b087521eSChiichen } 143b087521eSChiichen if self.multiblock { 144b087521eSChiichen return Some(self.next_multiblock()); 145b087521eSChiichen } else { 146b087521eSChiichen return Some(self.next_block()); 147b087521eSChiichen } 148b087521eSChiichen } 149b087521eSChiichen } 150b087521eSChiichen 151b087521eSChiichen /// BlockRange 函数实现 152b087521eSChiichen impl BlockRange { 153b087521eSChiichen #[allow(dead_code)] 154b087521eSChiichen pub fn is_empty(&self) -> bool { 155b087521eSChiichen return self.end == self.begin; 156b087521eSChiichen } 157b087521eSChiichen pub fn len(&self) -> usize { 158b087521eSChiichen return self.end - self.begin; 159b087521eSChiichen } 160b087521eSChiichen /// 判断是不是整块 161b087521eSChiichen pub fn is_full(&self) -> bool { 162b087521eSChiichen return self.len() == (1usize << self.blk_size_log2); 163b087521eSChiichen } 164b087521eSChiichen /// 判断是不是多个整块连在一起 165b087521eSChiichen pub fn is_multi(&self) -> bool { 166b087521eSChiichen return self.len() >= (1usize << self.blk_size_log2) 167b087521eSChiichen && (self.len() % (1usize << self.blk_size_log2) == 0); 168b087521eSChiichen } 169b087521eSChiichen /// 获取 BlockRange 在块设备内部的起始位置 (单位是字节) 170b087521eSChiichen pub fn origin_begin(&self) -> usize { 171b087521eSChiichen return (self.lba_start << self.blk_size_log2) + self.begin; 172b087521eSChiichen } 173b087521eSChiichen /// 获取 BlockRange 在块设备内部的结尾位置 (单位是字节) 174b087521eSChiichen pub fn origin_end(&self) -> usize { 175b087521eSChiichen return (self.lba_start << self.blk_size_log2) + self.end; 176b087521eSChiichen } 177b087521eSChiichen } 178b087521eSChiichen 179b087521eSChiichen /// 从字节地址转换到lba id 180b087521eSChiichen #[inline] 181b087521eSChiichen pub fn __bytes_to_lba(addr: usize, blk_size: usize) -> BlockId { 182b087521eSChiichen return addr / blk_size; 183b087521eSChiichen } 184b087521eSChiichen 185b087521eSChiichen /// 从lba id转换到字节地址, 返回lba_id的最左侧字节 186b087521eSChiichen #[inline] 187b087521eSChiichen pub fn __lba_to_bytes(lba_id: usize, blk_size: usize) -> BlockId { 188b087521eSChiichen return lba_id * blk_size; 189b087521eSChiichen } 190b087521eSChiichen 191b087521eSChiichen /// @brief 块设备应该实现的操作 192b087521eSChiichen pub trait BlockDevice: Device { 193b087521eSChiichen /// @brief: 在块设备中,从第lba_id_start个块开始,读取count个块数据,存放到buf中 194b087521eSChiichen /// 195b087521eSChiichen /// @parameter lba_id_start: 起始块 196b087521eSChiichen /// @parameter count: 读取块的数量 197b087521eSChiichen /// @parameter buf: 目标数组 198b087521eSChiichen /// @return: 如果操作成功,返回 Ok(操作的长度) 其中单位是字节; 199b087521eSChiichen /// 否则返回Err(错误码),其中错误码为负数; 200b087521eSChiichen /// 如果操作异常,但是并没有检查出什么错误,将返回Err(已操作的长度) 201*eb49bb99S曾俊 fn read_at_sync( 202b087521eSChiichen &self, 203b087521eSChiichen lba_id_start: BlockId, 204b087521eSChiichen count: usize, 205b087521eSChiichen buf: &mut [u8], 206b087521eSChiichen ) -> Result<usize, SystemError>; 207b087521eSChiichen 208b087521eSChiichen /// @brief: 在块设备中,从第lba_id_start个块开始,把buf中的count个块数据,存放到设备中 209b087521eSChiichen /// @parameter lba_id_start: 起始块 210b087521eSChiichen /// @parameter count: 写入块的数量 211b087521eSChiichen /// @parameter buf: 目标数组 212b087521eSChiichen /// @return: 如果操作成功,返回 Ok(操作的长度) 其中单位是字节; 213b087521eSChiichen /// 否则返回Err(错误码),其中错误码为负数; 214b087521eSChiichen /// 如果操作异常,但是并没有检查出什么错误,将返回Err(已操作的长度) 215*eb49bb99S曾俊 fn write_at_sync( 216b087521eSChiichen &self, 217b087521eSChiichen lba_id_start: BlockId, 218b087521eSChiichen count: usize, 219b087521eSChiichen buf: &[u8], 220b087521eSChiichen ) -> Result<usize, SystemError>; 221b087521eSChiichen 222b087521eSChiichen /// @brief: 同步磁盘信息,把所有的dirty数据写回硬盘 - 待实现 223b087521eSChiichen fn sync(&self) -> Result<(), SystemError>; 224b087521eSChiichen 225b087521eSChiichen /// @brief: 每个块设备都必须固定自己块大小,而且该块大小必须是2的幂次 226b087521eSChiichen /// @return: 返回一个固定量,硬编码(编程的时候固定的常量). 227b087521eSChiichen fn blk_size_log2(&self) -> u8; 228b087521eSChiichen 229b087521eSChiichen // TODO: 待实现 open, close 230b087521eSChiichen 231b087521eSChiichen /// @brief 本函数用于实现动态转换。 232b087521eSChiichen /// 具体的文件系统在实现本函数时,最简单的方式就是:直接返回self 233b087521eSChiichen fn as_any_ref(&self) -> &dyn Any; 234b087521eSChiichen 235b087521eSChiichen /// @brief 本函数用于将BlockDevice转换为Device。 236b087521eSChiichen /// 由于实现了BlockDevice的结构体,本身也实现了Device Trait, 因此转换是可能的。 237b087521eSChiichen /// 思路:在BlockDevice的结构体中新增一个self_ref变量,返回self_ref.upgrade()即可。 238b087521eSChiichen fn device(&self) -> Arc<dyn Device>; 239b087521eSChiichen 240b087521eSChiichen /// @brief 返回块设备的块大小(单位:字节) 241b087521eSChiichen fn block_size(&self) -> usize; 242b087521eSChiichen 243b087521eSChiichen /// @brief 返回当前磁盘上的所有分区的Arc指针数组 244b087521eSChiichen fn partitions(&self) -> Vec<Arc<Partition>>; 245b087521eSChiichen 246*eb49bb99S曾俊 /// # 函数的功能 247*eb49bb99S曾俊 /// 经由Cache对块设备的读操作 248*eb49bb99S曾俊 fn read_at( 249*eb49bb99S曾俊 &self, 250*eb49bb99S曾俊 lba_id_start: BlockId, 251*eb49bb99S曾俊 count: usize, 252*eb49bb99S曾俊 buf: &mut [u8], 253*eb49bb99S曾俊 ) -> Result<usize, SystemError> { 254*eb49bb99S曾俊 self.cache_read(lba_id_start, count, buf) 255*eb49bb99S曾俊 } 256*eb49bb99S曾俊 257*eb49bb99S曾俊 /// # 函数的功能 258*eb49bb99S曾俊 /// 经由Cache对块设备的写操作 259*eb49bb99S曾俊 fn write_at( 260*eb49bb99S曾俊 &self, 261*eb49bb99S曾俊 lba_id_start: BlockId, 262*eb49bb99S曾俊 count: usize, 263*eb49bb99S曾俊 buf: &[u8], 264*eb49bb99S曾俊 ) -> Result<usize, SystemError> { 265*eb49bb99S曾俊 self.cache_write(lba_id_start, count, buf) 266*eb49bb99S曾俊 } 267*eb49bb99S曾俊 268*eb49bb99S曾俊 /// # 函数的功能 269*eb49bb99S曾俊 /// 其功能对外而言和read_at函数完全一致,但是加入blockcache的功能 270*eb49bb99S曾俊 fn cache_read( 271*eb49bb99S曾俊 &self, 272*eb49bb99S曾俊 lba_id_start: BlockId, 273*eb49bb99S曾俊 count: usize, 274*eb49bb99S曾俊 buf: &mut [u8], 275*eb49bb99S曾俊 ) -> Result<usize, SystemError> { 276*eb49bb99S曾俊 let cache_response = BlockCache::read(lba_id_start, count, buf); 277*eb49bb99S曾俊 if let Err(e) = cache_response { 278*eb49bb99S曾俊 match e { 279*eb49bb99S曾俊 BlockCacheError::StaticParameterError => { 280*eb49bb99S曾俊 BlockCache::init(); 281*eb49bb99S曾俊 let ans = self.read_at_sync(lba_id_start, count, buf)?; 282*eb49bb99S曾俊 return Ok(ans); 283*eb49bb99S曾俊 } 284*eb49bb99S曾俊 BlockCacheError::BlockFaultError(fail_vec) => { 285*eb49bb99S曾俊 let ans = self.read_at_sync(lba_id_start, count, buf)?; 286*eb49bb99S曾俊 let _ = BlockCache::insert(fail_vec, buf); 287*eb49bb99S曾俊 return Ok(ans); 288*eb49bb99S曾俊 } 289*eb49bb99S曾俊 _ => { 290*eb49bb99S曾俊 let ans = self.read_at_sync(lba_id_start, count, buf)?; 291*eb49bb99S曾俊 return Ok(ans); 292*eb49bb99S曾俊 } 293*eb49bb99S曾俊 } 294*eb49bb99S曾俊 } else { 295*eb49bb99S曾俊 return Ok(count * BLOCK_SIZE); 296*eb49bb99S曾俊 } 297*eb49bb99S曾俊 } 298*eb49bb99S曾俊 299*eb49bb99S曾俊 /// # 函数功能 300*eb49bb99S曾俊 /// 其功能对外而言和write_at函数完全一致,但是加入blockcache的功能 301*eb49bb99S曾俊 fn cache_write( 302*eb49bb99S曾俊 &self, 303*eb49bb99S曾俊 lba_id_start: BlockId, 304*eb49bb99S曾俊 count: usize, 305*eb49bb99S曾俊 buf: &[u8], 306*eb49bb99S曾俊 ) -> Result<usize, SystemError> { 307*eb49bb99S曾俊 let _cache_response = BlockCache::immediate_write(lba_id_start, count, buf); 308*eb49bb99S曾俊 self.write_at_sync(lba_id_start, count, buf) 309*eb49bb99S曾俊 } 310*eb49bb99S曾俊 311b087521eSChiichen fn write_at_bytes(&self, offset: usize, len: usize, buf: &[u8]) -> Result<usize, SystemError> { 312b087521eSChiichen if len > buf.len() { 313b087521eSChiichen return Err(SystemError::E2BIG); 314b087521eSChiichen } 315b087521eSChiichen 316b087521eSChiichen let iter = BlockIter::new_multiblock(offset, offset + len, self.blk_size_log2()); 317b087521eSChiichen let multi = iter.multiblock; 318b087521eSChiichen 319b087521eSChiichen for range in iter { 320b087521eSChiichen let buf_begin = range.origin_begin() - offset; // 本次读操作的起始位置/已经读了这么多字节 321b087521eSChiichen let buf_end = range.origin_end() - offset; 322b087521eSChiichen let buf_slice = &buf[buf_begin..buf_end]; 323b5b571e0SLoGin let count: usize = range.lba_end - range.lba_start; 324b087521eSChiichen let full = multi && range.is_multi() || !multi && range.is_full(); 325b087521eSChiichen 326b087521eSChiichen if full { 327b087521eSChiichen self.write_at(range.lba_start, count, buf_slice)?; 328b087521eSChiichen } else { 329b087521eSChiichen if self.blk_size_log2() > BLK_SIZE_LOG2_LIMIT { 330b087521eSChiichen return Err(SystemError::E2BIG); 331b087521eSChiichen } 332b087521eSChiichen 333b5b571e0SLoGin let mut temp = vec![0; 1usize << self.blk_size_log2()]; 334b087521eSChiichen // 由于块设备每次读写都是整块的,在不完整写入之前,必须把不完整的地方补全 3350facf623SLoGin self.read_at(range.lba_start, 1, &mut temp[..])?; 336b087521eSChiichen // 把数据从临时buffer复制到目标buffer 337b5b571e0SLoGin temp[range.begin..range.end].copy_from_slice(buf_slice); 338b087521eSChiichen self.write_at(range.lba_start, 1, &temp[..])?; 339b087521eSChiichen } 340b087521eSChiichen } 341b087521eSChiichen return Ok(len); 342b087521eSChiichen } 343b087521eSChiichen 344b087521eSChiichen fn read_at_bytes( 345b087521eSChiichen &self, 346b087521eSChiichen offset: usize, 347b087521eSChiichen len: usize, 348b087521eSChiichen buf: &mut [u8], 349b087521eSChiichen ) -> Result<usize, SystemError> { 350b087521eSChiichen if len > buf.len() { 351b087521eSChiichen return Err(SystemError::E2BIG); 352b087521eSChiichen } 353b087521eSChiichen 354b087521eSChiichen let iter = BlockIter::new_multiblock(offset, offset + len, self.blk_size_log2()); 355b087521eSChiichen let multi = iter.multiblock; 356b087521eSChiichen 357b087521eSChiichen // 枚举每一个range 358b087521eSChiichen for range in iter { 359b087521eSChiichen let buf_begin = range.origin_begin() - offset; // 本次读操作的起始位置/已经读了这么多字节 360b087521eSChiichen let buf_end = range.origin_end() - offset; 361b087521eSChiichen let buf_slice = &mut buf[buf_begin..buf_end]; 362b5b571e0SLoGin let count: usize = range.lba_end - range.lba_start; 363b087521eSChiichen let full = multi && range.is_multi() || !multi && range.is_full(); 364b087521eSChiichen 3651effcfe5SGnoCiYeH // 读取整个block作为有效数据 366b087521eSChiichen if full { 367b087521eSChiichen // 调用 BlockDevice::read_at() 直接把引用传进去,不是把整个数组move进去 3681effcfe5SGnoCiYeH self.read_at(range.lba_start, count, buf_slice)?; 369b087521eSChiichen } else { 370b087521eSChiichen // 判断块的长度不能超过最大值 371b087521eSChiichen if self.blk_size_log2() > BLK_SIZE_LOG2_LIMIT { 372b087521eSChiichen return Err(SystemError::E2BIG); 373b087521eSChiichen } 374b087521eSChiichen 375b5b571e0SLoGin let mut temp = vec![0; 1usize << self.blk_size_log2()]; 376b087521eSChiichen self.read_at(range.lba_start, 1, &mut temp[..])?; 377b087521eSChiichen 378b087521eSChiichen // 把数据从临时buffer复制到目标buffer 379b087521eSChiichen buf_slice.copy_from_slice(&temp[range.begin..range.end]); 380b087521eSChiichen } 381b087521eSChiichen } 382b087521eSChiichen return Ok(len); 383b087521eSChiichen } 384b087521eSChiichen } 385ae5ede03SLoGin 386ae5ede03SLoGin /// @brief 块设备框架函数集 387ae5ede03SLoGin pub struct BlockDeviceOps; 388ae5ede03SLoGin 389ae5ede03SLoGin impl BlockDeviceOps { 390ae5ede03SLoGin /// @brief: 主设备号转下标 391ae5ede03SLoGin /// @parameter: major: 主设备号 392ae5ede03SLoGin /// @return: 返回下标 393ae5ede03SLoGin #[allow(dead_code)] 394c566df45SLoGin fn major_to_index(major: Major) -> usize { 395b5b571e0SLoGin return (major.data() % DEV_MAJOR_HASH_SIZE) as usize; 396ae5ede03SLoGin } 397ae5ede03SLoGin 398ae5ede03SLoGin /// @brief: 动态获取主设备号 399ae5ede03SLoGin /// @parameter: None 400ae5ede03SLoGin /// @return: 如果成功,返回主设备号,否则,返回错误码 401ae5ede03SLoGin #[allow(dead_code)] 402c566df45SLoGin fn find_dynamic_major() -> Result<Major, SystemError> { 403ae5ede03SLoGin let blockdevs = BLOCKDEVS.lock(); 404ae5ede03SLoGin // 寻找主设备号为234~255的设备 405c566df45SLoGin for index in ((DEV_MAJOR_DYN_END.data())..DEV_MAJOR_HASH_SIZE).rev() { 406c566df45SLoGin if let Some(item) = blockdevs.get(index as usize) { 407ae5ede03SLoGin if item.is_empty() { 408c566df45SLoGin return Ok(Major::new(index)); // 返回可用的主设备号 409ae5ede03SLoGin } 410ae5ede03SLoGin } 411ae5ede03SLoGin } 412ae5ede03SLoGin // 寻找主设备号在384~511的设备 413c566df45SLoGin for index in 414c566df45SLoGin ((DEV_MAJOR_DYN_EXT_END.data() + 1)..(DEV_MAJOR_DYN_EXT_START.data() + 1)).rev() 415c566df45SLoGin { 416b5b571e0SLoGin if let Some(blockdevss) = blockdevs.get(Self::major_to_index(Major::new(index))) { 417ae5ede03SLoGin let mut flag = true; 418ae5ede03SLoGin for item in blockdevss { 419b5b571e0SLoGin if item.device_number().major() == Major::new(index) { 420ae5ede03SLoGin flag = false; 421ae5ede03SLoGin break; 422ae5ede03SLoGin } 423ae5ede03SLoGin } 424ae5ede03SLoGin if flag { 425ae5ede03SLoGin // 如果数组中不存在主设备号等于index的设备 426c566df45SLoGin return Ok(Major::new(index)); // 返回可用的主设备号 427ae5ede03SLoGin } 428ae5ede03SLoGin } 429ae5ede03SLoGin } 430ae5ede03SLoGin return Err(SystemError::EBUSY); 431ae5ede03SLoGin } 432ae5ede03SLoGin 433ae5ede03SLoGin /// @brief: 注册设备号,该函数需要指定主设备号 434ae5ede03SLoGin /// @parameter: from: 主设备号 435ae5ede03SLoGin /// count: 次设备号数量 436ae5ede03SLoGin /// name: 字符设备名 437ae5ede03SLoGin /// @return: 如果注册成功,返回设备号,否则,返回错误码 438ae5ede03SLoGin #[allow(dead_code)] 439ae5ede03SLoGin pub fn register_blockdev_region( 440ae5ede03SLoGin from: DeviceNumber, 441c566df45SLoGin count: u32, 442ae5ede03SLoGin name: &'static str, 443ae5ede03SLoGin ) -> Result<DeviceNumber, SystemError> { 444ae5ede03SLoGin Self::__register_blockdev_region(from, count, name) 445ae5ede03SLoGin } 446ae5ede03SLoGin 447ae5ede03SLoGin /// @brief: 注册设备号,该函数自动分配主设备号 448ae5ede03SLoGin /// @parameter: baseminor: 主设备号 449ae5ede03SLoGin /// count: 次设备号数量 450ae5ede03SLoGin /// name: 字符设备名 451ae5ede03SLoGin /// @return: 如果注册成功,返回,否则,返回false 452ae5ede03SLoGin #[allow(dead_code)] 453ae5ede03SLoGin pub fn alloc_blockdev_region( 454c566df45SLoGin baseminor: u32, 455c566df45SLoGin count: u32, 456ae5ede03SLoGin name: &'static str, 457ae5ede03SLoGin ) -> Result<DeviceNumber, SystemError> { 458c566df45SLoGin Self::__register_blockdev_region( 459c566df45SLoGin DeviceNumber::new(Major::UNNAMED_MAJOR, baseminor), 460c566df45SLoGin count, 461c566df45SLoGin name, 462c566df45SLoGin ) 463ae5ede03SLoGin } 464ae5ede03SLoGin 465ae5ede03SLoGin /// @brief: 注册设备号 466ae5ede03SLoGin /// @parameter: device_number: 设备号,主设备号如果为0,则动态分配 467ae5ede03SLoGin /// minorct: 次设备号数量 468ae5ede03SLoGin /// name: 字符设备名 469ae5ede03SLoGin /// @return: 如果注册成功,返回设备号,否则,返回错误码 470ae5ede03SLoGin fn __register_blockdev_region( 471ae5ede03SLoGin device_number: DeviceNumber, 472c566df45SLoGin minorct: u32, 473ae5ede03SLoGin name: &'static str, 474ae5ede03SLoGin ) -> Result<DeviceNumber, SystemError> { 475ae5ede03SLoGin let mut major = device_number.major(); 476ae5ede03SLoGin let baseminor = device_number.minor(); 477ae5ede03SLoGin if major >= DEV_MAJOR_MAX { 478ae5ede03SLoGin kerror!( 479c566df45SLoGin "DEV {} major requested {:?} is greater than the maximum {}\n", 480ae5ede03SLoGin name, 481ae5ede03SLoGin major, 482c566df45SLoGin DEV_MAJOR_MAX.data() - 1 483ae5ede03SLoGin ); 484ae5ede03SLoGin } 485c566df45SLoGin if minorct > DeviceNumber::MINOR_MASK + 1 - baseminor { 486ae5ede03SLoGin kerror!("DEV {} minor range requested ({}-{}) is out of range of maximum range ({}-{}) for a single major\n", 487c566df45SLoGin name, baseminor, baseminor + minorct - 1, 0, DeviceNumber::MINOR_MASK); 488ae5ede03SLoGin } 489c566df45SLoGin let blockdev = DeviceStruct::new(DeviceNumber::new(major, baseminor), minorct, name); 490c566df45SLoGin if major == Major::UNNAMED_MAJOR { 491ae5ede03SLoGin // 如果主设备号为0,则自动分配主设备号 492ae5ede03SLoGin major = Self::find_dynamic_major().expect("Find synamic major error.\n"); 493ae5ede03SLoGin } 494ae5ede03SLoGin if let Some(items) = BLOCKDEVS.lock().get_mut(Self::major_to_index(major)) { 495ae5ede03SLoGin let mut insert_index: usize = 0; 496ae5ede03SLoGin for (index, item) in items.iter().enumerate() { 497ae5ede03SLoGin insert_index = index; 498ae5ede03SLoGin match item.device_number().major().cmp(&major) { 499ae5ede03SLoGin core::cmp::Ordering::Less => continue, 500ae5ede03SLoGin core::cmp::Ordering::Greater => { 501ae5ede03SLoGin break; // 大于则向后插入 502ae5ede03SLoGin } 503ae5ede03SLoGin core::cmp::Ordering::Equal => { 504ae5ede03SLoGin if item.device_number().minor() + item.minorct() <= baseminor { 505ae5ede03SLoGin continue; // 下一个主设备号大于或者次设备号大于被插入的次设备号最大值 506ae5ede03SLoGin } 507ae5ede03SLoGin if item.base_minor() >= baseminor + minorct { 508ae5ede03SLoGin break; // 在此处插入 509ae5ede03SLoGin } 510ae5ede03SLoGin return Err(SystemError::EBUSY); // 存在重合的次设备号 511ae5ede03SLoGin } 512ae5ede03SLoGin } 513ae5ede03SLoGin } 514ae5ede03SLoGin items.insert(insert_index, blockdev); 515ae5ede03SLoGin } 516c566df45SLoGin 517c566df45SLoGin return Ok(DeviceNumber::new(major, baseminor)); 518ae5ede03SLoGin } 519ae5ede03SLoGin 520ae5ede03SLoGin /// @brief: 注销设备号 521ae5ede03SLoGin /// @parameter: major: 主设备号,如果为0,动态分配 522ae5ede03SLoGin /// baseminor: 起始次设备号 523ae5ede03SLoGin /// minorct: 次设备号数量 524ae5ede03SLoGin /// @return: 如果注销成功,返回(),否则,返回错误码 525ae5ede03SLoGin fn __unregister_blockdev_region( 526ae5ede03SLoGin device_number: DeviceNumber, 527c566df45SLoGin minorct: u32, 528ae5ede03SLoGin ) -> Result<(), SystemError> { 529ae5ede03SLoGin if let Some(items) = BLOCKDEVS 530ae5ede03SLoGin .lock() 531ae5ede03SLoGin .get_mut(Self::major_to_index(device_number.major())) 532ae5ede03SLoGin { 533ae5ede03SLoGin for (index, item) in items.iter().enumerate() { 534ae5ede03SLoGin if item.device_number() == device_number && item.minorct() == minorct { 535ae5ede03SLoGin // 设备号和数量都相等 536ae5ede03SLoGin items.remove(index); 537ae5ede03SLoGin return Ok(()); 538ae5ede03SLoGin } 539ae5ede03SLoGin } 540ae5ede03SLoGin } 541ae5ede03SLoGin return Err(SystemError::EBUSY); 542ae5ede03SLoGin } 543ae5ede03SLoGin 544ae5ede03SLoGin /// @brief: 块设备注册 545ae5ede03SLoGin /// @parameter: cdev: 字符设备实例 546ae5ede03SLoGin /// dev_t: 字符设备号 547ae5ede03SLoGin /// range: 次设备号范围 548ae5ede03SLoGin /// @return: none 549ae5ede03SLoGin #[allow(dead_code)] 55006d5e247SLoGin pub fn bdev_add(_bdev: Arc<dyn BlockDevice>, id_table: IdTable) -> Result<(), DeviceError> { 551c566df45SLoGin if id_table.device_number().data() == 0 { 552ae5ede03SLoGin kerror!("Device number can't be 0!\n"); 553ae5ede03SLoGin } 55406d5e247SLoGin todo!("bdev_add") 55506d5e247SLoGin // return device_manager().add_device(bdev.id_table(), bdev.device()); 556ae5ede03SLoGin } 557ae5ede03SLoGin 558ae5ede03SLoGin /// @brief: block设备注销 559ae5ede03SLoGin /// @parameter: dev_t: 字符设备号 560ae5ede03SLoGin /// range: 次设备号范围 561ae5ede03SLoGin /// @return: none 562ae5ede03SLoGin #[allow(dead_code)] 563ae5ede03SLoGin pub fn bdev_del(_devnum: DeviceNumber, _range: usize) { 564ae5ede03SLoGin unimplemented!(); 565ae5ede03SLoGin } 566ae5ede03SLoGin } 567