#include "fs.hpp" #include Fs::Fs(RawDisk *disk, bool load) : disk(disk) { superblock = SuperBlock_Data(); // Determine the num inode blocks uint64_t num_inode_blocks = 0; // The superblock is not loaded from disk here; it is done in FilesOperation::initialize called by fischl_init if(load) { load_superblock(); num_inode_blocks = superblock.num_inode_blocks; } else { num_inode_blocks = (disk->diskSize / IO_BLOCK_SIZE) / 8; // adaptive size superblock.num_inode_blocks = num_inode_blocks; } assert((disk->diskSize / IO_BLOCK_SIZE) > 2 + num_inode_blocks + DATABLOCKS_PER_BITMAP_BLOCK); inode_manager = new INode_Manager_Freelist(this, 1, 1 + num_inode_blocks); datablock_manager = new DataBlock_Manager_Bitmap( this, 1 + num_inode_blocks, disk->diskSize / IO_BLOCK_SIZE); }; Fs::~Fs() { delete inode_manager; delete datablock_manager; }; int Fs::format() { int err; if ((err = save_superblock()) < 0) return err; if ((err = inode_manager->format()) < 0) return err; if ((err = datablock_manager->format()) < 0) return err; return 0; } int Fs::load_superblock() { char buf[IO_BLOCK_SIZE]; int err; if ((err = disk->read_block(0, buf)) < 0) return err; superblock.deserialize(buf); return 0; } int Fs::save_superblock() { char buf[IO_BLOCK_SIZE] = {0}; int err; superblock.serialize(buf); if ((err = disk->write_block(0, buf)) < 0) return err; return 0; } int Fs::save_free_list_head(u_int64_t new_free_list_head) { u_int64_t temp = superblock.free_list_head; int err; superblock.free_list_head = new_free_list_head; if ((err = save_superblock()) < 0) { superblock.free_list_head = temp; return err; } return 0; } int Fs::save_inode_list_head(u_int64_t new_inode_list_head) { u_int64_t temp = superblock.inode_list_head; int err; superblock.inode_list_head = new_inode_list_head; if ((err = save_superblock()) < 0) { superblock.inode_list_head = temp; return err; } return 0; }