const long file_handle_timeout = 30; class FileHandle; // base class for file handles class FileHandle { public: virtual ~FileHandle(); FileHandle(const char* name, const char* real_name); // assigns name virtual int Open()=0; // opens (maybe fails) virtual int Close()=0; virtual int Stat(struct lufs_fattr *fattr)=0; virtual int Read(long long pos, unsigned long length, char* buf)=0; virtual const char* Identity() { return "FileHandle"; } typedef vector Array; string name; // virtual name string real_name; // name of the real file on disk // don't close this before time(0)>timeout void KeepAlive(); bool IsTimedOut(time_t t); protected: time_t timeout; }; class FileHandleArray : public FileHandle::Array { public: FileHandleArray() {} virtual ~FileHandleArray() {} // finds handle by name, returns 0 if no handle in stock FileHandle* Find( const char* name ); // Deletes a named handle, does nothing fi it does not exist int Delete( const char* name ); // Inserts a named handle void Insert( FileHandle* handle ); // removes timed out handles void Cleanup(); }; class FileHandle_Default : public FileHandle { public: FileHandle_Default(const char* name, const char* real_name); ~FileHandle_Default(); int Open(); int Stat(struct lufs_fattr *fattr); int Read(long long pos, unsigned long length, char* buf); int Close(); virtual const char* Identity() { return "FileHandle_Default"; } protected: int handle; }; // pipes the output from a command (typically a decompressor) and caches it // so that we can seek it afterwards. class SeekablePipe: public FileHandle { public: // name and real_name are inherited from FileHandle SeekablePipe(const char* name, const char* real_name, const char* cmd); ~SeekablePipe(); int Open(); int Stat(struct lufs_fattr *fattr); int Read(long long pos, unsigned long length, char* buf); int Close(); virtual const char* Identity() { return "SeekablePipe"; } protected: int Cache(long long upto); long long already_read; bool eof; FILE *pipe; FILE *tmp_file; string command; }; // handles a compressed wave file class FileHandle_XWav : public SeekablePipe { public: FileHandle_XWav(const char* name, const char* real_name, const char* cmd); ~FileHandle_XWav(); int Stat(struct lufs_fattr *fattr); virtual const char* Identity() { return "FileHandle_XWav"; } protected: }; class FileHandle_Flac : public FileHandle_XWav { public: FileHandle_Flac(const char* name, const char* real_name); virtual const char* Identity() { return "FileHandle_Flac"; } protected: }; /* class FileHandle_Ogg : public FileHandle_XWav { public: FileHandle_Ogg(const char* name, const char* real_name); virtual const char* Identity() { return "FileHandle_Ogg"; } protected: }; class FileHandle_MP3 : public FileHandle_XWav { public: FileHandle_MP3(const char* name, const char* real_name); virtual const char* Identity() { return "FileHandle_MP3"; } protected: }; */