From 761e3f04833c0bf10d03c0803f528618c65bda9e Mon Sep 17 00:00:00 2001 From: Josh Holtrop Date: Mon, 26 Dec 2005 22:00:00 -0500 Subject: [PATCH] Import backup from 2005-12-26 --- kernel/Makefile | 23 +- kernel/Makefile.bak | 25 ++- kernel/fs/FileSystem.cpp | 18 +- kernel/fs/FileSystem.h | 9 +- kernel/fs/OpenDirectory.cpp | 11 + kernel/fs/OpenDirectory.h | 21 ++ kernel/fs/OpenFile.cpp | 5 + kernel/fs/OpenFile.h | 23 ++ kernel/fs/VFSMount.cpp | 19 +- kernel/fs/VFSMount.h | 7 +- kernel/fs/ext2/Ext2OpenDirectory.cpp | 34 +++ kernel/fs/ext2/Ext2OpenDirectory.h | 23 ++ kernel/fs/ext2/Ext2OpenFile.cpp | 5 + kernel/fs/ext2/Ext2OpenFile.h | 16 ++ kernel/fs/ext2/ext2.cpp | 43 ++++ kernel/fs/ext2/ext2.h | 11 + kernel/fs/vfs.cpp | 306 ++++++++++++++++++++++++++- kernel/fs/vfs.h | 50 ++++- kernel/kernel.c | 21 +- 19 files changed, 613 insertions(+), 57 deletions(-) create mode 100644 kernel/fs/OpenDirectory.cpp create mode 100644 kernel/fs/OpenDirectory.h create mode 100644 kernel/fs/OpenFile.cpp create mode 100644 kernel/fs/OpenFile.h create mode 100644 kernel/fs/ext2/Ext2OpenDirectory.cpp create mode 100644 kernel/fs/ext2/Ext2OpenDirectory.h create mode 100644 kernel/fs/ext2/Ext2OpenFile.cpp create mode 100644 kernel/fs/ext2/Ext2OpenFile.h diff --git a/kernel/Makefile b/kernel/Makefile index 2e2e5f8..3e7e822 100644 --- a/kernel/Makefile +++ b/kernel/Makefile @@ -26,14 +26,17 @@ OBJS=boot.o lang/lang_a.o \ lang/string.o lang/new.o char/misc_char.o char/vconsole.o \ devices.o block/ramdisk.o fs/vfs.o fs/FileSystem.o fs/VFSMount.o \ fs/ext2/ext2.o fs/sysfs/sysfs.o fs/sysfs/sysfs_entry.o \ - sys/pci.o + sys/pci.o fs/OpenFile.o fs/OpenDirectory.o \ + fs/ext2/Ext2OpenDirectory.o fs/ext2/Ext2OpenFile.o CSRC=kernel.c mm/mm.c mm/vmm.c lang/conv.c display/kout.c \ display/display.c sys/pic.c char/keyboard.c lang/lang.c \ sys/pci_classes.c CXXSRC=lang/string.cpp lang/new.cpp char/misc_char.cpp char/vconsole.cpp \ block/ramdisk.cpp devices.cpp fs/vfs.cpp fs/FileSystem.o fs/VFSMount.o\ fs/ext2/ext2.cpp fs/sysfs/sysfs.cpp fs/sysfs/sysfs_entry.cpp \ - sys/pci.cpp proc/proc.cpp proc/hash.cpp + sys/pci.cpp proc/proc.cpp proc/hash.cpp fs/OpenFile.cpp \ + fs/OpenDirectory.cpp fs/ext2/Ext2OpenDirectory.cpp \ + fs/ext2/Ext2OpenFile.cpp .PHONY: all depend clean html @@ -90,14 +93,16 @@ block/ramdisk.o: functions.h hos_defines.h sys/io.h mm/vmm.h multiboot.h block/ramdisk.o: lang/lang.h block/ramdisk.h devices.h devices.o: hos_defines.h devices.h char/misc_char.h char/misc_char.h devices.o: char/vconsole.h block/ramdisk.h -fs/vfs.o: hos_defines.h display/kout.h functions.h sys/io.h fs/vfs.h -fs/vfs.o: devices.h lang/string.h fs/FileSystem.h fs/VFSMount.h -fs/vfs.o: fs/FileSystem.h fs/vfs.h fs/ext2/ext2.h lang/vector.h +fs/vfs.o: hos_defines.h display/kout.h functions.h sys/io.h lang/lang.h +fs/vfs.o: fs/vfs.h devices.h lang/string.h lang/vector.h fs/FileSystem.h +fs/vfs.o: fs/OpenFile.h fs/OpenDirectory.h fs/VFSMount.h fs/FileSystem.h +fs/vfs.o: fs/vfs.h fs/ext2/ext2.h fs/ext2/ext2.o: display/kout.h hos_defines.h mm/vmm.h multiboot.h lang/lang.h fs/ext2/ext2.o: fs/ext2/ext2.h fs/vfs.h devices.h fs/sysfs/sysfs.o: display/kout.h hos_defines.h fs/vfs.h devices.h -fs/sysfs/sysfs.o: fs/sysfs/sysfs.h fs/FileSystem.h lang/vector.h -fs/sysfs/sysfs.o: lang/string.h fs/sysfs/sysfs_entry.h +fs/sysfs/sysfs.o: fs/sysfs/sysfs.h fs/FileSystem.h fs/OpenFile.h +fs/sysfs/sysfs.o: fs/OpenDirectory.h fs/vfs.h lang/string.h lang/vector.h +fs/sysfs/sysfs.o: fs/VFSMount.h fs/FileSystem.h fs/sysfs/sysfs_entry.h fs/sysfs/sysfs_entry.o: fs/sysfs/sysfs_entry.h lang/vector.h hos_defines.h fs/sysfs/sysfs_entry.o: lang/string.h sys/pci.o: hos_defines.h display/kout.h sys/io.h sys/pci.h lang/vector.h @@ -106,3 +111,7 @@ proc/proc.o: functions.h sys/io.h display/kout.h proc/proc.h proc/hash.h proc/proc.o: lang/vector.h proc/hash.o: hos_defines.h proc/hash.h lang/vector.h display/kout.h mm/vmm.h proc/hash.o: multiboot.h +fs/OpenFile.o: fs/OpenFile.h hos_defines.h +fs/OpenDirectory.o: fs/OpenDirectory.h fs/vfs.h hos_defines.h devices.h +fs/OpenDirectory.o: lang/string.h lang/vector.h fs/FileSystem.h fs/OpenFile.h +fs/OpenDirectory.o: fs/VFSMount.h fs/FileSystem.h fs/vfs.h diff --git a/kernel/Makefile.bak b/kernel/Makefile.bak index 54a5598..e0cb323 100644 --- a/kernel/Makefile.bak +++ b/kernel/Makefile.bak @@ -26,14 +26,17 @@ OBJS=boot.o lang/lang_a.o \ lang/string.o lang/new.o char/misc_char.o char/vconsole.o \ devices.o block/ramdisk.o fs/vfs.o fs/FileSystem.o fs/VFSMount.o \ fs/ext2/ext2.o fs/sysfs/sysfs.o fs/sysfs/sysfs_entry.o \ - sys/pci.o + sys/pci.o fs/OpenFile.o fs/OpenDirectory.o \ + fs/ext2/Ext2OpenDirectory.o fs/ext2/Ext2OpenFile.o CSRC=kernel.c mm/mm.c mm/vmm.c lang/conv.c display/kout.c \ display/display.c sys/pic.c char/keyboard.c lang/lang.c \ sys/pci_classes.c CXXSRC=lang/string.cpp lang/new.cpp char/misc_char.cpp char/vconsole.cpp \ block/ramdisk.cpp devices.cpp fs/vfs.cpp fs/FileSystem.o fs/VFSMount.o\ fs/ext2/ext2.cpp fs/sysfs/sysfs.cpp fs/sysfs/sysfs_entry.cpp \ - sys/pci.cpp proc/proc.cpp proc/hash.cpp + sys/pci.cpp proc/proc.cpp proc/hash.cpp fs/OpenFile.cpp \ + fs/OpenDirectory.cpp fs/ext2/Ext2OpenDirectory.cpp \ + fs/ext2/Ext2OpenFile.cpp .PHONY: all depend clean html @@ -73,8 +76,8 @@ lang/conv.o: lang/conv.h hos_defines.h display/kout.o: hos_defines.h display/kout.h lang/conv.h devices.h display/kout.o: char/misc_char.h char/misc_char.h functions.h sys/io.h display/display.o: devices.h hos_defines.h char/vconsole.h display/display.h -display/display.o: lang/lang.h kernel.h multiboot.h display/vesafb.h -display/display.o: char/keyboard.h display/kout.h +display/display.o: lang/lang.h kernel.h multiboot.h char/keyboard.h +display/display.o: display/kout.h sys/pic.o: hos_defines.h sys/pic.h sys/io.h char/keyboard.o: hos_defines.h char/keyboard.h sys/io.h functions.h char/keyboard.o: lang/conv.h display/kout.h display/display.h devices.h @@ -90,14 +93,16 @@ block/ramdisk.o: functions.h hos_defines.h sys/io.h mm/vmm.h multiboot.h block/ramdisk.o: lang/lang.h block/ramdisk.h devices.h devices.o: hos_defines.h devices.h char/misc_char.h char/misc_char.h devices.o: char/vconsole.h block/ramdisk.h -fs/vfs.o: hos_defines.h display/kout.h fs/vfs.h devices.h lang/string.h -fs/vfs.o: fs/FileSystem.h fs/VFSMount.h fs/FileSystem.h fs/vfs.h +fs/vfs.o: hos_defines.h display/kout.h functions.h sys/io.h fs/vfs.h +fs/vfs.o: devices.h lang/string.h fs/FileSystem.h fs/OpenFile.h +fs/vfs.o: fs/OpenDirectory.h fs/VFSMount.h fs/FileSystem.h fs/vfs.h fs/vfs.o: fs/ext2/ext2.h lang/vector.h fs/ext2/ext2.o: display/kout.h hos_defines.h mm/vmm.h multiboot.h lang/lang.h fs/ext2/ext2.o: fs/ext2/ext2.h fs/vfs.h devices.h fs/sysfs/sysfs.o: display/kout.h hos_defines.h fs/vfs.h devices.h -fs/sysfs/sysfs.o: fs/sysfs/sysfs.h fs/FileSystem.h lang/vector.h -fs/sysfs/sysfs.o: lang/string.h fs/sysfs/sysfs_entry.h +fs/sysfs/sysfs.o: fs/sysfs/sysfs.h fs/FileSystem.h fs/OpenFile.h +fs/sysfs/sysfs.o: fs/OpenDirectory.h fs/vfs.h lang/string.h fs/VFSMount.h +fs/sysfs/sysfs.o: fs/FileSystem.h lang/vector.h fs/sysfs/sysfs_entry.h fs/sysfs/sysfs_entry.o: fs/sysfs/sysfs_entry.h lang/vector.h hos_defines.h fs/sysfs/sysfs_entry.o: lang/string.h sys/pci.o: hos_defines.h display/kout.h sys/io.h sys/pci.h lang/vector.h @@ -106,3 +111,7 @@ proc/proc.o: functions.h sys/io.h display/kout.h proc/proc.h proc/hash.h proc/proc.o: lang/vector.h proc/hash.o: hos_defines.h proc/hash.h lang/vector.h display/kout.h mm/vmm.h proc/hash.o: multiboot.h +fs/OpenFile.o: fs/OpenFile.h +fs/OpenDirectory.o: fs/OpenDirectory.h fs/vfs.h hos_defines.h devices.h +fs/OpenDirectory.o: lang/string.h fs/FileSystem.h fs/OpenFile.h fs/VFSMount.h +fs/OpenDirectory.o: fs/FileSystem.h fs/vfs.h diff --git a/kernel/fs/FileSystem.cpp b/kernel/fs/FileSystem.cpp index 3ee0170..f327771 100644 --- a/kernel/fs/FileSystem.cpp +++ b/kernel/fs/FileSystem.cpp @@ -5,14 +5,18 @@ // Modified: 06/21/05 #include "FileSystem.h" +#include "OpenFile.h" +#include "OpenDirectory.h" #include "hos_defines.h" FileSystem::FileSystem() {} FileSystem::~FileSystem() {} -u32_t FileSystem::totalBlocks(){return 0;} -u32_t FileSystem::usedBlocks(){return 0;}; -u32_t FileSystem::freeBlocks(){return 0;}; -u32_t FileSystem::totalInodes(){return 0;}; -u32_t FileSystem::usedInodes(){return 0;}; -u32_t FileSystem::freeInodes(){return 0;}; -u32_t FileSystem::getRootInodeNumber(){return 0;}; +u32_t FileSystem::totalBlocks() {return 0;} +u32_t FileSystem::freeBlocks() {return 0;}; +u32_t FileSystem::totalInodes() {return 0;}; +u32_t FileSystem::freeInodes() {return 0;}; +u32_t FileSystem::getRootInodeNumber() {return 0;}; + +OpenFile *FileSystem::openFile(u32_t inum) {return NULL;}; +OpenDirectory *FileSystem::openDirectory(u32_t inum) {return NULL;}; +int FileSystem::stat(u32_t inum, vfs_stat_t *buf) {return -1;}; diff --git a/kernel/fs/FileSystem.h b/kernel/fs/FileSystem.h index e5de9f3..7637d36 100644 --- a/kernel/fs/FileSystem.h +++ b/kernel/fs/FileSystem.h @@ -7,8 +7,9 @@ #ifndef __HOS_FILESYSTEM__ #define __HOS_FILESYSTEM__ __HOS_FILESYSTEM__ -#include "devices.h" #include "hos_defines.h" +#include "OpenFile.h" +#include "OpenDirectory.h" class FileSystem { @@ -17,14 +18,16 @@ public: virtual ~FileSystem(); virtual u32_t totalBlocks(); /* 512 byte blocks */ - virtual u32_t usedBlocks(); virtual u32_t freeBlocks(); virtual u32_t totalInodes(); - virtual u32_t usedInodes(); virtual u32_t freeInodes(); virtual u32_t getRootInodeNumber(); + + virtual OpenFile *openFile(u32_t inum); + virtual OpenDirectory *openDirectory(u32_t inum); + virtual int stat(u32_t inum, vfs_stat_t *buf); }; #endif diff --git a/kernel/fs/OpenDirectory.cpp b/kernel/fs/OpenDirectory.cpp new file mode 100644 index 0000000..1fe9995 --- /dev/null +++ b/kernel/fs/OpenDirectory.cpp @@ -0,0 +1,11 @@ +// OpenDirectory.cpp +// Author: Josh Holtrop +// Date: 12/19/05 + +#include "OpenDirectory.h" + +OpenDirectory::OpenDirectory() {} +OpenDirectory::~OpenDirectory() {} +int OpenDirectory::seek(int pos, int mode) { return -1; } +int OpenDirectory::read(vfs_dir_entry_t *ent) { return -1; } +int OpenDirectory::write(vfs_dir_entry_t *ent) { return -1; } diff --git a/kernel/fs/OpenDirectory.h b/kernel/fs/OpenDirectory.h new file mode 100644 index 0000000..b05e126 --- /dev/null +++ b/kernel/fs/OpenDirectory.h @@ -0,0 +1,21 @@ +// OpenDirectory.h +// Author: Josh Holtrop +// Date: 12/19/05 + +#ifndef __HOS_OPENDIRECTORY_H__ +#define __HOS_OPENDIRECTORY_H__ __HOS_OPENDIRECTORY_H__ + +#include "vfs.h" + +class OpenDirectory +{ +public: + OpenDirectory(); + virtual ~OpenDirectory(); + virtual int seek(int pos, int mode); + virtual int read(vfs_dir_entry_t *ent); + virtual int write(vfs_dir_entry_t *ent); +}; + +#endif + diff --git a/kernel/fs/OpenFile.cpp b/kernel/fs/OpenFile.cpp new file mode 100644 index 0000000..2b2f521 --- /dev/null +++ b/kernel/fs/OpenFile.cpp @@ -0,0 +1,5 @@ +// OpenFile.cpp +// Author: Josh Holtrop +// Date: 12/19/05 + +#include "OpenFile.h" diff --git a/kernel/fs/OpenFile.h b/kernel/fs/OpenFile.h new file mode 100644 index 0000000..7e152b2 --- /dev/null +++ b/kernel/fs/OpenFile.h @@ -0,0 +1,23 @@ +// OpenFile.h +// Author: Josh Holtrop +// Date: 12/19/05 + +#ifndef __HOS_OPENFILE_H__ +#define __HOS_OPENFILE_H__ __HOS_OPENFILE_H__ + +#include "hos_defines.h" + +class OpenFile +{ +public: + OpenFile(); + virtual ~OpenFile(); + virtual int seek(int pos, int mode); + virtual int read(); + virtual int read(void *buf, u32_t num); + virtual int write(int chr); + virtual int write(void *ptr, u32_t num); +}; + +#endif + diff --git a/kernel/fs/VFSMount.cpp b/kernel/fs/VFSMount.cpp index 3116ae3..9b19dd8 100644 --- a/kernel/fs/VFSMount.cpp +++ b/kernel/fs/VFSMount.cpp @@ -14,11 +14,13 @@ extern "C" { #include "lang/string.h" #include "fs/vfs.h" -VFSMount::VFSMount(device_t dev, FileSystem *fs, string mountPoint, inode_num_t mountInode, inode_num_t thisInode) +VFSMount::VFSMount(device_t dev, string fsType, FileSystem *fs, + string mountPoint, + inode_num_t mountInode, inode_num_t thisInode) { myDev = dev; + myFSType = fsType; myFS = fs; - myRefs = 0; myMountPoint = mountPoint; myMountInode = mountInode; myThisInode = thisInode; @@ -26,11 +28,12 @@ VFSMount::VFSMount(device_t dev, FileSystem *fs, string mountPoint, inode_num_t VFSMount::~VFSMount() { - if (myFS) - { - delete myFS; - if (myRefs) - kprintf("Filesystem uncleanly mounted from %s\n", myMountPoint.data()); - } + if (umount_safe()) + kprintf("Filesystem uncleanly mounted from %s\n", myMountPoint.data()); + delete myFS; } +int VFSMount::umount_safe() +{ + return 0; +} diff --git a/kernel/fs/VFSMount.h b/kernel/fs/VFSMount.h index bd442a2..7d327d4 100644 --- a/kernel/fs/VFSMount.h +++ b/kernel/fs/VFSMount.h @@ -16,14 +16,17 @@ class VFSMount { public: device_t myDev; + string myFSType; FileSystem *myFS; - int myRefs; string myMountPoint; inode_num_t myMountInode; inode_num_t myThisInode; - VFSMount(device_t dev, FileSystem *fs, string mountPoint, inode_num_t mountInode, inode_num_t thisInode); + VFSMount(device_t dev, string fsType, FileSystem *fs, + string mountPoint, + inode_num_t mountInode, inode_num_t thisInode); ~VFSMount(); + int umount_safe(); }; #endif diff --git a/kernel/fs/ext2/Ext2OpenDirectory.cpp b/kernel/fs/ext2/Ext2OpenDirectory.cpp new file mode 100644 index 0000000..656ba7b --- /dev/null +++ b/kernel/fs/ext2/Ext2OpenDirectory.cpp @@ -0,0 +1,34 @@ +// Ext2OpenDirectory.cpp +// Author: Josh Holtrop +// Date: 12/26/05 +// Modified: 12/26/05 + +#include "Ext2OpenDirectory.h" +extern "C" { +#include "display/kout.h" +#include "lang/lang.h" +} + +Ext2OpenDirectory::Ext2OpenDirectory() +{ + myPosition = 0; +} + +Ext2OpenDirectory::~Ext2OpenDirectory() +{ +} + +int Ext2OpenDirectory::seek(int pos, int mode) +{ + return -1; +} + +int Ext2OpenDirectory::read(vfs_dir_entry_t *ent) +{ + return -1; +} + +int Ext2OpenDirectory::write(vfs_dir_entry_t *ent) +{ + return -1; +} diff --git a/kernel/fs/ext2/Ext2OpenDirectory.h b/kernel/fs/ext2/Ext2OpenDirectory.h new file mode 100644 index 0000000..98bae84 --- /dev/null +++ b/kernel/fs/ext2/Ext2OpenDirectory.h @@ -0,0 +1,23 @@ +// Ext2OpenDirectory.h +// Author: Josh Holtrop +// Date: 12/26/05 +// Modified: 12/26/05 + +#ifndef __HOS_EXT2OPENDIRECTORY__ +#define __HOS_EXT2OPENDIRECTORY__ __HOS_EXT2OPENDIRECTORY__ + +#include "fs/OpenDirectory.h" + +class Ext2OpenDirectory : public OpenDirectory +{ +private: + int myPosition; +public: + Ext2OpenDirectory(); + ~Ext2OpenDirectory(); + int seek(int pos, int mode); + int read(vfs_dir_entry_t *ent); + int write(vfs_dir_entry_t *ent); +}; + +#endif diff --git a/kernel/fs/ext2/Ext2OpenFile.cpp b/kernel/fs/ext2/Ext2OpenFile.cpp new file mode 100644 index 0000000..fe935fa --- /dev/null +++ b/kernel/fs/ext2/Ext2OpenFile.cpp @@ -0,0 +1,5 @@ +// Ext2OpenFile.h +// Author: Josh Holtrop +// Date: 12/26/05 +// Modified: 12/26/05 + diff --git a/kernel/fs/ext2/Ext2OpenFile.h b/kernel/fs/ext2/Ext2OpenFile.h new file mode 100644 index 0000000..1b9b323 --- /dev/null +++ b/kernel/fs/ext2/Ext2OpenFile.h @@ -0,0 +1,16 @@ +// Ext2OpenFile.h +// Author: Josh Holtrop +// Date: 12/26/05 +// Modified: 12/26/05 + +#ifndef __HOS_EXT2OPENFILE__ +#define __HOS_EXT2OPENFILE__ __HOS_EXT2OPENFILE__ + +#include "fs/OpenFile.h" + +class Ext2OpenFile : public OpenFile +{ +}; + + +#endif diff --git a/kernel/fs/ext2/ext2.cpp b/kernel/fs/ext2/ext2.cpp index 78d791d..b6461b1 100644 --- a/kernel/fs/ext2/ext2.cpp +++ b/kernel/fs/ext2/ext2.cpp @@ -13,6 +13,8 @@ extern "C" { } #include "ext2.h" +#include "Ext2OpenDirectory.h" +#include "Ext2OpenFile.h" int ext2_init() { @@ -54,3 +56,44 @@ Ext2fs::~Ext2fs() if (mySuperDirty) block_write(DEV_MAJOR(myDevice), DEV_MINOR(myDevice), 2, 2, &mySuper); } + +u32_t Ext2fs::totalBlocks() +{ + return mySuper.s_blocks_count << (mySuper.s_log_block_size + 1); +} + +u32_t Ext2fs::freeBlocks() +{ + return mySuper.s_free_blocks_count << (mySuper.s_log_block_size + 1); +} + +u32_t Ext2fs::totalInodes() +{ + return mySuper.s_inodes_count; +} + +u32_t Ext2fs::freeInodes() +{ + return mySuper.s_free_inodes_count; +} + +/* ext2 filesystems always have a root-directory inode number of 2 */ +u32_t Ext2fs::getRootInodeNumber() +{ + return 2; +} + +OpenDirectory *Ext2fs::openDirectory(u32_t inum) +{ + return NULL; +} + +OpenFile *Ext2fs::openFile(u32_t inum) +{ + return NULL; +} + +int Ext2fs::stat(u32_t inum, vfs_stat_t *buf) +{ + return -1; +} diff --git a/kernel/fs/ext2/ext2.h b/kernel/fs/ext2/ext2.h index bc36640..8d06dc0 100644 --- a/kernel/fs/ext2/ext2.h +++ b/kernel/fs/ext2/ext2.h @@ -142,6 +142,9 @@ typedef struct #ifdef _HOS_CPP_ +#include "Ext2OpenDirectory.h" +#include "Ext2OpenFile.h" + int ext2_init(); FileSystem *ext2__mount_func(device_t dev); @@ -154,6 +157,14 @@ protected: public: Ext2fs(ext2_super_block_t *super, device_t dev); ~Ext2fs(); + u32_t totalBlocks(); + u32_t freeBlocks(); + u32_t totalInodes(); + u32_t freeInodes(); + u32_t getRootInodeNumber(); + OpenDirectory *openDirectory(u32_t inum); + OpenFile *openFile(u32_t inum); + int stat(u32_t inum, vfs_stat_t *buf); }; #endif diff --git a/kernel/fs/vfs.cpp b/kernel/fs/vfs.cpp index 2483d23..46ca940 100644 --- a/kernel/fs/vfs.cpp +++ b/kernel/fs/vfs.cpp @@ -2,7 +2,7 @@ // Virtual file system subsystem for HOS // Author: Josh Holtrop // Date: 05/10/05 -// Modified: 05/10/05 +// Modified: 12/26/05 #define _HOS_CPP_ _HOS_CPP_ @@ -10,6 +10,7 @@ extern "C" { #include "hos_defines.h" #include "display/kout.h" #include "functions.h" +#include "lang/lang.h" } #include "vfs.h" @@ -20,17 +21,38 @@ extern "C" { #include "lang/string.h" #include "devices.h" -vector *mountPoints; + +/* Internal module function prototypes */ +FileSystem *vfs_attempt_mount(device_t device, char *fsType); +mount_func_t vfs_get_mount_func(const string & fsName); +inode_num_t vfs_get_inode(const string & path); +inode_num_t vfs_get_inode_rel(const string & path, inode_num_t start_dir); +inode_num_t vfs_get_dir_entry_inode(inode_num_t dir, const string & fname); +int vfs_stat_inode(inode_num_t inum, vfs_stat_t *statptr); +VFSMount *vfs_get_mount(u32_t mt_id); +vector vfs_split_dirs(const string & path); +OpenDirectory *vfs_open_directory_inode(inode_num_t inum); +OpenFile *vfs_open_file_inode(inode_num_t inum); +void vfs_close_directory_real(OpenDirectory *o); +void vfs_close_file_real(OpenFile *o); +inode_num_t vfs_get_real_inode(inode_num_t inum); + +/* Global module data members */ +vector *mountPoints; vector *fses; +u32_t mount_id = 0; + +/* initialize the VFS module */ int vfs_init() { - mountPoints = new vector; + mountPoints = new vector; fses = new vector; ext2_init(); return 0; } +/* register a filesystem driver to the VFS module */ int vfs_register(char *fs, mount_func_t mount_func) { string fsName(fs); @@ -41,12 +63,17 @@ int vfs_register(char *fs, mount_func_t mount_func) return 0; } +/* mount a device with a filesystem to a mount point */ int vfs_mount(device_t device, char *fsType, char *mountPoint) { string mountPt(mountPoint); string fsName(fsType); + /* Bad filesystem type */ if (!vfs_get_mount_func(fsName)) + { + kprintf("vfs_mount: %s: unrecognized filesystem\n", fsType); return -501; + } if (mountPt == "/") { if (mountPoints->size()) @@ -55,22 +82,147 @@ int vfs_mount(device_t device, char *fsType, char *mountPoint) return -1; } FileSystem *fs = vfs_attempt_mount(device, fsType); + /* Couldn't mount root */ if (fs == NULL) return -2; - mountPoints->add(VFSMount(device, fs, mountPt, 0, fs->getRootInodeNumber())); + mountPoints->add(new VFSMount(device, fsName, fs, mountPt, 0, fs->getRootInodeNumber())); + mount_id++; return 0; } inode_num_t mtInode = vfs_get_inode(mountPt); + /* Invalid mount point */ if (mtInode == 0) return -3; FileSystem *fs = vfs_attempt_mount(device, fsType); + /* Couldn't mount */ if (fs == NULL) return -2; - inode_num_t thisInode = ((u64_t)(mountPoints->size()) << 32) | fs->getRootInodeNumber(); - mountPoints->add(VFSMount(device, fs, mountPt, mtInode, thisInode)); + inode_num_t thisInode = (((u64_t)(mount_id++)) << 32) | fs->getRootInodeNumber(); + mountPoints->add(new VFSMount(device, fsName, fs, mountPt, mtInode, thisInode)); return 0; } +/* get mount information about the mount point */ +int vfs_get_mount_info(unsigned int mountNum, vfs_mount_info_t *infoptr) +{ + if (mountNum >= mountPoints->size()) + return -1; + VFSMount *mt = (*mountPoints)[mountNum]; + strcpy(infoptr->fs, mt->myFSType.data()); + strcpy(infoptr->mountPoint, mt->myMountPoint.data()); + infoptr->totalBlocks = mt->myFS->totalBlocks(); + infoptr->freeBlocks = mt->myFS->freeBlocks(); + infoptr->totalInodes = mt->myFS->totalInodes(); + infoptr->freeInodes = mt->myFS->freeInodes(); + return 0; +} + +/* unmount a device */ +int vfs_umount(device_t dev) +{ + unsigned int max = mountPoints->size(); + for (unsigned int i = 0; i < max; i++) + { + if ((*mountPoints)[i]->myDev == dev) + { + if ((*mountPoints)[i]->umount_safe()) + return -502; + delete (*mountPoints)[i]; + mountPoints->remove(i); + return 0; + } + } + return -501; +} + +/* stat a filename */ +int vfs_stat(char *name, vfs_stat_t *buff) +{ + string sname = string(name); + inode_num_t inum; + if ((inum = vfs_get_inode(sname)) == 0) + return -502; + return vfs_stat_inode(inum, buff); +} + +void *vfs_open_dir(char *name) +{ + string sname(name); + inode_num_t inum = vfs_get_inode(sname); + return (void *) vfs_open_directory_inode(inum); +} + +void *vfs_open_file(char *name) +{ + string sname(name); + inode_num_t inum = vfs_get_inode(sname); + return (void *) vfs_open_file_inode(inum); +} + +void vfs_close_dir(void *o) +{ + vfs_close_directory_real((OpenDirectory *) o); +} + +void vfs_close_file(void *o) +{ + vfs_close_file_real((OpenFile *) o); +} + +int vfs_read_dir(void *o, vfs_dir_entry_t *dirent) +{ + OpenDirectory *odir = (OpenDirectory *) o; + return odir->read(dirent); +} + +int vfs_write_dir(void *o, vfs_dir_entry_t *dirent) +{ + OpenDirectory *odir = (OpenDirectory *) o; + return odir->write(dirent); +} + +int vfs_seek_dir(void *o, int pos, int mode) +{ + OpenDirectory *odir = (OpenDirectory *) o; + return odir->seek(pos, mode); +} + +int vfs_read_file(void *o) +{ + OpenFile *ofile = (OpenFile *) o; + return ofile->read(); +} + +int vfs_read_file_block(void *o, void *buf, u32_t num) +{ + OpenFile *ofile = (OpenFile *) o; + return ofile->read(buf, num); +} + +int vfs_write_file(void *o, int chr) +{ + OpenFile *ofile = (OpenFile *) o; + return ofile->write(chr); +} + +int vfs_write_file_block(void *o, void *buf, u32_t num) +{ + OpenFile *ofile = (OpenFile *) o; + return ofile->write(buf, num); +} + +int vfs_seek_file(void *o, int pos, int mode) +{ + OpenFile *ofile = (OpenFile *) o; + return ofile->seek(pos, mode); +} + + + + + +/**************************** Internal functions ****************************/ +/* "attempt" a mount */ FileSystem *vfs_attempt_mount(device_t device, char *fsType) { mount_func_t mount_func; @@ -80,17 +232,155 @@ FileSystem *vfs_attempt_mount(device_t device, char *fsType) return NULL; } +/* Trace a file name to make an inode */ inode_num_t vfs_get_inode(const string & path) { - return 0; + return vfs_get_inode_rel(path, 0ULL); } +/* Trace file name to inode starting from this directory (recursive) */ +inode_num_t vfs_get_inode_rel(const string & path, inode_num_t start_dir) +{ + vector paths = vfs_split_dirs(path); + unsigned int paths_size = paths.size(); + inode_num_t currentInum = start_dir; + for (unsigned int i = 0; i < paths_size; i++) + { + currentInum = vfs_get_dir_entry_inode(currentInum, paths[i]); + if (currentInum == 0ULL) + return 0ULL; + currentInum = vfs_get_real_inode(currentInum); + } + return currentInum; +} + +/* return the inode of a directory entry in the directory pointed to by dir */ +inode_num_t vfs_get_dir_entry_inode(inode_num_t dir, const string & fname) +{ + OpenDirectory *odir = vfs_open_directory_inode(dir); + if (odir == NULL) + return 0ULL; + vfs_dir_entry_t dir_ent; + inode_num_t inum = 0ULL; + while (vfs_read_dir(odir, &dir_ent) == 0) + { + if (strcmp(dir_ent.name, fname.data()) == 0) + { + inum = (dir & 0xFFFFFFFF00000000ULL) | dir_ent.inum; + break; + } + } + vfs_close_directory_real(odir); + return inum; +} + +/* Just split up a string into a vector of strings based on the path + * delimeter character ('/'). + */ +vector vfs_split_dirs(const string & path) +{ + char *sptr = new char[path.size() + 1]; + strcpy(sptr, path.data()); + char *bptr = sptr; + char *cptr = sptr; + vector parts; + while (*cptr) + { + if (*cptr == '/') + { + *cptr = 0; + string dir(bptr); + if (dir.size() > 0) + parts.add(dir); + bptr = cptr + 1; + } + cptr++; + } + string dir(bptr); + if (dir.size() > 0) + parts.add(dir); + delete sptr; + return parts; +} + +/* Return a pointer to the mount function for a certain file system type */ mount_func_t vfs_get_mount_func(const string & fsName) { - for (unsigned int i = 0; i < fses->size(); i++) + unsigned int max = fses->size(); + for (unsigned int i = 0; i < max; i++) { if (fsName == (*fses)[i].name) return (*fses)[i].mount_func; } return NULL; } + +/* Return a pointer to a VFSMount by the "mount id" (upper 32 bits of inode) */ +VFSMount *vfs_get_mount(u32_t mt_id) +{ + int max = mountPoints->size(); + for (int i = 0; i < max; i++) + { + if (((*mountPoints)[i]->myThisInode >> 32) == mt_id) + return (*mountPoints)[i]; + } + return NULL; +} + +/* FS function: stat a inode, return error code */ +int vfs_stat_inode(inode_num_t inum, vfs_stat_t *statptr) +{ + inum = vfs_get_real_inode(inum); + VFSMount *mt = vfs_get_mount(inum >> 32); + if (mt == NULL) + return -501; + return mt->myFS->stat((u32_t)inum, statptr); +} + +/* FS function: open a directory based on the inode number */ +OpenDirectory *vfs_open_directory_inode(inode_num_t inum) +{ + inum = vfs_get_real_inode(inum); + VFSMount *mt = vfs_get_mount(inum >> 32); + if (mt == NULL) + return NULL; + return mt->myFS->openDirectory((u32_t)inum); +} + +/* FS function: open a file based on the inode number */ +OpenFile *vfs_open_file_inode(inode_num_t inum) +{ + inum = vfs_get_real_inode(inum); + VFSMount *mt = vfs_get_mount(inum >> 32); + if (mt == NULL) + return NULL; + return mt->myFS->openFile((u32_t)inum); +} + +/* FS function: close a directory */ +void vfs_close_directory_real(OpenDirectory *o) +{ + delete o; +} + +/* FS function: close a file */ +void vfs_close_file_real(OpenFile *o) +{ + delete o; +} + +/* return the "real" inode number based on the given one + * This function enables inode numbers for directories that have something + * mounted in them to be converted to the inode number for the root directory + * of that mounted filesystem + */ +inode_num_t vfs_get_real_inode(inode_num_t inum) +{ + unsigned int mounts = mountPoints->size(); + for (unsigned int i = 0; i < mounts; i++) + { + if ((*mountPoints)[i]->myMountInode == inum) + return (*mountPoints)[i]->myThisInode; + } + return inum; +} diff --git a/kernel/fs/vfs.h b/kernel/fs/vfs.h index a524e6b..3ebe25c 100644 --- a/kernel/fs/vfs.h +++ b/kernel/fs/vfs.h @@ -2,7 +2,7 @@ // Virtual file system subsystem for HOS // Author: Josh Holtrop // Date: 05/10/05 -// Modified: 05/10/05 +// Modified: 12/26/05 #ifndef __HOS_VFS_H__ #define __HOS_VFS_H__ __HOS_VFS_H__ @@ -31,13 +31,19 @@ #define EOF 0x100 +#define VFS_MAX_FILENAME 255 + +#define SEEK_ABSOLUTE 0 +#define SEEK_RELATIVE 1 +#define SEEK_END 2 + #include "hos_defines.h" #include "devices.h" typedef struct { - u16_t type; // file type, of VFS_FILE_TYPE_* + u16_t type; // file type, of VFS_FT_* u32_t size; u32_t inode; u16_t permissions; @@ -50,6 +56,21 @@ typedef struct u32_t dev; } vfs_stat_t; +typedef struct +{ + char name[VFS_MAX_FILENAME + 1]; + u32_t inum; +} vfs_dir_entry_t; + +typedef struct +{ + char fs[16]; + char mountPoint[256]; + u32_t totalBlocks; + u32_t freeBlocks; + u32_t totalInodes; + u32_t freeInodes; +} vfs_mount_info_t; typedef u64_t inode_num_t; @@ -59,27 +80,40 @@ extern "C" { int vfs_init(); int vfs_mount(device_t device, char *fsType, char *mountPoint); +int vfs_umount(device_t dev); int vfs_stat(char *name, vfs_stat_t *buff); +int vfs_get_mount_info(unsigned int mountNum, vfs_mount_info_t *infoptr); +void *vfs_open_dir(char *name); +void *vfs_open_file(char *name); +void vfs_close_dir(void *o); +void vfs_close_file(void *o); +int vfs_read_dir(void *o, vfs_dir_entry_t *dirent); +int vfs_write_dir(void *o, vfs_dir_entry_t *dirent); +int vfs_seek_dir(void *o, int pos, int mode); +int vfs_read_file(void *o); +int vfs_read_file_block(void *o, void *buf, u32_t num); +int vfs_write_file(void *o, int chr); +int vfs_write_file_block(void *o, void *buf, u32_t num); +int vfs_seek_file(void *o, int pos, int mode); + #ifdef _HOS_CPP_ } #include "lang/string.h" +#include "lang/vector.h" #include "fs/FileSystem.h" #include "fs/VFSMount.h" +typedef FileSystem *(*mount_func_t)(device_t); + typedef struct { string name; - FileSystem *(*mount_func)(device_t); + mount_func_t mount_func; } FSHandle; -typedef FileSystem *(*mount_func_t)(device_t); - -FileSystem *vfs_attempt_mount(device_t device, char *fsType); int vfs_register(char *fs, mount_func_t mount_func); -mount_func_t vfs_get_mount_func(const string & fsName); -inode_num_t vfs_get_inode(const string & path); #endif diff --git a/kernel/kernel.c b/kernel/kernel.c index 8b617ff..95e672b 100644 --- a/kernel/kernel.c +++ b/kernel/kernel.c @@ -129,6 +129,7 @@ void k_init() } display_init(); // initialize display subsystem kprintf("HOS v0.16 initializing...\n"); + kprintf("Kernel load line: '%s'\n", mb_cmdline); kprintf("Kernel load size: %d (0x%x) bytes (%d kb)\n", kernel_size(), kernel_size(), kernel_size() >> 10); kprintf("Kernel memory size: %d (0x%x) bytes (%d kb)\n", kernel_size_used(), kernel_size_used(), kernel_size_used() >> 10); @@ -148,7 +149,7 @@ void k_init() kprintf("initrd (%dkb) loaded\n", (mb_modules[i].mod_end - mb_modules[i].mod_start) >> 10); k_check(vfs_mount(DEV(MAJOR_RAMDISK, initrd_minor), "ext2", "/"), "Kernel panic: Could not mount initrd to /!"); } - else if (((hos_module_header_t*)(mb_modules[i].mod_start))->mod_type == 2) +/* else if (((hos_module_header_t*)(mb_modules[i].mod_start))->mod_type == 2) { kprintf("Creating a task\n"); create_task((void *)mb_modules[i].mod_start, @@ -156,16 +157,23 @@ void k_init() 0, ((hos_module_header_t*)(mb_modules[i].mod_start))->init); } - } +*/ } -/* vfs_open_file_t *root = vfs_open_dir("////"); + vfs_mount_info_t mt_info; + vfs_get_mount_info(0, &mt_info); + kprintf("%s, %s, %d, %d, %d, %d\n", mt_info.fs, mt_info.mountPoint, mt_info.totalBlocks, mt_info.freeBlocks, mt_info.totalInodes, mt_info.freeInodes); + + void *root = vfs_open_dir("///"); + char name[256]; if (root) { vfs_dir_entry_t dentry; vfs_stat_t fstat; while (!vfs_read_dir(root, &dentry)) { - vfs_stat_inode(dentry.inode_number, &fstat); + strcpy(name, "/"); + strcat(name, dentry.name); + vfs_stat(name, &fstat); kprintf("%d\t", fstat.inode); putc(fstat.type == VFS_FT_DIR ? 'd' : fstat.type == VFS_FT_CHAR ? 'c' : fstat.type == VFS_FT_BLOCK ? 'b' : fstat.type == VFS_FT_SYMLINK ? 'l' : '-'); putc(fstat.permissions & VFS_PERMS_UR ? 'r' : '-'); @@ -186,7 +194,8 @@ void k_init() if (fstat.type == VFS_FT_SYMLINK) { char *link = kmalloc(4096); - vfs_link_deref(dentry.inode_number, link); + //vfs_link_deref(dentry.inode, link); + strcpy(link, "[a link]"); kprintf(" -> %s", link); kfree(link); } @@ -196,7 +205,7 @@ void k_init() } else kprintf("Error: Could not open directory\n"); -*/ + criticalCounter--; }