@@ -3,6 +3,7 @@ package fat32
33import (
44 "errors"
55 "fmt"
6+ "io"
67 iofs "io/fs"
78 "os"
89 "path"
@@ -509,7 +510,6 @@ func (fs *FileSystem) writeFat() error {
509510
510511// interface guard
511512var _ filesystem.FileSystem = (* FileSystem )(nil )
512- var _ iofs.FS = (* FileSystem )(nil )
513513
514514// Do cleaning job for fat32. Note that fat32 does not have side-effects so we do not do anything.
515515func (fs * FileSystem ) Close () error {
@@ -598,29 +598,23 @@ func (fs *FileSystem) Chown(_ string, _, _ int) error {
598598
599599// ReadDir return the contents of a given directory in a given filesystem.
600600//
601- // Returns a slice of os.FileInfo with all of the entries in the directory.
601+ // Returns a slice of iofs.DirEntry with all of the entries in the directory.
602602//
603603// Will return an error if the directory does not exist or is a regular file and not a directory
604- func (fs * FileSystem ) ReadDir (p string ) ([]os. FileInfo , error ) {
604+ func (fs * FileSystem ) ReadDir (p string ) ([]iofs. DirEntry , error ) {
605605 _ , entries , err := fs .readDirWithMkdir (p , false )
606606 if err != nil {
607607 return nil , fmt .Errorf ("error reading directory %s: %w" , p , err )
608608 }
609609 // once we have made it here, looping is done. We have found the final entry
610610 // we need to return all of the file info
611611 //nolint:prealloc // because the following loop may omit some entry
612- var ret []os. FileInfo
612+ var ret []iofs. DirEntry
613613 for _ , e := range entries {
614614 if e .isVolumeLabel {
615615 continue
616616 }
617- ret = append (ret , FileInfo {
618- modTime : e .modifyTime ,
619- name : e .filenameLong ,
620- shortName : shortNameFromDirEntry (e ),
621- size : int64 (e .fileSize ),
622- isDir : e .isSubdirectory ,
623- })
617+ ret = append (ret , e )
624618 }
625619 return ret , nil
626620}
@@ -713,6 +707,16 @@ func (fs *FileSystem) OpenFile(p string, flag int) (filesystem.File, error) {
713707 }, nil
714708}
715709
710+ // ReadFile implements ReadFileFS to read an entire file into memory
711+ func (fs * FileSystem ) ReadFile (name string ) ([]byte , error ) {
712+ f , err := fs .Open (name )
713+ if err != nil {
714+ return nil , err
715+ }
716+ defer f .Close ()
717+ return io .ReadAll (f )
718+ }
719+
716720// removes the named file or (empty) directory.
717721func (fs * FileSystem ) Remove (pathname string ) error {
718722 // get the path
@@ -837,6 +841,30 @@ func (fs *FileSystem) Rename(oldpath, newpath string) error {
837841 return nil
838842}
839843
844+ // Stat returns a FileInfo describing the file.
845+ func (fs * FileSystem ) Stat (name string ) (iofs.FileInfo , error ) {
846+ dir := path .Dir (name )
847+ basename := path .Base (name )
848+ des , err := fs .ReadDir (dir )
849+ if err != nil {
850+ return nil , fmt .Errorf ("could not read directory %s: %v" , dir , err )
851+ }
852+ // handle the root case
853+ if dir == basename && (basename == "/" || basename == "." ) {
854+ rootDir , _ , err := fs .readDirWithMkdir ("/" , false )
855+ if err != nil {
856+ return nil , fmt .Errorf ("could not read root directory: %v" , err )
857+ }
858+ return rootDir .Info ()
859+ }
860+ for _ , de := range des {
861+ if de .Name () == basename {
862+ return de .Info ()
863+ }
864+ }
865+ return nil , & iofs.PathError {Op : "stat" , Path : name , Err : fmt .Errorf ("file %s not found in directory %s" , basename , dir )}
866+ }
867+
840868// Label get the label of the filesystem from the secial file in the root directory.
841869// The label stored in the boot sector is ignored to mimic Windows behavior which
842870// only stores and reads the label from the special file in the root directory.
0 commit comments