Disk ARchive  2.4.12
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Defines
filesystem.hpp
Go to the documentation of this file.
00001 /*********************************************************************/
00002 // dar - disk archive - a backup/restoration program
00003 // Copyright (C) 2002-2052 Denis Corbin
00004 //
00005 // This program is free software; you can redistribute it and/or
00006 // modify it under the terms of the GNU General Public License
00007 // as published by the Free Software Foundation; either version 2
00008 // of the License, or (at your option) any later version.
00009 //
00010 // This program is distributed in the hope that it will be useful,
00011 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00012 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00013 // GNU General Public License for more details.
00014 //
00015 // You should have received a copy of the GNU General Public License
00016 // along with this program; if not, write to the Free Software
00017 // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
00018 //
00019 // to contact the author : http://dar.linux.free.fr/email.html
00020 /*********************************************************************/
00021 
00031 
00032 #ifndef FILESYSTEM_HPP
00033 #define FILESYSTEM_HPP
00034 
00035 #include "../my_config.h"
00036 
00037 extern "C"
00038 {
00039 #if HAVE_UNISTD_H
00040 #include <unistd.h>
00041 #endif
00042 
00043 #if HAVE_SYS_STAT_H
00044 #include <sys/stat.h>
00045 #endif
00046 } // end extern "C"
00047 
00048 #include <map>
00049 #include <vector>
00050 #include "catalogue.hpp"
00051 #include "infinint.hpp"
00052 #include "etage.hpp"
00053 #include "criterium.hpp"
00054 
00055 namespace libdar
00056 {
00059 
00061 
00062     class filesystem_hard_link_read : virtual protected mem_ui
00063     {
00064             // this class is not to be used directly
00065             // it only provides some routine for the inherited classes
00066 
00067     public:
00068         filesystem_hard_link_read(user_interaction & dialog,
00069                                   bool x_furtive_read_mode) : mem_ui(dialog) { furtive_read_mode = x_furtive_read_mode; };
00070 
00071             // the copy of the current object would make copy of addresses in
00072             // corres_read that could be released twice ... thus, copy constructor and
00073             // assignement are forbidden for this class:
00074 
00075         filesystem_hard_link_read(const filesystem_hard_link_read & ref) : mem_ui(ref.get_ui()) { throw SRC_BUG; };
00076         const filesystem_hard_link_read & operator = (const filesystem_hard_link_read & ref) { throw SRC_BUG; };
00077 
00078             // get the last assigned number for a hard linked inode
00079         const infinint & get_last_etoile_ref() const { return etiquette_counter; };
00080 
00081         virtual ~filesystem_hard_link_read() {};
00082 
00083     protected:
00084             // reset the whole list of hard linked inodes (hard linked inode stay alive but are no more referenced by the current object)
00085         void corres_reset() { corres_read.clear(); etiquette_counter = 0; };
00086 
00087             // create and return a libdar object corresponding to one pointed to by its path
00088             // during this operation, hard linked inode are recorded in a list to be easily pointed
00089             // to by a new reference to it.
00090         nomme *make_read_entree(path & lieu,               //< path of the file to read
00091                                 const std::string & name,  //< name of the file to read
00092                                 bool see_hard_link,        //< whether we want to detect hard_link and eventually return a mirage object (not necessary when diffing an archive with filesystem)
00093                                 const mask & ea_mask);    //< which EA to consider when creating the object
00094 
00095     private:
00096 
00097             // private datastructure
00098 
00099         struct couple
00100         {
00101             nlink_t count;       //< counts the number of hard link on that inode that have not yet been found in filesystem, once this count reaches zero, the "couple" structure can be dropped and the "holder" too (no more expected hard links to be found)
00102             etoile *obj;         //< the address of the corresponding etoile object for that inode
00103             mirage holder;       //< it increments by one the obj internal counters, thus, while this object is alive, the obj will not be destroyed
00104 
00105             couple(etoile *ptr, nlink_t ino_count) : holder("FAKE", ptr) { count = ino_count; obj = ptr; };
00106         };
00107 
00108         struct node
00109         {
00110             node(ino_t num, dev_t dev) { numnode = num; device = dev; };
00111 
00112                 // this operator is required to use the type node in a std::map
00113             bool operator < (const node & ref) const { return numnode < ref.numnode || (numnode == ref.numnode && device < ref.device); };
00114             ino_t numnode;
00115             dev_t device;
00116         };
00117 
00118             // private variable
00119 
00120         std::map <node, couple> corres_read;
00121         infinint etiquette_counter;
00122         bool furtive_read_mode;
00123 
00124     };
00125 
00126 
00127 
00129 
00130     class filesystem_backup : public filesystem_hard_link_read
00131     {
00132     public:
00133         filesystem_backup(user_interaction & dialog,
00134                           const path &root,
00135                           bool x_info_details,
00136                           const mask & x_ea_mask,
00137                           bool check_no_dump_flag,
00138                           bool alter_atime,
00139                           bool furtive_read_mode,
00140                           bool x_cache_directory_tagging,
00141                           infinint & root_fs_device,
00142                           bool x_ignore_unknown);
00143         filesystem_backup(const filesystem_backup & ref) : mem_ui(ref.get_ui()), filesystem_hard_link_read(ref.get_ui(), ref.furtive_read_mode) { copy_from(ref); };
00144         const filesystem_backup & operator = (const filesystem_backup & ref) { detruire(); copy_from(ref); return *this; };
00145         ~filesystem_backup() { detruire(); };
00146 
00147         void reset_read(infinint & root_fs_device);
00148         bool read(entree * & ref, infinint & errors, infinint & skipped_dump);
00149         void skip_read_to_parent_dir();
00150             //  continue reading in parent directory and
00151             // ignore all entry not yet read of current directory
00152     private:
00153 
00154         path *fs_root;           //< filesystem's root to consider
00155         bool info_details;       //< detailed information returned to the user
00156         mask *ea_mask;           //< mask defining the EA to consider
00157         bool no_dump_check;      //< whether to check against the nodump flag presence
00158         bool alter_atime;        //< whether to set back atime or not
00159         bool furtive_read_mode;  //< whether to use furtive read mode (if true, alter_atime is ignored)
00160         bool cache_directory_tagging; //< whether to consider cache directory taggin standard
00161         path *current_dir;       //< needed to translate from an hard linked inode to an  already allocated object
00162         std::vector<etage> pile; //< to store the contents of a directory
00163         bool ignore_unknown;     //< whether to ignore unknown inode types
00164 
00165         void detruire();
00166         void copy_from(const filesystem_backup & ref);
00167     };
00168 
00169 
00171 
00172     class filesystem_diff : public filesystem_hard_link_read
00173     {
00174     public:
00175         filesystem_diff(user_interaction & dialog,
00176                         const path &root,
00177                         bool x_info_details,
00178                         const mask & x_ea_mask,
00179                         bool alter_atime,
00180                         bool furtive_read_mode);
00181         filesystem_diff(const filesystem_diff & ref) : mem_ui(ref.get_ui()), filesystem_hard_link_read(ref.get_ui(), ref.furtive_read_mode) { copy_from(ref); };
00182         const filesystem_diff & operator = (const filesystem_diff & ref) { detruire(); copy_from(ref); return *this; };
00183         ~filesystem_diff() { detruire(); };
00184 
00185         void reset_read();
00186         bool read_filename(const std::string & name, nomme * &ref);
00187             // looks for a file of name given in argument, in current reading directory
00188             // if this is a directory, subsequent read take place in it
00189 
00190         void skip_read_filename_in_parent_dir();
00191             // subsequent calls to read_filename will take place in parent directory.
00192 
00193     private:
00194         struct filename_struct
00195         {
00196             infinint last_acc;
00197             infinint last_mod;
00198         };
00199 
00200         path *fs_root;
00201         bool info_details;
00202         mask *ea_mask;
00203         bool alter_atime;
00204         bool furtive_read_mode;
00205         path *current_dir;
00206         std::vector<filename_struct> filename_pile;
00207 
00208         void detruire();
00209         void copy_from(const filesystem_diff & ref);
00210     };
00211 
00213 
00214     class filesystem_hard_link_write : virtual protected mem_ui
00215     {
00216             // this class is not to be used directly
00217             // it only provides routines to its inherited classes
00218 
00219     public:
00220         filesystem_hard_link_write(user_interaction & dialog) : mem_ui(dialog) { corres_write.clear(); };
00221         filesystem_hard_link_write(const filesystem_hard_link_write & ref) : mem_ui(ref) { throw SRC_BUG; };
00222         const filesystem_hard_link_write & operator = (const filesystem_hard_link_write & ref) { throw SRC_BUG; };
00223 
00224         void write_hard_linked_target_if_not_set(const mirage *ref, const std::string & chemin);
00225             // if a hard linked inode has not been restored (no change, or less recent than the one on filesystem)
00226             // it is necessary to inform filesystem, where to hard link on, any future hard_link
00227             // that could be necessary to restore.
00228 
00229         bool known_etiquette(const infinint & eti);
00230             // return true if an inode in filesystem has been seen for that hard linked inode
00231 
00235         void clear_corres_if_pointing_to(const infinint & ligne, const std::string & path);
00236 
00237     protected:
00238         void corres_reset() { corres_write.clear(); };
00239         void make_file(const nomme * ref,                       //< object to restore in filesystem
00240                        const path & ou,                         //< where to restore it
00241                        bool dir_perm,                           //< false for already existing directories, this makes dar set the minimum available permission to be able to restore files in that directory at a later time
00242                        inode::comparison_fields what_to_check); //< defines whether to restore permission, ownership, dates, etc.
00243             // generate inode or make a hard link on an already restored or existing inode.
00244 
00245 
00247 
00253         bool raw_set_ea(const nomme *e,
00254                         const ea_attributs & list_ea,
00255                         const std::string & spot,
00256                         const mask & ea_mask);
00257             // check whether the inode for which to restore EA is not a hard link to
00258             // an already restored inode. if not, it calls the proper ea_filesystem call to restore EA
00259 
00261 
00265         bool raw_clear_ea_set(const nomme *e, const std::string & path);
00266 
00267 
00268     private:
00269         struct corres_ino_ea
00270         {
00271             std::string chemin;
00272             bool ea_restored;
00273         };
00274 
00275         std::map <infinint, corres_ino_ea> corres_write;
00276     };
00277 
00278 
00280 
00281     class filesystem_restore : public filesystem_hard_link_write, public filesystem_hard_link_read
00282     {
00283     public:
00285         filesystem_restore(user_interaction & dialog,
00286                            const path & root,
00287                            bool x_warn_overwrite,
00288                            bool x_info_details,
00289                            const mask & x_ea_mask,
00290                            inode::comparison_fields what_to_check,
00291                            bool x_warn_remove_no_match,
00292                            bool empty,
00293                            const crit_action *x_overwrite,
00294                            bool x_only_overwrite);
00296         filesystem_restore(const filesystem_restore & ref) : mem_ui(ref), filesystem_hard_link_write(ref), filesystem_hard_link_read(get_ui(), true) { throw SRC_BUG; };
00298         const filesystem_restore & operator = (const filesystem_restore  & ref) { throw SRC_BUG; };
00300         ~filesystem_restore() { restore_stack_dir_ownership(); detruire(); };
00301 
00303         void reset_write();
00304 
00305         typedef enum
00306         {
00307             done_data_restored,     //< data has been restored to filesystem
00308             done_no_change_no_data, //< no change in filesystem because no data present in archive
00309             done_no_change_policy,  //< no change in filesystem because of overwiting policy decision
00310             done_data_removed       //< data (= whole inode) removed from filesystem
00311         } action_done_for_data;
00312 
00314 
00322         void write(const entree *x, action_done_for_data & data_restored, bool & ea_restored, bool & data_created, bool & hard_link);
00323 
00324 
00329         void ignore_overwrite_restrictions_for_next_write() { ignore_over_restricts = true; };
00330 
00331 
00332     private:
00333         class stack_dir_t : public directory
00334         {
00335         public:
00336             stack_dir_t(const directory & ref, bool restore) : directory(ref) { restore_date = restore; };
00337 
00338             bool get_restore_date() const { return restore_date; };
00339             void set_restore_date(bool val) { restore_date = val; };
00340 
00341         private:
00342             bool restore_date;
00343         };
00344 
00345         path *fs_root;
00346         bool info_details;
00347         mask *ea_mask;
00348         bool warn_overwrite;
00349         inode::comparison_fields what_to_check;
00350         bool warn_remove_no_match;
00351         std::vector<stack_dir_t> stack_dir;
00352         path *current_dir;
00353         bool empty;
00354         bool ignore_over_restricts;
00355         const crit_action *overwrite;
00356         bool only_overwrite;
00357 
00358         void detruire();
00359         void restore_stack_dir_ownership();
00360 
00361             // subroutines of write()
00362         void action_over_remove(const inode *in_place, const detruit *to_be_added, const std::string & spot, over_action_data action);
00363         void action_over_data(const inode *in_place,
00364                               const nomme *to_be_added,
00365                               const std::string & spot,
00366                               over_action_data action,
00367                               action_done_for_data & data_done);
00368         bool action_over_ea(const inode *in_place, const nomme *to_be_added, const std::string & spot, over_action_ea action);
00369     };
00370 
00372 
00373 } // end of namespace
00374 
00375 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Defines