|
1 /****************************************************************************** |
|
2 * |
|
3 * |
|
4 * |
|
5 * Copyright (C) 1997-2008 by Dimitri van Heesch. |
|
6 * |
|
7 * Permission to use, copy, modify, and distribute this software and its |
|
8 * documentation under the terms of the GNU General Public License is hereby |
|
9 * granted. No representations are made about the suitability of this software |
|
10 * for any purpose. It is provided "as is" without express or implied warranty. |
|
11 * See the GNU General Public License for more details. |
|
12 * |
|
13 * Documents produced by Doxygen are derivative works derived from the |
|
14 * input used in their production; they are not affected by this license. |
|
15 * |
|
16 */ |
|
17 |
|
18 #ifndef STORE_H |
|
19 #define STORE_H |
|
20 |
|
21 #include <qglobal.h> |
|
22 #include <stdio.h> |
|
23 |
|
24 #include "portable.h" |
|
25 |
|
26 /*! @brief Abstract interface for file based memory storage operations */ |
|
27 class StorageIntf |
|
28 { |
|
29 public: |
|
30 /*! Required by gcc */ |
|
31 virtual ~StorageIntf() {} |
|
32 /*! Read \a size bytes from the store into \a buf. */ |
|
33 virtual int read(char *buf,uint size) = 0; |
|
34 /*! Write \a size bytes from \a buf into the store. */ |
|
35 virtual int write(const char *buf,uint size) = 0; |
|
36 }; |
|
37 |
|
38 /*! @brief The Store is a file based memory manager. |
|
39 * |
|
40 * You can open the store using open(). Then obtain a handle via alloc() |
|
41 * followed by a sequence of write() commands to store information, |
|
42 * and finalize it using end(). |
|
43 * |
|
44 * Later on you locate the information |
|
45 * with seek() using the handle obtained with alloc(), and then use a |
|
46 * sequence of read() calls to read the information back. |
|
47 * |
|
48 * If no longer needed the storage space can be freed using release(). |
|
49 * |
|
50 * The store will dynamically grow the file on disk if needed. |
|
51 */ |
|
52 class Store : public StorageIntf |
|
53 { |
|
54 public: |
|
55 /*! Creates a store. */ |
|
56 Store(); |
|
57 |
|
58 /*! Releases the store object. Will close the underlying file if opened. */ |
|
59 ~Store(); |
|
60 |
|
61 /*! Opens the file underlying the store using \a name as the file name. |
|
62 * Returns 0 upon success, or -1 otherwise. |
|
63 */ |
|
64 int open(const char *name); |
|
65 |
|
66 /*! Allocates a handle to write to and read from. */ |
|
67 portable_off_t alloc(); |
|
68 |
|
69 /*! Writes \a size bytes in array \a buf to the store. |
|
70 * First alloc() has to be called. |
|
71 * \note The information can only be read after end() has been called. |
|
72 */ |
|
73 int write(const char *buf,uint size); |
|
74 |
|
75 /*! Ends the sequence of writes. |
|
76 * \note After this call, first alloc() has to be called |
|
77 * before new writes can be done. |
|
78 */ |
|
79 void end(); |
|
80 |
|
81 /*! Releases the memory corresponding to the handle returned with alloc() */ |
|
82 void release(portable_off_t handle); |
|
83 |
|
84 /*! Closes the store */ |
|
85 void close(); |
|
86 |
|
87 /*! Goes to the start of information corresponding to handle \a pos */ |
|
88 void seek(portable_off_t handle); |
|
89 |
|
90 /*! Reads \a size bytes from the store into the array pointed to be \a buf. |
|
91 * \note Before reading seek() has to be called to set the right start of the store. |
|
92 */ |
|
93 int read(char *buf,uint size); |
|
94 |
|
95 void printStats(); |
|
96 |
|
97 private: |
|
98 enum State |
|
99 { |
|
100 Init, |
|
101 Reading, |
|
102 Writing |
|
103 }; |
|
104 struct Node |
|
105 { |
|
106 portable_off_t pos; |
|
107 struct Node *next; |
|
108 }; |
|
109 void printFreeList(); |
|
110 FILE *m_file; |
|
111 portable_off_t m_front; |
|
112 Node *m_head; |
|
113 State m_state; |
|
114 int m_reads; |
|
115 int m_writes; |
|
116 }; |
|
117 |
|
118 #endif |