Improved build system
Added new entries to .gitignore Moved away from source directory as central spot for all source code
This commit is contained in:
		
							
								
								
									
										417
									
								
								kernel/vfs/VFS.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										417
									
								
								kernel/vfs/VFS.cpp
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,417 @@
 | 
			
		||||
#include "VFS.h"
 | 
			
		||||
#include "../filesystem/FAT/BiosParameterBlock.h"
 | 
			
		||||
#include "../drivers/ide/ide.h"
 | 
			
		||||
#include "../drivers/ata/ataDevice.h"
 | 
			
		||||
#include "../partitiontable/mbr/MasterBootRecord.h"
 | 
			
		||||
#include "../memory/KernelHeap.h"
 | 
			
		||||
#include "../../CoreLib/Memory.h"
 | 
			
		||||
#include "../filesystem/FAT/DirectoryEntry.h"
 | 
			
		||||
 | 
			
		||||
MOUNT_INFO mountInfo;
 | 
			
		||||
 | 
			
		||||
PFILESYSTEM _filesystems[DEVICE_MAX];
 | 
			
		||||
 | 
			
		||||
FILE volOpenFile(const char* fname)
 | 
			
		||||
{
 | 
			
		||||
    if(fname){
 | 
			
		||||
        unsigned char device = 'a';
 | 
			
		||||
 | 
			
		||||
        char* filename = (char*) fname;
 | 
			
		||||
 | 
			
		||||
        if(fname[1]== ':'){
 | 
			
		||||
            device = fname[0];
 | 
			
		||||
            filename += 2; // strip the volume component from the path
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if(_filesystems[device - 'a']){
 | 
			
		||||
            FILE file = _filesystems[device-'a']->Open(filename);
 | 
			
		||||
            file.device = device;
 | 
			
		||||
            return file;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    FILE file;
 | 
			
		||||
    file.flags = FS_INVALID;
 | 
			
		||||
    return file;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
extern void volReadFile(PFILE file, unsigned char* Buffer, unsigned int length)
 | 
			
		||||
{
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
extern void volCloseFile(PFILE file)
 | 
			
		||||
{
 | 
			
		||||
    if( file->device < DEVICE_MAX){
 | 
			
		||||
    //    _filesystems[file->device]->Close(file);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
extern void volRegisterFilesystem(PFILESYSTEM fsys , unsigned int deviceID){
 | 
			
		||||
    if(deviceID < DEVICE_MAX)
 | 
			
		||||
        if(fsys)
 | 
			
		||||
            _filesystems[deviceID] = fsys;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
extern void volUnregisterFilesystem(PFILESYSTEM){
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
extern void volUnregisterFileSystemByID(unsigned int deviceID){
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
enum BUS_PORT {
 | 
			
		||||
    Primary = 0x1f0,
 | 
			
		||||
    Secondary = 0x170
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
bool driveAvailable(){
 | 
			
		||||
    int devNumber = 0;
 | 
			
		||||
    for ( auto device : ide_devices){
 | 
			
		||||
        if(!device.Reserved)
 | 
			
		||||
            continue;
 | 
			
		||||
        devNumber++;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    // FIXME: If no drive is connected we continue trying to read from
 | 
			
		||||
    // a not connected drive!
 | 
			
		||||
    ATA_DEVICE::Identify((uint16_t) BUS_PORT::Primary, DEVICE_DRIVE::MASTER);
 | 
			
		||||
    return true;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
MBR* getPartitions(bool DEBUG = false){
 | 
			
		||||
    const int C = 0;
 | 
			
		||||
    const int H = 0;
 | 
			
		||||
    const int HPC = 16;
 | 
			
		||||
    const int SPT = 63;
 | 
			
		||||
 | 
			
		||||
    int S =1;
 | 
			
		||||
    uint32_t LBA = (C*HPC+H) * SPT + (S-1);
 | 
			
		||||
    MBR* mbr =(MBR*) malloc(sizeof (MBR));
 | 
			
		||||
 | 
			
		||||
    ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, LBA, (uint16_t*)mbr);
 | 
			
		||||
 | 
			
		||||
    if(DEBUG){
 | 
			
		||||
        printf("BootSector: 0x%x\n", mbr->ValidBootsector );
 | 
			
		||||
        for( int i = 0 ; i < 4 ; i ++){
 | 
			
		||||
            PartitionTableEntry PT = mbr->TableEntries[i];
 | 
			
		||||
 | 
			
		||||
            printf("Partition %d [  %d sectors,  PartitionType: 0x%x, 0x%x, \nLBA Start: 0x%x ]\n" ,
 | 
			
		||||
                   i, PT.Number_sectors_inPartition, PT.PartitionType, mbr->uniqueID,  PT.LBA_partition_start );
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return mbr;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
BiosParameterBlock* getBPB(MBR* mbr, bool DEBUG =false ){
 | 
			
		||||
    BiosParameterBlock* bpb = (BiosParameterBlock*) malloc(sizeof(BiosParameterBlock));
 | 
			
		||||
    ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, mbr->TableEntries[0].LBA_partition_start, (uint16_t*) bpb);
 | 
			
		||||
 | 
			
		||||
    if(DEBUG)
 | 
			
		||||
    {
 | 
			
		||||
        printf("OEM ID: %s\n", bpb->OEM_id);
 | 
			
		||||
        printf("Bytes per sector: %d\n", bpb->BytesPerSector);
 | 
			
		||||
        printf("Sectors per cluster: %d\n", bpb->SectorsPerCluster);
 | 
			
		||||
        printf("Reserved sectors: %d\n", bpb->ReservedSectors);
 | 
			
		||||
        printf("Number of FAT: %d\n", bpb->NumberOfFileAllocationTables);
 | 
			
		||||
        printf("Number of Dir entries: %d\n", bpb->NumberOfDirectoryEntries);
 | 
			
		||||
        printf("Total Sectors in volume: %d\n", bpb->TotalSectorsInLogicalVolume);
 | 
			
		||||
        printf("Sectors per FAT: %d\n", bpb->NumberOfSectorsPerFAT);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    return bpb;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
uint16_t* ReadFAT (BiosParameterBlock& bpb , MBR& mbr, bool DEBUG = false ) {
 | 
			
		||||
    uint32_t FATAddress = mbr.TableEntries[0].LBA_partition_start +  bpb.ReservedSectors ;
 | 
			
		||||
    uint16_t* FAT = (uint16_t*)malloc(sizeof (uint16_t) * 256);
 | 
			
		||||
    ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, FATAddress, FAT );
 | 
			
		||||
 | 
			
		||||
    // Show data in terminal
 | 
			
		||||
    if(DEBUG){
 | 
			
		||||
        for( unsigned int i =0 ; i < 256 ; i++) {
 | 
			
		||||
            printf("0x%x ", (unsigned short)FAT[i]);
 | 
			
		||||
        }
 | 
			
		||||
        kterm_put('\n');
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return FAT;
 | 
			
		||||
}
 | 
			
		||||
void readFile(uint32_t DataRegion, DirectoryEntry* entry, uint16_t FATentry, BiosParameterBlock& bpb ){
 | 
			
		||||
    printf("Show contents");
 | 
			
		||||
 | 
			
		||||
    printf("Start cluster of the file: 0x%x\n", entry->StartingCluster);
 | 
			
		||||
 | 
			
		||||
    printf("IS it only 1 cluster? %s\n", FATentry == 0xFFFF ? "Yes" : "No");
 | 
			
		||||
 | 
			
		||||
    uint32_t sector = DataRegion + ((entry->StartingCluster - 0x02) * bpb.SectorsPerCluster);
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    uint16_t dataBlob[256];
 | 
			
		||||
    ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, sector, dataBlob);
 | 
			
		||||
    for (unsigned short n: dataBlob) {
 | 
			
		||||
        kterm_put(n & 0x00ff);
 | 
			
		||||
 | 
			
		||||
        kterm_put(n >> 8);
 | 
			
		||||
    }
 | 
			
		||||
    kterm_put('\n');
 | 
			
		||||
}
 | 
			
		||||
void listFilesInRoot(MBR& mbr, BiosParameterBlock& bpb ){
 | 
			
		||||
    auto FATAddress = mbr.TableEntries[0].LBA_partition_start +  bpb.ReservedSectors;
 | 
			
		||||
    uint32_t RootDirectoryRegion = FATAddress + ( bpb.NumberOfFileAllocationTables * bpb.NumberOfSectorsPerFAT );
 | 
			
		||||
    uint32_t DataRegion = RootDirectoryRegion + ((bpb.NumberOfDirectoryEntries * 32) / bpb.BytesPerSector );
 | 
			
		||||
    uint16_t* FAT = ReadFAT(bpb, mbr);
 | 
			
		||||
 | 
			
		||||
    uint16_t data2 [256];
 | 
			
		||||
    ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, RootDirectoryRegion, data2 );
 | 
			
		||||
    auto* RootDirectory = (DirectoryEntry*) data2;
 | 
			
		||||
 | 
			
		||||
    // List files in root
 | 
			
		||||
    for(int i= 0; i < sizeof (data2) / sizeof (DirectoryEntry); i++ ) {
 | 
			
		||||
        auto *entry = (DirectoryEntry * )((uint32_t) RootDirectory + (i * sizeof(DirectoryEntry)));
 | 
			
		||||
 | 
			
		||||
        if (entry->filename[0] == (uint8_t) 0x00)
 | 
			
		||||
            continue; // There are no more entries in this directory or the entry is free
 | 
			
		||||
 | 
			
		||||
        if ((entry->attribute & 0x01) == 0x01 || (entry->attribute & 0x20) == 0x20)
 | 
			
		||||
            continue; // Skip listing if hidden or Achieve flag is set
 | 
			
		||||
 | 
			
		||||
        // Print the filename;
 | 
			
		||||
        for (char n: entry->filename) {
 | 
			
		||||
            if (n == 0x20)
 | 
			
		||||
                break;
 | 
			
		||||
            kterm_put(n);
 | 
			
		||||
        }
 | 
			
		||||
        for (unsigned char n: entry->Extension) {
 | 
			
		||||
            kterm_put(n);
 | 
			
		||||
        }
 | 
			
		||||
        kterm_put('\n');
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
        printf("Attribute: %x \n", entry->attribute);
 | 
			
		||||
        printf("FileSize: %d Bytes\n", entry->FilesizeInBytes);
 | 
			
		||||
 | 
			
		||||
        if (entry->FilesizeInBytes != 0x0  && (entry->attribute == 0x08)) {
 | 
			
		||||
            readFile(DataRegion,entry, FAT[i], bpb);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
    }
 | 
			
		||||
    free(FAT);
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
FILE fsysFatDirectory (const char* DirectoryName){
 | 
			
		||||
    FILE file;
 | 
			
		||||
    unsigned char* buf;
 | 
			
		||||
    PDIRECTORY directory;
 | 
			
		||||
 | 
			
		||||
    char DosFileName[11];
 | 
			
		||||
    ToDosFileName(DirectoryName, DosFileName, 11);
 | 
			
		||||
    DosFileName[11] =0;
 | 
			
		||||
 | 
			
		||||
    for (int sector=0; sector <14 ; sector++){
 | 
			
		||||
        ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, mountInfo.rootOffset + sector, (uint16_t*)buf);
 | 
			
		||||
        directory = (PDIRECTORY) buf;
 | 
			
		||||
 | 
			
		||||
        for (int i =0; i < 16; i++){
 | 
			
		||||
            char name[11];
 | 
			
		||||
            memcpy(name, directory->Filename, 11);
 | 
			
		||||
            name[11]=0;
 | 
			
		||||
 | 
			
		||||
            if(strncmp(DosFileName, name, 11) == 0){
 | 
			
		||||
                strcpy(file.name, DirectoryName);
 | 
			
		||||
                file.id = 0;
 | 
			
		||||
                file.currentCluster = directory->FirstCluster;
 | 
			
		||||
                file.eof = 0;
 | 
			
		||||
                file.filelength = directory->FileSize;
 | 
			
		||||
 | 
			
		||||
                if(directory->Attrib == 0x10){
 | 
			
		||||
                    file.flags = FS_DIRECTORY;
 | 
			
		||||
                } else {
 | 
			
		||||
                    file.flags = FS_FILE;
 | 
			
		||||
                }
 | 
			
		||||
                return file;
 | 
			
		||||
            }
 | 
			
		||||
            directory++;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Can't find file
 | 
			
		||||
    file.flags = FS_INVALID;
 | 
			
		||||
    return file;
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
void fsysFATRead(PFILE file, unsigned char* buffer, unsigned int length){
 | 
			
		||||
    if(file){
 | 
			
		||||
        unsigned int physSector = 32 + (file->currentCluster - 1);
 | 
			
		||||
        const unsigned int  SECTOR_SIZE = 512;
 | 
			
		||||
        // read sector
 | 
			
		||||
        ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, physSector, (uint16_t*) buffer );
 | 
			
		||||
 | 
			
		||||
        unsigned int FAT_Offset = file->currentCluster + (file->currentCluster /2);
 | 
			
		||||
        unsigned int FAT_Sector = 1 + (FAT_Offset / SECTOR_SIZE);
 | 
			
		||||
        unsigned int entryOffset =FAT_Offset % SECTOR_SIZE;
 | 
			
		||||
 | 
			
		||||
        uint8_t FAT[SECTOR_SIZE*2];
 | 
			
		||||
        ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, FAT_Sector,(uint16_t*) FAT); // Read 1st FAT sector
 | 
			
		||||
 | 
			
		||||
        ATA_DEVICE::Read(BUS_PORT::Primary, DEVICE_DRIVE::MASTER, FAT_Sector +1, (uint16_t*)FAT+SECTOR_SIZE);
 | 
			
		||||
 | 
			
		||||
        // read entry for next cluster
 | 
			
		||||
        uint16_t nextCluster = *(uint16_t*) &FAT[entryOffset];
 | 
			
		||||
 | 
			
		||||
        // test if entry is odd or even
 | 
			
		||||
        if(file->currentCluster & 0x0001){
 | 
			
		||||
            nextCluster>>= 4; // grab the high 12 bits
 | 
			
		||||
        }else{
 | 
			
		||||
            nextCluster &= 0x0FFF; // grab the low 12 bits
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        // test for end of file
 | 
			
		||||
        if(nextCluster >= 0xff8){
 | 
			
		||||
            file->eof -1;
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        // test for file corruption
 | 
			
		||||
        if(nextCluster == 0){
 | 
			
		||||
            file->eof =1;
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        // set next cluster
 | 
			
		||||
        file->currentCluster = nextCluster;
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
/*
 | 
			
		||||
FILE fsysFatOpenSubDir(FILE kFile, const char* filename){
 | 
			
		||||
    FILE file;
 | 
			
		||||
 | 
			
		||||
    char DosFileName[11];
 | 
			
		||||
    ToDosFileName(filename, DosFileName, 11);
 | 
			
		||||
    DosFileName[11] = 0;
 | 
			
		||||
 | 
			
		||||
    while(!kFile.eof){
 | 
			
		||||
        //read directory
 | 
			
		||||
        unsigned char buf[512];
 | 
			
		||||
        fsysFATRead(&file, buf, 512);
 | 
			
		||||
 | 
			
		||||
        PDIRECTORY  pkDir = (PDIRECTORY) buf;
 | 
			
		||||
 | 
			
		||||
        for (unsigned int i = 0; i < 16; i++){
 | 
			
		||||
            // get current filename
 | 
			
		||||
            char name[11];
 | 
			
		||||
            memcpy(name, pkDir->Filename, 11);
 | 
			
		||||
            name[11] = 0;
 | 
			
		||||
 | 
			
		||||
            if(strncmp(name, DosFileName, 11) == 0){
 | 
			
		||||
                strcpy(file.name, filename);
 | 
			
		||||
                file.id = 0;
 | 
			
		||||
                file.currentCluster = pkDir->FirstCluster;
 | 
			
		||||
                file.filelength = pkDir->FileSize;
 | 
			
		||||
                file.eof = 0;
 | 
			
		||||
 | 
			
		||||
                // set file type;
 | 
			
		||||
                if(pkDir->Attrib == 0x10){
 | 
			
		||||
                    file.flags = FS_DIRECTORY;
 | 
			
		||||
                } else{
 | 
			
		||||
                    file.flags = FS_FILE;
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                return file;
 | 
			
		||||
            }
 | 
			
		||||
            // go to next entry
 | 
			
		||||
            pkDir++;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    // unable to find file
 | 
			
		||||
    file.flags = FS_INVALID;
 | 
			
		||||
    return file;
 | 
			
		||||
}
 | 
			
		||||
*/
 | 
			
		||||
 | 
			
		||||
void FileSystem::initialize()
 | 
			
		||||
{
 | 
			
		||||
    MBR* mbr = getPartitions();
 | 
			
		||||
    BiosParameterBlock* bootsector =  getBPB(mbr);
 | 
			
		||||
    listFilesInRoot(*mbr, *bootsector);
 | 
			
		||||
 | 
			
		||||
    free(mbr);
 | 
			
		||||
    free(bootsector);
 | 
			
		||||
/*
 | 
			
		||||
    mountInfo.numSectors =  bootsector->NumberOfSectorsPerFAT;
 | 
			
		||||
    mountInfo.fatOffset = 1;
 | 
			
		||||
    mountInfo.fatSize = bootsector->NumberOfSectorsPerFAT;
 | 
			
		||||
    mountInfo.fatEntrySize = 8;
 | 
			
		||||
    mountInfo.numRootEntries = bootsector->NumberOfDirectoryEntries;
 | 
			
		||||
    mountInfo.rootOffset = (bootsector->NumberOfFileAllocationTables * bootsector->NumberOfSectorsPerFAT) + 1;
 | 
			
		||||
    mountInfo.rootSize = (bootsector->NumberOfDirectoryEntries * 32) / bootsector->BytesPerSector;
 | 
			
		||||
*/
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
char* FindNextEntryName (char* path )
 | 
			
		||||
{
 | 
			
		||||
    int length = strlen(path);
 | 
			
		||||
 | 
			
		||||
    char* name = path;
 | 
			
		||||
    int i = 0;
 | 
			
		||||
 | 
			
		||||
    if( name[0] == '/')
 | 
			
		||||
        i++;
 | 
			
		||||
 | 
			
		||||
    while ( name[i] != '/' && i <= length)
 | 
			
		||||
        i++;
 | 
			
		||||
 | 
			
		||||
    char* s = (char*) malloc(i + 1 * sizeof(char));
 | 
			
		||||
    for ( int a = 0; a < i; a++)
 | 
			
		||||
        s[a] = path[a];
 | 
			
		||||
 | 
			
		||||
    s[i + 1] = '\0';
 | 
			
		||||
 | 
			
		||||
    return s;
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
void FileSystem::ResolvePath(Path &path)
 | 
			
		||||
{
 | 
			
		||||
    // See reference material (1) https://man7.org/linux/man-pages/man7/path_resolution.7.html
 | 
			
		||||
 | 
			
		||||
    char* string_path  = path.str();
 | 
			
		||||
    void* cpy = string_path;
 | 
			
		||||
 | 
			
		||||
    bool isAbsolutePath = string_path[0] == '/';
 | 
			
		||||
    if(isAbsolutePath)
 | 
			
		||||
    {
 | 
			
		||||
        // strip the first slash
 | 
			
		||||
        string_path++;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    char* entry_name = FindNextEntryName(string_path);
 | 
			
		||||
    printf("Look for entry with name: %s\n", entry_name);
 | 
			
		||||
    int skip = strlen(entry_name);
 | 
			
		||||
    free(entry_name);
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    entry_name = FindNextEntryName(string_path + skip);
 | 
			
		||||
    printf("Look for entry with name: %s\n", entry_name);
 | 
			
		||||
    skip = strlen(entry_name);
 | 
			
		||||
    free(entry_name);
 | 
			
		||||
 | 
			
		||||
    free(cpy);
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										80
									
								
								kernel/vfs/VFS.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										80
									
								
								kernel/vfs/VFS.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,80 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
#include <stdint.h>
 | 
			
		||||
#include "../../CoreLib/Path.h"
 | 
			
		||||
 | 
			
		||||
#define FS_FILE 0
 | 
			
		||||
#define FS_DIRECTORY 1
 | 
			
		||||
#define FS_INVALID 2
 | 
			
		||||
#define DEVICE_MAX 26
 | 
			
		||||
 | 
			
		||||
typedef struct _FILE {
 | 
			
		||||
    char name [32];
 | 
			
		||||
    uint32_t flags;
 | 
			
		||||
    uint32_t filelength;
 | 
			
		||||
    uint32_t id;
 | 
			
		||||
    uint32_t eof;
 | 
			
		||||
    uint32_t position;
 | 
			
		||||
    uint32_t currentCluster;
 | 
			
		||||
    uint32_t device;
 | 
			
		||||
}FILE, *PFILE;
 | 
			
		||||
 | 
			
		||||
typedef struct _FILE_SYSTEM{
 | 
			
		||||
    char name[8];
 | 
			
		||||
    FILE (*Directory) (const char* Directoryname);
 | 
			
		||||
    void (*Mount) ();
 | 
			
		||||
    void (*Read) (PFILE file, unsigned char* buffer, unsigned int length);
 | 
			
		||||
    void (Close) (PFILE);
 | 
			
		||||
    FILE (*Open) (const char* filename);
 | 
			
		||||
}FILESYSTEM, *PFILESYSTEM;
 | 
			
		||||
 | 
			
		||||
typedef struct _MOUNT_INFO{
 | 
			
		||||
    uint32_t numSectors;
 | 
			
		||||
    uint32_t fatOffset;
 | 
			
		||||
    uint32_t numRootEntries;
 | 
			
		||||
    uint32_t rootOffset;
 | 
			
		||||
    uint32_t rootSize;
 | 
			
		||||
    uint32_t fatSize;
 | 
			
		||||
    uint32_t fatEntrySize;
 | 
			
		||||
}MOUNT_INFO, *PMOUNT_INFO;
 | 
			
		||||
 | 
			
		||||
typedef struct _DIRECTORY{
 | 
			
		||||
    uint8_t Filename[8];
 | 
			
		||||
    uint8_t Ext[3];
 | 
			
		||||
    uint8_t Attrib;
 | 
			
		||||
    uint8_t Reserved;
 | 
			
		||||
    uint8_t TimeCreatedMs;
 | 
			
		||||
    uint16_t TimeCreated;
 | 
			
		||||
    uint16_t DateCreated;
 | 
			
		||||
    uint16_t DateLastAccessed;
 | 
			
		||||
    uint16_t FirstClusterHiBytes;
 | 
			
		||||
    uint16_t LastModTime;
 | 
			
		||||
    uint16_t LastModDate;
 | 
			
		||||
    uint16_t FirstCluster;
 | 
			
		||||
    uint32_t FileSize;
 | 
			
		||||
}DIRECTORY, *PDIRECTORY;
 | 
			
		||||
// Date Format
 | 
			
		||||
// [0..4] Day
 | 
			
		||||
// [5..8] Month
 | 
			
		||||
// [9..15] Year
 | 
			
		||||
 | 
			
		||||
// Time Format
 | 
			
		||||
// [0..4] Seconds
 | 
			
		||||
// [5..10] Minute
 | 
			
		||||
// [11..15] Hour
 | 
			
		||||
extern PFILESYSTEM _filesystems[DEVICE_MAX];
 | 
			
		||||
 | 
			
		||||
 FILE volOpenFile(const char* fname);
 | 
			
		||||
 | 
			
		||||
 void volCloseFile(PFILE file);
 | 
			
		||||
 void volRegisterFilesystem(PFILESYSTEM, unsigned int deviceID);
 | 
			
		||||
 void volUnregisterFilesystem(PFILESYSTEM);
 | 
			
		||||
 void volUnregisterFileSystemByID(unsigned int deviceID);
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 class FileSystem{
 | 
			
		||||
 public:
 | 
			
		||||
     static void initialize();
 | 
			
		||||
 | 
			
		||||
     static void ResolvePath(Path& path);
 | 
			
		||||
 | 
			
		||||
 };
 | 
			
		||||
		Reference in New Issue
	
	Block a user