| Disk ARchive 2.5.10 Full featured and portable backup and archiving tool

- Main Page
- Modules
- Namespaces
- Classes
- Files

- File List
- File Members

storage.hpp
Go to the documentation of this file.
1 /*********************************************************************/
2 // dar - disk archive - a backup/restoration program
3 // Copyright (C) 2002-2052 Denis Corbin
4 //
5 // This program is free software; you can redistribute it and/or
6 // modify it under the terms of the GNU General Public License
7 // as published by the Free Software Foundation; either version 2
8 // of the License, or (at your option) any later version.
9 //
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
14 //
15 // You should have received a copy of the GNU General Public License
16 // along with this program; if not, write to the Free Software
17 // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18 //
19 // to contact the author : http://dar.linux.free.fr/email.html
20 /*********************************************************************/
21
25
26 #include "../my_config.h"
27 #include "erreurs.hpp"
28 #include "integers.hpp"
29 #include "on_pool.hpp"
30
31 #ifdef LIBDAR_MODE
32 #include "infinint.hpp"
33 #endif
34
35 // it is necessary to not protect the previous inclusion inside
36 // the STORAGE_HPP protection to avoid cyclic dependancies.
37
38 #ifndef STORAGE_HPP
39 #define STORAGE_HPP
40
41 #ifndef LIBDAR_MODE
42 namespace libdar
43 {
44 class infinint;
45 }
46 #endif
47
48 namespace libdar
49 {
50 class generic_file;
51
53
56
57 class storage : public on_pool
58 {
59 private:
60 struct cellule
61 {
62 cellule() : next(nullptr), prev(nullptr), data(nullptr), size(0) {};
63 struct cellule *next, *prev;
64 unsigned char *data;
65 U_32 size;
66 };
67
68 public:
69 storage(U_32 size)
70 { make_alloc(size, first, last); };
71 storage(const infinint & size);
72 storage(const storage & ref)
73 { copy_from(ref); };
74 storage(generic_file & f, const infinint &size);
75 ~storage() throw(Ebug)
76 { detruit(first); };
77
78 const storage & operator = (const storage & val)
79 { detruit(first); copy_from(val); return *this; };
80
81 bool operator < (const storage & ref) const
82 { return difference(ref) < 0; }; // true if arg uses more space than this
83 bool operator == (const storage & ref) const
84 { return difference(ref) == 0; }; //true if arg have same space than this
85 bool operator > (const storage & ref) const
86 { return difference(ref) > 0; };
87 bool operator <= (const storage & ref) const
88 { return difference(ref) <= 0; };
89 bool operator >= (const storage & ref) const
90 { return difference(ref) >= 0; };
91 bool operator != (const storage & ref) const
92 { return difference(ref) != 0; };
93 unsigned char & operator [](infinint position);
94 unsigned char operator [](const infinint & position) const;
95 infinint size() const;
96 void clear(unsigned char val = 0);
97 void dump(generic_file & f) const;
98
99 class iterator : public on_pool
100 {
101 public :
102 iterator() : ref(nullptr), cell(nullptr), offset(0) {};
103 // default constructor by reference is OK
104 // default destructor is OK
105 // default operator = is OK
106
107 iterator operator ++ (S_I x)
108 { iterator ret = *this; skip_plus_one(); return ret; };
109 iterator operator -- (S_I x)
110 { iterator ret = *this; skip_less_one(); return ret; };
111 iterator & operator ++ ()
112 { skip_plus_one(); return *this; };
113 iterator & operator -- ()
114 { skip_less_one(); return *this; };
115 iterator operator + (U_32 s) const
116 { iterator ret = *this; ret += s; return ret; };
117 iterator operator - (U_32 s) const
118 { iterator ret = *this; ret -= s; return ret; };
119 iterator & operator += (U_32 s);
120 iterator & operator -= (U_32 s);
121 unsigned char &operator *() const;
122
123 void skip_to(const storage & st, infinint val); // absolute position in st
124 infinint get_position() const;
125
126 bool operator == (const iterator & cmp) const
127 { return ref == cmp.ref && cell == cmp.cell && offset == cmp.offset; };
128 bool operator != (const iterator & cmp) const
129 { return ! (*this == cmp); };
130
131 private:
132 static const U_32 OFF_BEGIN = 1;
133 static const U_32 OFF_END = 2;
134
135 const storage *ref;
136 struct cellule *cell;
137 U_32 offset;
138
139 void relative_skip_to(S_32 val);
140 bool points_on_data() const
141 { return ref != nullptr && cell != nullptr && offset < cell->size; };
142
143 inline void skip_plus_one();
144 inline void skip_less_one();
145
146 friend class storage;
147 };
148
149 // public storage methode using iterator
150
151 iterator begin() const
152 { iterator ret; ret.cell = first; if(ret.cell != nullptr) ret.offset = 0; else ret.offset = iterator::OFF_END; ret.ref = this; return ret; };
153 iterator end() const
154 { iterator ret; ret.cell = nullptr; ret.offset = iterator::OFF_END; ret.ref = this; return ret; };
155
156 // WARNING for the two following methods :
157 // there is no "reverse_iterator" type, unlike the standart lib,
158 // thus when going from rbegin() to rend(), you must use the -- operator
159 // unlike the stdlib, that uses the ++ operator. this is the only difference in use with stdlib.
160 iterator rbegin() const
161 { iterator ret; ret.cell = last; ret.offset = last != nullptr ? last->size-1 : 0; ret.ref = this; return ret; };
162 iterator rend() const
163 { iterator ret; ret.cell = nullptr, ret.offset = iterator::OFF_BEGIN; ret.ref = this; return ret; };
164
166
170 U_I write(iterator & it, unsigned char *a, U_I size);
171 U_I read(iterator & it, unsigned char *a, U_I size) const;
172 bool write(iterator & it, unsigned char a)
173 { return write(it, &a, 1) == 1; };
174 bool read(iterator & it, unsigned char &a) const
175 { return read(it, &a, 1) == 1; };
176
177 // after one of these 3 calls, the iterator given in argument are undefined (they may point nowhere)
178 void insert_null_bytes_at_iterator(iterator it, U_I size);
179 void insert_const_bytes_at_iterator(iterator it, unsigned char a, U_I size);
180 void insert_bytes_at_iterator(iterator it, unsigned char *a, U_I size);
181 void insert_as_much_as_necessary_const_byte_to_be_as_wider_as(const storage & ref, const iterator & it, unsigned char value);
182 void remove_bytes_at_iterator(iterator it, U_I number);
183 void remove_bytes_at_iterator(iterator it, infinint number);
184
185 private:
186 struct cellule *first, *last;
187
188 void copy_from(const storage & ref);
189 S_32 difference(const storage & ref) const;
190 void reduce(); // heuristic that tries to free some memory;
191 void insert_bytes_at_iterator_cmn(iterator it, bool constant, unsigned char *a, U_I size);
192 void fusionne(struct cellule *a_first, struct cellule *a_last, struct cellule *b_first, struct cellule *b_last,
193 struct cellule *&res_first, struct cellule * & res_last);
194
196 // these were STATIC statments, but now object methods
197 // because they rely on on_pool templates that require object field
198
199 void detruit(struct cellule *c);
200 void make_alloc(U_32 size, struct cellule * & begin, struct cellule * & end);
201 void make_alloc(infinint size, cellule * & begin, struct cellule * & end);
202
203 friend class storage::iterator;
204 };
205
206 inline void storage::iterator::skip_plus_one()
207 {
208 if(cell != nullptr)
209 if(++offset >= cell->size)
210 {
211 cell = cell->next;
212 if(cell != nullptr)
213 offset = 0;
214 else
215 offset = OFF_END;
216 }
217 }
218
219 inline void storage::iterator::skip_less_one()
220 {
221 if(cell != nullptr)
222 {
223 if(offset > 0)
224 --offset;
225 else
226 {
227 cell = cell->prev;
228 if(cell != nullptr)
229 offset = cell->size - 1;
230 else
231 offset = OFF_BEGIN;
232 }
233 }
234 }
235
236 } // end of namespace
237
238 #endif
libdar::on_pool
Definition: on_pool.hpp:52
integers.hpp
are defined here basic integer types that tend to be portable
libdar::operator+=
std::vector< T > operator+=(std::vector< T > &a, const std::vector< T > &b)
template function to add two vectors
Definition: tools.hpp:332
libdar::storage::write
U_I write(iterator &it, unsigned char *a, U_I size)
write data to the storage at the location pointed to by it
libdar::storage
arbitrary large storage structure
Definition: storage.hpp:57
erreurs.hpp
contains all the excetion class thrown by libdar
infinint.hpp
switch module to limitint (32 ou 64 bits integers) or infinint
libdar::Ebug
exception used to signal a bug. A bug is triggered when reaching some code that should never be reach...
Definition: erreurs.hpp:137
libdar::generic_file
this is the interface class from which all other data transfer classes inherit
Definition: generic_file.hpp:100
on_pool.hpp
this is the base class of object that can be allocated on a memory pool
libdar::infinint
the arbitrary large positive integer class
Definition: real_infinint.hpp:59
libdar
libdar namespace encapsulate all libdar symbols
Definition: archive.hpp:47