You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

184 satır
4.9KB

  1. /* Teensyduino Core Library - File base class
  2. * http://www.pjrc.com/teensy/
  3. * Copyright (c) 2020 PJRC.COM, LLC.
  4. *
  5. * Permission is hereby granted, free of charge, to any person obtaining
  6. * a copy of this software and associated documentation files (the
  7. * "Software"), to deal in the Software without restriction, including
  8. * without limitation the rights to use, copy, modify, merge, publish,
  9. * distribute, sublicense, and/or sell copies of the Software, and to
  10. * permit persons to whom the Software is furnished to do so, subject to
  11. * the following conditions:
  12. *
  13. * 1. The above copyright notice and this permission notice shall be
  14. * included in all copies or substantial portions of the Software.
  15. *
  16. * 2. If the Software is incorporated into a build system that allows
  17. * selection among a list of target devices, then similar target
  18. * devices manufactured by PJRC.COM must be included in the list of
  19. * target devices and selectable in the same manner.
  20. *
  21. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  22. * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
  23. * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  24. * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
  25. * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
  26. * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  27. * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  28. * SOFTWARE.
  29. */
  30. #ifndef FS_H
  31. #define FS_H
  32. #ifdef __cplusplus
  33. #include <Arduino.h>
  34. #define FILE_READ 0
  35. #define FILE_WRITE 1
  36. #define FILE_WRITE_BEGIN 2
  37. enum SeekMode {
  38. SeekSet = 0,
  39. SeekCur = 1,
  40. SeekEnd = 2
  41. };
  42. //#define FILE_WHOAMI
  43. class File : public Stream {
  44. public:
  45. File() : f(nullptr) { }
  46. File(File *file) {
  47. // "file" must only be a class derived from File
  48. // can we use is_same or is_polymorphic with static_assert?
  49. // or is_base_of
  50. //static_assert(std::is_same<decltype(*file),File>::value,
  51. //"File(File *file) constructor only accepts pointers "
  52. //"to derived classes, not File itself");
  53. f = file;
  54. if (f) f->refcount++;
  55. }
  56. File(const File &file) {
  57. //Serial.println("File copy constructor");
  58. //static int copycount=0;
  59. //if (++copycount > 20) while (1) ;
  60. f = file.f;
  61. if (f) f->refcount++;
  62. }
  63. File& operator = (const File &file) {
  64. //Serial.println("File assignment");
  65. //static int assigncount=0;
  66. //if (++assigncount > 20) while (1) ;
  67. invalidate();
  68. f = file.f;
  69. if (f) f->refcount++;
  70. return *this;
  71. }
  72. virtual ~File() {
  73. invalidate();
  74. }
  75. #ifdef FILE_WHOAMI
  76. virtual void whoami() { // testing only
  77. Serial.printf(" File this=%x, f=%x\n", (int)this, (int)f);
  78. if (f) f->whoami();
  79. }
  80. unsigned int getRefcount() { // testing only
  81. return refcount;
  82. }
  83. #endif
  84. virtual size_t read(void *buf, size_t nbyte) {
  85. return (f) ? f->read(buf, nbyte) : 0;
  86. }
  87. virtual size_t write(const void *buf, size_t size) {
  88. return (f) ? f->write(buf, size) : 0;
  89. }
  90. virtual int available() {
  91. return (f) ? f->available() : 0;
  92. }
  93. virtual int peek() {
  94. return (f) ? f->peek() : -1;
  95. }
  96. virtual void flush() {
  97. if (f) f->flush();
  98. }
  99. virtual bool truncate(uint64_t size=0) {
  100. return (f) ? f->truncate(size) : false;
  101. }
  102. virtual bool seek(uint64_t pos, int mode) {
  103. return (f) ? f->seek(pos, mode) : false;
  104. }
  105. virtual uint64_t position() {
  106. return (f) ? f->position() : 0;
  107. }
  108. virtual uint64_t size() {
  109. return (f) ? f->size() : 0;
  110. }
  111. virtual void close() {
  112. if (f) f->close();
  113. }
  114. virtual operator bool() {
  115. return (f) ? (bool)*f : false;
  116. }
  117. virtual const char* name() {
  118. return (f) ? f->name() : "";
  119. }
  120. virtual bool isDirectory() {
  121. return (f) ? f->isDirectory() : false;
  122. }
  123. virtual File openNextFile(uint8_t mode=0) {
  124. return (f) ? f->openNextFile(mode) : *this;
  125. }
  126. virtual void rewindDirectory(void) {
  127. if (f) f->rewindDirectory();
  128. }
  129. bool seek(uint64_t pos) {
  130. return seek(pos, SeekSet);
  131. }
  132. int read() {
  133. if (!f) return -1;
  134. unsigned char b;
  135. if (f->read(&b, 1) < 1) return -1;
  136. return b;
  137. }
  138. size_t write(uint8_t b) {
  139. return write(&b, 1);
  140. }
  141. size_t write(const char *str) {
  142. return write(str, strlen(str));
  143. }
  144. size_t readBytes(char *buffer, size_t length) {
  145. return read(buffer, length);
  146. }
  147. private:
  148. void invalidate() {
  149. if (f && --(f->refcount) == 0) delete f;
  150. }
  151. union {
  152. // instances of base File class use this pointer
  153. File *f;
  154. // instances of derived classes (which actually access media)
  155. // use this reference count which is managed by the base class
  156. unsigned int refcount;
  157. };
  158. };
  159. class FS
  160. {
  161. public:
  162. FS() {}
  163. virtual File open(const char *filename, uint8_t mode = FILE_READ);
  164. virtual bool exists(const char *filepath);
  165. virtual bool mkdir(const char *filepath);
  166. virtual bool rename(const char *oldfilepath, const char *newfilepath);
  167. virtual bool remove(const char *filepath);
  168. virtual bool rmdir(const char *filepath);
  169. virtual uint64_t usedSize();
  170. virtual uint64_t totalSize();
  171. };
  172. #endif // __cplusplus
  173. #endif // FS_H