From 25140bda17220a4c169015e0519bda415a795eb0 Mon Sep 17 00:00:00 2001 From: AmauryBrodu <60550980+AmauryBrodu@users.noreply.github.com> Date: Tue, 4 Apr 2023 21:51:45 +0200 Subject: [PATCH] ajout de directory.rs --- src/filesys/directory.rs | 145 +++++++++++++++++++++++++++++++++++++++ src/filesys/filehdr.rs | 34 ++++++--- src/filesys/openfile.rs | 2 +- 3 files changed, 169 insertions(+), 12 deletions(-) diff --git a/src/filesys/directory.rs b/src/filesys/directory.rs index e69de29..189e348 100644 --- a/src/filesys/directory.rs +++ b/src/filesys/directory.rs @@ -0,0 +1,145 @@ +const FILE_NAME_MAX_LEN: i32 = 80; +const NUM_DIR_ENTRIES: i32 = 30; + +use crate::kernel::mgerror::ErrorCode; +use crate::kernel::mgerror::ErrorCode::{AlreadyInDirectory, NospaceInDirectory, InexistDirectoryError}; +use std::mem; +pub struct DirectoryEntry { + in_use: bool, + sector: i32, + name: [char; FILE_NAME_MAX_LEN as usize], +} + +pub struct Directory { + table_size: i32, + table: Vec, +} + +impl Directory { + /// Initialize a directory; initially, the directory is completely + /// empty. If the disk is being formatted, an empty directory + /// is all we need, but otherwise, we need to call FetchFrom in order + /// to initialize it from disk. + /// + /// ### Parameters + /// - **size** is the number of entries in the directory + pub fn init_directory(size: i32) -> Directory { + let tmp:Vec = Vec::new(); + for i in 0..size { + tmp[i as usize].in_use = false; + } + Directory { + table_size: size, + table: tmp, + + } + } + + pub fn fetch_from(&self, OpenFile file) { + file.read_at(self.table,self.table_size * mem::size_of::() as i32); + } + + pub fn write_back(&self, OpenFile file) { + file.write_at(self.table,self.table_size * mem::size_of::() as i32); + } + + /// Look up file name in directory. + /// + /// return its location in the table of directory entries, + /// ERROR if the name isn't in the directory. + /// + /// ### Parameters + /// - **name** the file name to look up + pub fn find_index(&self, name: char) -> i32 { + for i in 0..self.table_size { + if self.table[i as usize].in_use && self.table[i as usize].name.starts_with(&self.table[i as usize].name) { + return i; + } + } + + return -1; + } + + /// Look up file name in directory, and return the disk sector number + /// where the file's header is stored. Return ERROR if the name isn't + /// in the directory. + /// + /// return the disk sector number where the file's header is stored + /// or ERROR if the name isn't in the directory. + /// + /// ### Parameters + /// + /// - **name** the file name to look up + pub fn find(&self, name: char) -> i32 { + let i = self.find_index(name); + if i != -1 { + return self.table[i as usize].sector; + } + return -1; + } + + ///Add a file into the directory. + /// + /// ### Parameters + /// - **name** the name of the file being added + /// - **new_sector** the disk sector containing the added file's header + /// + /// return NO_ERROR, ALREADY_IN_DIRECTORY or NOSPACE_IN_DIRECTORY. + pub fn add(&self, name: char, new_sector: i32) -> ErrorCode { + if self.find_index(name) != -1 { + return AlreadyInDirectory; + } + for i in 0..self.table_size { + if !self.table[i as usize].in_use { + self.table[i as usize].in_use = true; + self.table[i as usize].name.starts_with(&self.table[i as usize].name); + self.table[i as usize].sector = new_sector; + return NoError; + } + } + return NospaceInDirectory; + } + + /// Remove a file name from the directory. + /// + /// ### Parameters + /// - **name** the file name to be removed + /// return NO_ERROR, or INEXIST_DIRECTORY_ERROR + + pub fn remove(&self, name: char) -> ErrorCode{ + let i = self.find_index(name); + if i == -1 { + return InexistDirectoryError; + } + self.table[i as usize].in_use = false; + return NoError; + } + + /// List all the file names in the directory.(recursive function) + /// + /// ### Parameters + /// - **name** the name of the Dir to print + /// - **depth** the depth in the recursion (to print a nice hierarchy with spaces) + pub fn list(&self, name: char, depth: i32) { + let dir = Directory::init_directory(NUM_DIR_ENTRIES); + + for i in 0..self.table_size { + if self.table[i as usize].in_use { + for j in 0..depth { + if jdepth-3 { + print!("-"); + } + } + print!("{:#?}",self.table[i as usize].name); + + + } + } + } + + +} \ No newline at end of file diff --git a/src/filesys/filehdr.rs b/src/filesys/filehdr.rs index e0b6be1..3bf809b 100644 --- a/src/filesys/filehdr.rs +++ b/src/filesys/filehdr.rs @@ -1,4 +1,3 @@ -use crate::simulator::disk; use crate::{simulator::disk::SECTOR_SIZE, utility::bitmap::BitMap}; pub const MAX_HEADER_SECTORS: i32 = 32; pub const DATAS_IN_FIRST_SECTOR: i32 = (SECTOR_SIZE - 5 * 8) /8; @@ -8,6 +7,11 @@ pub const MAX_FILE_LENGTH: i32 = ((MAX_DATA_SECTORS) * SECTOR_SIZE); use crate::DrvDisk; use crate::Disk; +use crate::OpenFile; + +use std::mem; + +use super::openfile::OpenFile; pub struct FileHdr { is_dir: i32, @@ -20,18 +24,19 @@ pub struct FileHdr { impl FileHdr { - //Juste histoire d'avoir un constructeur, temporaire - pub fn new() -> FileHdr { - FileHdr{ - is_dir : 0, - num_bytes : 0, - num_sectors : 0, - data_sectors : Vec::new(), - num_header_sectors : 0, - header_sectors : [0 ; MAX_HEADER_SECTORS as usize] + + pub fn init_file_hdr() -> FileHdr { + FileHdr { + is_dir: 0, + num_bytes: 0, + num_sectors: 0, + data_sectors: Vec::new(), + num_header_sectors: 0, + header_sectors: [0;MAX_HEADER_SECTORS as usize], } } + pub fn allocate(&mut self, mut free_map: BitMap, file_size: i32) -> bool { self.num_bytes = file_size; if file_size > MAX_FILE_LENGTH { @@ -96,7 +101,14 @@ impl FileHdr { } } - //TODO: fetchFrom WriteBack + pub fn fetch_from(&self, file: OpenFile) { + file.read_at(self.table,self.table_size * mem::size_of::() as i32); + } + + pub fn write_back(&self, file: OpenFile) { + file.write_at(self.table,self.table_size * mem::size_of::() as i32); + } + pub fn byte_to_sector(&self,offset: i32) -> i32 { diff --git a/src/filesys/openfile.rs b/src/filesys/openfile.rs index deafa89..190b47a 100644 --- a/src/filesys/openfile.rs +++ b/src/filesys/openfile.rs @@ -37,7 +37,7 @@ impl OpenFile { Creer un "fichier ouvert", charge le file_hdr depuis disk */ pub fn open_file(sector : i32) -> OpenFile{ - let file_hdr : FileHdr = FileHdr::new(); + let file_hdr : FileHdr = FileHdr::init_file_hdr(); let name : String = String::from(""); //ici appel a fetchFrom(sector) sur file_hdr