Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00025
00026
00027 #ifndef PILE_HPP
00028 #define PILE_HPP
00029
00030 #include "../my_config.h"
00031
00032 #include <vector>
00033 #include <list>
00034 #include "generic_file.hpp"
00035
00036 namespace libdar
00037 {
00038
00041
00042 class pile : public generic_file
00043 {
00044 public:
00049
00050 pile() : generic_file(gf_read_only) { stack.clear(); };
00051 pile(const pile & ref) : generic_file(ref) { copy_from(ref); };
00052 const pile & operator = (const pile & ref) { detruit(); copy_from(ref); return *this; };
00053 ~pile() { detruit(); };
00054
00064 void push(generic_file *f, const std::string & label = "");
00065
00070 generic_file *pop();
00071
00075 template <class T> bool pop_and_close_if_type_is(T *ptr);
00076
00078 generic_file *top() { if(stack.empty()) return NULL; else return stack.back().ptr; };
00079
00081 generic_file *bottom() { if(stack.empty()) return NULL; else return stack[0].ptr; };
00082
00084 U_I size() const { return stack.size(); };
00085
00087 bool is_empty() const { return stack.empty(); };
00088
00090 void clear() { detruit(); };
00091
00095 template<class T> void find_first_from_top(T * & ref);
00096
00098 template<class T> void find_first_from_bottom(T * & ref);
00099
00100
00102 generic_file *get_below(const generic_file *ref);
00103
00105 generic_file *get_above(const generic_file *ref);
00106
00107
00112 generic_file *get_by_label(const std::string & label);
00113
00114
00115
00120 void clear_label(const std::string & label);
00121
00122
00128 void add_label(const std::string & label);
00129
00130
00131
00132
00133
00134
00135 bool skip(const infinint & pos);
00136 bool skip_to_eof();
00137 bool skip_relative(S_I x);
00138 infinint get_position();
00139 void copy_to(generic_file & ref);
00140 void copy_to(generic_file & ref, const infinint & crc_size, crc * & value);
00141
00142 protected:
00143 U_I inherited_read(char *a, U_I size);
00144 void inherited_write(const char *a, U_I size);
00145 void inherited_sync_write();
00146 void inherited_terminate();
00147
00148 private:
00149 struct face
00150 {
00151 generic_file * ptr;
00152 std::list<std::string> labels;
00153 };
00154
00155 std::vector<face> stack;
00156
00157 void copy_from(const pile & ref)
00158 {
00159 throw SRC_BUG;
00160 };
00161 void detruit();
00162 std::vector<face>::iterator look_for_label(const std::string & label);
00163 };
00164
00165
00166 template <class T> bool pile::pop_and_close_if_type_is(T *ptr)
00167 {
00168 generic_file *top = NULL;
00169
00170 if(!stack.empty())
00171 {
00172 top = stack.back().ptr;
00173 ptr = dynamic_cast<T *>(top);
00174 if(ptr != NULL)
00175 {
00176 stack.pop_back();
00177 delete top;
00178 return true;
00179 }
00180 else
00181 return false;
00182 }
00183 else
00184 return false;
00185 }
00186
00187 template <class T> void pile::find_first_from_top(T * & ref)
00188 {
00189 ref = NULL;
00190 for(std::vector<face>::reverse_iterator it = stack.rbegin(); it != stack.rend() && ref == NULL; ++it)
00191 ref = dynamic_cast<T *>(it->ptr);
00192 }
00193
00194
00195 template <class T> void pile::find_first_from_bottom(T * & ref)
00196 {
00197 ref = NULL;
00198 for(std::vector<face>::iterator it = stack.begin(); it != stack.end() && ref == NULL; ++it)
00199 ref = dynamic_cast<T *>(it->ptr);
00200 }
00201
00203
00204 }
00205
00206 #endif