2017-02-19 23:55:54 +00:00
|
|
|
#ifndef __FILEMANAGER_H
|
|
|
|
#define __FILEMANAGER_H
|
|
|
|
|
|
|
|
#include <stdint.h>
|
|
|
|
|
|
|
|
#define MAXFILES 4 // how many results we can simultaneously manage
|
|
|
|
#define DIRPAGESIZE 10 // how many results in one readDir
|
|
|
|
#ifndef MAXPATH
|
|
|
|
#define MAXPATH 255
|
|
|
|
#endif
|
|
|
|
|
2017-12-30 20:20:34 +00:00
|
|
|
#define FMMAGIC 'F'
|
|
|
|
|
2020-06-28 12:29:51 +00:00
|
|
|
#ifndef SEEK_SET
|
|
|
|
#define SEEK_SET 0
|
|
|
|
#endif
|
|
|
|
#ifndef SEEK_CUR
|
|
|
|
#define SEEK_CUR 1
|
|
|
|
#endif
|
|
|
|
|
2017-02-19 23:55:54 +00:00
|
|
|
class FileManager {
|
|
|
|
public:
|
|
|
|
virtual ~FileManager() {};
|
|
|
|
|
2020-06-28 19:24:49 +00:00
|
|
|
#define writeByte(fd,x) {static uint8_t c = x; write(outfd, &c, 1);}
|
|
|
|
|
2017-12-30 20:20:34 +00:00
|
|
|
virtual bool SerializeFile(int8_t outfd, int8_t fd) {
|
|
|
|
writeByte(outfd, FMMAGIC);
|
|
|
|
|
|
|
|
if (fd == -1 ||
|
|
|
|
cachedNames[fd][0] == '\0') {
|
|
|
|
|
|
|
|
// No file to cache; we're done
|
|
|
|
writeByte(outfd, 0);
|
|
|
|
writeByte(outfd, FMMAGIC);
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
// have a file to cache; set a marker and continue
|
|
|
|
writeByte(outfd, 1);
|
|
|
|
|
|
|
|
int8_t l = 0;
|
|
|
|
char *p = cachedNames[fd];
|
|
|
|
while (*p) {
|
|
|
|
l++;
|
|
|
|
p++;
|
|
|
|
}
|
|
|
|
|
|
|
|
writeByte(outfd, l);
|
|
|
|
for (int i=0; i<l; i++) {
|
|
|
|
writeByte(outfd, cachedNames[fd][i]);
|
|
|
|
}
|
|
|
|
|
|
|
|
writeByte(outfd, (fileSeekPositions[fd] >> 24) & 0xFF);
|
|
|
|
writeByte(outfd, (fileSeekPositions[fd] >> 16) & 0xFF);
|
|
|
|
writeByte(outfd, (fileSeekPositions[fd] >> 8) & 0xFF);
|
|
|
|
writeByte(outfd, (fileSeekPositions[fd] ) & 0xFF);
|
|
|
|
|
|
|
|
writeByte(outfd, FMMAGIC);
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
virtual int8_t DeserializeFile(int8_t infd) {
|
2020-06-28 19:24:49 +00:00
|
|
|
uint8_t b;
|
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
if (b != FMMAGIC)
|
|
|
|
return -1;
|
|
|
|
|
|
|
|
if (read(infd, &b, 1) != 1)
|
2017-12-30 20:20:34 +00:00
|
|
|
return -1;
|
|
|
|
|
2020-06-28 19:24:49 +00:00
|
|
|
if (b == 0) {
|
2017-12-30 20:20:34 +00:00
|
|
|
// No file was cached. Verify footer and we're done without error
|
2020-06-28 19:24:49 +00:00
|
|
|
|
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
if (b != FMMAGIC) {
|
2017-12-30 20:20:34 +00:00
|
|
|
// FIXME: no way to raise this error.
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
|
|
|
char buf[MAXPATH];
|
2020-06-28 19:24:49 +00:00
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
|
|
|
|
int8_t len = b;
|
|
|
|
for (int i=0; i<len; i++) {
|
|
|
|
if (read(infd, &buf[i], 1) != 1)
|
|
|
|
return false;
|
2017-12-30 20:20:34 +00:00
|
|
|
}
|
2020-06-28 19:24:49 +00:00
|
|
|
buf[len] = '\0';
|
2017-12-30 20:20:34 +00:00
|
|
|
|
|
|
|
int8_t ret = openFile(buf);
|
|
|
|
if (ret == -1)
|
|
|
|
return ret;
|
|
|
|
|
2020-06-28 19:24:49 +00:00
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
fileSeekPositions[ret] <<= 8; fileSeekPositions[ret] |= b;
|
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
fileSeekPositions[ret] <<= 8; fileSeekPositions[ret] |= b;
|
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
fileSeekPositions[ret] <<= 8; fileSeekPositions[ret] |= b;
|
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
fileSeekPositions[ret] <<= 8; fileSeekPositions[ret] |= b;
|
|
|
|
|
|
|
|
if (read(infd, &b, 1) != 1)
|
|
|
|
return -1;
|
|
|
|
if (b != FMMAGIC)
|
2017-12-30 20:20:34 +00:00
|
|
|
return -1;
|
|
|
|
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
2017-02-19 23:55:54 +00:00
|
|
|
virtual int8_t openFile(const char *name) = 0;
|
|
|
|
virtual void closeFile(int8_t fd) = 0;
|
|
|
|
|
|
|
|
virtual const char *fileName(int8_t fd) = 0;
|
|
|
|
|
2020-07-11 11:39:56 +00:00
|
|
|
virtual int16_t readDir(const char *where, const char *suffix, char *outputFN, int16_t startIdx, uint16_t maxlen) = 0;
|
|
|
|
virtual void closeDir() = 0;
|
2017-12-29 19:08:49 +00:00
|
|
|
|
2018-02-07 15:20:26 +00:00
|
|
|
virtual void getRootPath(char *toWhere, int8_t maxLen) = 0;
|
|
|
|
|
2019-02-20 16:51:55 +00:00
|
|
|
virtual uint32_t getSeekPosition(int8_t fd) {
|
|
|
|
return fileSeekPositions[fd];
|
|
|
|
};
|
|
|
|
|
2019-02-21 03:06:55 +00:00
|
|
|
virtual bool setSeekPosition(int8_t fd, uint32_t pos) = 0;
|
2019-02-20 16:51:55 +00:00
|
|
|
virtual void seekToEnd(int8_t fd) = 0;
|
|
|
|
|
2020-06-28 13:21:27 +00:00
|
|
|
virtual int write(int8_t fd, const void *buf, int nbyte) = 0;
|
|
|
|
virtual int read(int8_t fd, void *buf, int nbyte) = 0;
|
|
|
|
virtual int lseek(int8_t fd, int offset, int whence) = 0;
|
2022-01-07 17:50:13 +00:00
|
|
|
|
|
|
|
virtual void flush() = 0;
|
|
|
|
|
2017-12-30 20:20:34 +00:00
|
|
|
protected:
|
2020-07-03 02:02:21 +00:00
|
|
|
volatile unsigned long fileSeekPositions[MAXFILES];
|
2017-12-30 20:20:34 +00:00
|
|
|
char cachedNames[MAXFILES][MAXPATH];
|
|
|
|
|
2017-02-19 23:55:54 +00:00
|
|
|
};
|
|
|
|
|
2020-06-28 19:24:49 +00:00
|
|
|
#undef writeByte
|
|
|
|
|
2017-02-19 23:55:54 +00:00
|
|
|
#endif
|