= GIET-VM / FAT32 Handler = [[PageOutline]] The [source:soft/giet_vm/giet_fat32/fat32.c fat32.c] and [source:soft/giet_vm/giet_fat32/fat32.h fat32.h] files define the data structures and functions that are used to access a FAT32 file system stored on a mass storage block device (such as the [wiki:bdv_driver BDV], [wiki:hba_driver HBA], [wiki:sdc_driver SDC], or [wiki:rdk_driver RDK] peripherals). All the block device peripherals support a polling mode on the peripheral status register to detect the completion of a read or write access to the device, but some peripheral (BDV and HBA) support a descheduling mode for the calling task, with an interrupt to signal transfer completion. The GIET-VM handler supports the 4 peripheral types (only one type in a given platform), and most of the FAT access functions support a specific argument to activate the descheduling/IRQ mode when it is supported by the hardware. As a general rule the GIET-VM boot-loader uses only the polling mode, and the GIET-VM kernel uses the descheduling + IRQ mode to handle the user system calls. All these functions are prefixed by ''_'' to remind that they can only be executed by a processor in kernel mode. == Kernel-level FAT32 access functions == === 1) int '''_fat_init'''( unsigned int use_irq ) === This function initialises the kernel ''_fat'' structure describing the FAT32 file system, including the set of open files, and the FAT cache (only one single 512 bytes block at the moment). The '''use_irq''' argument define the requested access mode (polling / descheduling), but both the GIET-VM boot-loader and the GIET-VM kernel use the polling mode for FAT initialisation. Return 0 in case of success, exit if error. === 2) int '''_fat_open'''( unsigned int use_irq , char* pathname , unsigned int create ) === This function open a file, register it in the set of open files, and return a file descriptor index (fd_id) that must be used by all other access functions. * '''use_irq''' : Boolean => request to use the descheduling mode when non zero. * '''pathname''' : file absolute path name from the root directory. * ''' create''' : Boolean => request to create the file if it does not exist (Not supported yet). Returns fd_id if success, returns -1 if file not found). === 3) int '''_fat_read'''( unsigned int use_irq , unsigned int fd_id , void* buffer , unsigned int count , unsigned int offset ) === This function transfer an integer number of blocks from an open file (identified by the fd_id) to a memory buffer, after checking the arguments. If the number of requested sectors exceeds the file size, this number of loaded sectors is reduced. * '''use_irq''' : Boolean => request to use the descheduling mode when non zero. * '''fd_id''' : file descriptor index * '''buffer''' : memory buffer virtual base address * '''count''' : number of blocks to transfer * '''offset''' : number of blocks to skip in file Returns number of sectors transfered if success, returns -1 if error. === 4) int '''_fat_write( unsigned int use_irq , unsigned int fd_id , void* buffer , unsigned int count , unsigned int offset ) === This function transfer an integer number of blocks from a memory buffer to an open file (identified by the fd_id), after checking the arguments. It allocates new clusters on the block device if (offset + count) is larger than the current file size. * '''use_irq''' : Boolean => request to use the descheduling mode when non zero. * '''fd_id''' : file descriptor index * '''buffer''' : memory buffer virtual base address * '''count''' : number of blocks to transfer * '''offset''' : number of blocks to skip in file Returns number of sectors written if success, returns -1 if error. === 5) int '''_fat_fstat'''( unsigned int fd_id ) === Return the file size (bytes) for a file identified by the fd_id. === 6) int '''_fat_close'''( unsigned int fd_id ) === This function removes a file identified by the fd_id from the set of open files. === 7) int '''_fat_ioc_access'''( unsigned int use_irq , unsigned int to_mem , unsigned int lba , unsigned int buf_vaddr , unsigned int count ) === This function is acting as a generic block device driver: all the previous functions use this last function to access the available block device, depending on the USE_IOC_BDV / USE_IOC_HBA / USE_IOC_SDC / USE_IOC_RDK flags defined in the ''hard_config.h'' file. It computes the buffer physical address, and check access rights. * '''use_irq''' : Boolean => request to use the descheduling mode when non zero. * '''to_mem''' : Boolean => to memory transfer when non zero. * '''lba''' : first block index on the block device. * '''buf_vaddr''' : memory buffer virtual base address * '''count''' : number of blocks to transfer Returns 0 if success, returns -1 if error. == User level FAT32 access functions == These functions are used by the kernel to handle the user system calls. They should be modified to respect the UNIX specification. === 1) int '''_fat_user_open'''( char* pathname , unsigned int flags ) === === 2) int '''_fat_user_read'''( unsigned int fd , void* buffer , unsigned int count , unsigned int offset ) === === 3) int '''_fat_user_write'''( unsigned int fd , void* buffer , unsigned int count , unsigned int offset ) === === 4) int '''_fat_user_lseek( unsigned int fd , unsigned int offset , unsigned int whence ) ===