1 /* 2 * Copyright 2003-2013, Axel Dörfler, axeld@pinc-software.de. 3 * Copyright 2008, François Revol <revol@free.fr> 4 * Distributed under the terms of the MIT License. 5 */ 6 7 8 #include "File.h" 9 10 #include <sys/stat.h> 11 #include <unistd.h> 12 13 #include "Directory.h" 14 15 16 //#define TRACE(x) dprintf x 17 #define TRACE(x) do {} while (0) 18 19 20 namespace FATFS { 21 22 23 File::File(Volume &volume, off_t dirEntryOffset, uint32 cluster, off_t size, 24 const char *name) 25 : 26 fVolume(volume), 27 fStream(volume, cluster, size, name), 28 fDirEntryOffset(dirEntryOffset) 29 { 30 TRACE(("FATFS::File::()\n")); 31 } 32 33 34 File::~File() 35 { 36 TRACE(("FATFS::File::~()\n")); 37 } 38 39 40 status_t 41 File::InitCheck() 42 { 43 if (fStream.InitCheck() != B_OK) 44 return fStream.InitCheck(); 45 46 return B_OK; 47 } 48 49 50 status_t 51 File::Open(void **_cookie, int mode) 52 { 53 TRACE(("FATFS::File::%s(, %d)\n", __FUNCTION__, mode)); 54 if (fStream.InitCheck() < B_OK) 55 return fStream.InitCheck(); 56 57 return Node::Open(_cookie, mode); 58 } 59 60 61 status_t 62 File::Close(void *cookie) 63 { 64 return Node::Close(cookie); 65 } 66 67 68 ssize_t 69 File::ReadAt(void *cookie, off_t pos, void *buffer, size_t bufferSize) 70 { 71 TRACE(("FATFS::File::%s(, %lld,, %d)\n", __FUNCTION__, pos, bufferSize)); 72 status_t err; 73 err = fStream.ReadAt(pos, buffer, &bufferSize); 74 if (err < B_OK) 75 return err; 76 return bufferSize; 77 } 78 79 80 ssize_t 81 File::WriteAt(void *cookie, off_t pos, const void *buffer, size_t bufferSize) 82 { 83 off_t streamSize = fStream.Size(); 84 uint32 firstCluster = fStream.FirstCluster(); 85 86 // write data 87 size_t written = bufferSize; 88 status_t error = fStream.WriteAt(pos, buffer, &written); 89 if (error != B_OK) 90 return error; 91 92 // If the file size has changed, we need to adjust the directory entry. 93 if (fStream.Size() > streamSize || fStream.FirstCluster() != firstCluster) { 94 error = Directory::UpdateDirEntry(fVolume, fDirEntryOffset, 95 fStream.FirstCluster(), fStream.Size()); 96 if (error != B_OK) 97 return error; 98 // TODO: Undo the changes! 99 } 100 101 return written; 102 } 103 104 105 status_t 106 File::GetName(char *nameBuffer, size_t bufferSize) const 107 { 108 return fStream.GetName(nameBuffer, bufferSize); 109 } 110 111 112 status_t 113 File::GetFileMap(struct file_map_run *runs, int32 *count) 114 { 115 return fStream.GetFileMap(runs, count); 116 } 117 118 119 int32 120 File::Type() const 121 { 122 return S_IFREG; 123 } 124 125 126 off_t 127 File::Size() const 128 { 129 return fStream.Size(); 130 } 131 132 133 ino_t 134 File::Inode() const 135 { 136 return fStream.FirstCluster() << 16; 137 } 138 139 140 } // namespace FATFS 141