2
Copyright (C) 2010 Paul Davis
4
This program is free software; you can redistribute it and/or modify
5
it under the terms of the GNU General Public License as published by
6
the Free Software Foundation; either version 2 of the License, or
7
(at your option) any later version.
9
This program is distributed in the hope that it will be useful,
10
but WITHOUT ANY WARRANTY; without even the implied warranty of
11
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
GNU General Public License for more details.
14
You should have received a copy of the GNU General Public License
15
along with this program; if not, write to the Free Software
16
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20
#ifndef __pbd_file_manager_h__
21
#define __pbd_file_manager_h__
23
#include <sys/types.h>
27
#include <glibmm/threads.h>
28
#include "pbd/signals.h"
34
/** Parent class for FileDescriptors.
36
* When a subclass is instantiated, the file it describes is added to a
37
* list. The FileDescriptor can be `allocated', meaning that its
38
* file will be opened on the filesystem, and can then be `released'.
39
* FileDescriptors are reference counted as they are allocated and
40
* released. When a descriptor's refcount is 0, the file on the
41
* filesystem is eligible to be closed if necessary to free up file
42
* handles for other files.
44
* The upshot of all this is that Ardour can manage the number of
45
* open files to stay within limits imposed by the operating system.
51
FileDescriptor (std::string const &, bool);
52
virtual ~FileDescriptor () {}
54
const std::string& path() const { return _path; }
57
virtual void set_path (const std::string&);
59
/** Emitted when the file is closed */
60
PBD::Signal0<void> Closed;
64
friend class FileManager;
66
/* These methods and variables must be called / accessed
67
with a lock held on the FileManager's mutex
70
/** @return false on success, true on failure */
71
virtual bool open () = 0;
72
virtual void close () = 0;
73
virtual bool is_open () const = 0;
75
int _refcount; ///< number of active users of this file
76
double _last_used; ///< monotonic time that this file was last allocated
77
std::string _path; ///< file path
78
bool _writeable; ///< true if it should be opened writeable, otherwise false
80
FileManager* manager ();
84
static FileManager* _manager;
88
/** FileDescriptor for a file to be opened using POSIX open */
89
class FdFileDescriptor : public FileDescriptor
92
FdFileDescriptor (std::string const & file_name, bool writeable, mode_t mode);
99
friend class FileManager;
103
bool is_open () const;
105
int _fd; ///< file descriptor, or -1 if the file is closed
106
mode_t _mode; ///< mode to use when creating files
109
/** FileDescriptor for a file opened using stdio */
110
class StdioFileDescriptor : public FileDescriptor
113
StdioFileDescriptor (std::string const & file_name, std::string const & mode);
114
~StdioFileDescriptor ();
120
friend class FileManager;
124
bool is_open () const;
131
/** Class to limit the number of files held open */
137
void add (FileDescriptor *);
138
void remove (FileDescriptor *);
140
void release (FileDescriptor *);
141
bool allocate (FileDescriptor *);
145
void close (FileDescriptor *);
147
std::list<FileDescriptor*> _files; ///< files we know about
148
Glib::Threads::Mutex _mutex; ///< mutex for _files, _open and FileDescriptor contents
149
int _open; ///< number of open files
150
int _max_open; ///< maximum number of open files