1 /*
2    BAREOS® - Backup Archiving REcovery Open Sourced
3 
4    Copyright (C) 2001-2010 Free Software Foundation Europe e.V.
5    Copyright (C) 2011-2012 Planets Communications B.V.
6    Copyright (C) 2013-2019 Bareos GmbH & Co. KG
7 
8    This program is Free Software; you can redistribute it and/or
9    modify it under the terms of version three of the GNU Affero General Public
10    License as published by the Free Software Foundation and included
11    in the file LICENSE.
12 
13    This program is distributed in the hope that it will be useful, but
14    WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16    Affero General Public License for more details.
17 
18    You should have received a copy of the GNU Affero General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
21    02110-1301, USA.
22 */
23 /*
24  * Kern Sibbald MMI
25  */
26 /**
27  * @file
28  * File types as returned by FindFiles()
29  */
30 
31 #ifndef BAREOS_FINDLIB_FIND_H_
32 #define BAREOS_FINDLIB_FIND_H_
33 
34 #include "include/fileopts.h"
35 #include "bfile.h"
36 #include "lib/htable.h"
37 #include "lib/dlist.h"
38 #include "lib/alist.h"
39 
40 #ifdef HAVE_DIRENT_H
41 #include <dirent.h>
42 #define NAMELEN(dirent) (strlen((dirent)->d_name))
43 #endif
44 
45 #include <sys/file.h>
46 #if !defined(HAVE_WIN32) || defined(HAVE_MINGW)
47 #include <sys/param.h>
48 #endif
49 
50 #if !defined(HAVE_UTIMES) && !defined(HAVE_LUTIMES)
51 #if HAVE_UTIME_H
52 #include <utime.h>
53 #else
54 struct utimbuf {
55   long actime;
56   long modtime;
57 };
58 #endif
59 #endif
60 
61 #define MODE_RALL (S_IRUSR | S_IRGRP | S_IROTH)
62 
63 #include "lib/fnmatch.h"
64 
65 #ifndef HAVE_REGEX_H
66 #include "lib/bregex.h"
67 #else
68 #include <regex.h>
69 #endif
70 #ifdef USE_READDIR_R
71 #ifndef HAVE_READDIR_R
72 int Readdir_r(DIR* dirp, struct dirent* entry, struct dirent** result);
73 #endif
74 #endif
75 /**
76  * For options FO_xxx values see src/fileopts.h
77  */
78 enum
79 {
80   state_none,
81   state_options,
82   state_include,
83   state_error
84 };
85 
86 typedef enum
87 {
88   check_shadow_none,
89   check_shadow_local_warn,
90   check_shadow_local_remove,
91   check_shadow_global_warn,
92   check_shadow_global_remove
93 } b_fileset_shadow_type;
94 
95 typedef enum
96 {
97   size_match_none,
98   size_match_approx,
99   size_match_smaller,
100   size_match_greater,
101   size_match_range
102 } b_sz_match_type;
103 
104 struct s_sz_matching {
105   b_sz_match_type type{size_match_none};
106   uint64_t begin_size{};
107   uint64_t end_size{};
108 };
109 
110 struct s_included_file {
111   struct s_included_file* next;
112   char options[FOPTS_BYTES]; /**< Backup options */
113   uint32_t cipher;           /**< Encryption cipher forced by fileset */
114   uint32_t algo; /**< Compression algorithm. 4 letters stored as an integer */
115   int level;     /**< Compression level */
116   int len;       /**< Length of fname */
117   int pattern;   /**< Set if wild card pattern */
118   struct s_sz_matching* size_match;  /**< Perform size matching ? */
119   b_fileset_shadow_type shadow_type; /**< Perform fileset shadowing check ? */
120   char VerifyOpts[20];               /**< Options for verify */
121   char fname[1];
122 };
123 
124 struct s_excluded_file {
125   struct s_excluded_file* next;
126   int len;
127   char fname[1];
128 };
129 
130 #define MAX_OPTS 20
131 
132 /**
133  * File options structure
134  */
135 struct findFOPTS {
136   char flags[FOPTS_BYTES]{};    /**< Backup options */
137   uint32_t Encryption_cipher{}; /**< Encryption cipher forced by fileset */
138   uint32_t Compress_algo{}; /**< Compression algorithm. 4 letters stored as an
139                              integer */
140   int Compress_level{};     /**< Compression level */
141   int StripPath{};          /**< Strip path count */
142   struct s_sz_matching* size_match; /**< Perform size matching ? */
143   b_fileset_shadow_type shadow_type{
144       check_shadow_none};        /**< Perform fileset shadowing check ? */
145   char VerifyOpts[MAX_OPTS]{};   /**< Verify options */
146   char AccurateOpts[MAX_OPTS]{}; /**< Accurate mode options */
147   char BaseJobOpts[MAX_OPTS]{};  /**< Basejob mode options */
148   char* plugin{};                /**< Plugin that handle this section */
149   alist regex;                   /**< Regex string(s) */
150   alist regexdir;                /**< Regex string(s) for directories */
151   alist regexfile;               /**< Regex string(s) for files */
152   alist wild;                    /**< Wild card strings */
153   alist wilddir;                 /**< Wild card strings for directories */
154   alist wildfile;                /**< Wild card strings for files */
155   alist wildbase;                /**< Wild card strings for basenames */
156   alist base;                    /**< List of base names */
157   alist fstype;                  /**< File system type limitation */
158   alist Drivetype;               /**< Drive type limitation */
159 };
160 
161 /**
162  * This is either an include item or an exclude item
163  */
164 struct findIncludeExcludeItem {
165   findFOPTS* current_opts; /**< Points to current options structure */
166   alist opts_list;         /**< Options list */
167   dlist name_list;         /**< Filename list -- holds dlistString */
168   dlist plugin_list;       /**< Plugin list -- holds dlistString */
169   alist ignoredir;         /**< Ignore directories with this file(s) */
170 };
171 
172 /**
173  * FileSet Resource
174  */
175 struct findFILESET {
176   int state;
177   findIncludeExcludeItem* incexe; /**< Current item */
178   alist include_list;
179   alist exclude_list;
180 };
181 
182 /**
183  * OSX resource fork.
184  */
185 struct HfsPlusInfo {
186   unsigned long length{0}; /**< Mandatory field */
187   char fndrinfo[32]{};     /**< Finder Info */
188   off_t rsrclength{0};     /**< Size of resource fork */
189 };
190 
191 /**
192  * Structure for keeping track of hard linked files, we
193  * keep an entry for each hardlinked file that we save,
194  * which is the first one found. For all the other files that
195  * are linked to this one, we save only the directory
196  * entry so we can link it.
197  */
198 struct CurLink {
199   struct hlink link;
200   dev_t dev;             /**< Device */
201   ino_t ino;             /**< Inode with device is unique */
202   uint32_t FileIndex;    /**< Bareos FileIndex of this file */
203   int32_t digest_stream; /**< Digest type if needed */
204   uint32_t digest_len;   /**< Digest len if needed */
205   char* digest;          /**< Checksum of the file if needed */
206   char name[1];          /**< The name */
207 };
208 
209 /**
210  * Definition of the FindFiles packet passed as the
211  * first argument to the FindFiles callback subroutine.
212  */
213 /* clang-format off */
214 struct FindFilesPacket {
215   char* top_fname{nullptr};          /**< Full filename before descending */
216   char* fname{nullptr};              /**< Full filename */
217   char* link{nullptr};               /**< Link if file linked */
218   char* object_name{nullptr};        /**< Object name */
219   char* object{nullptr};             /**< Restore object */
220   char* plugin{nullptr};             /**< Current Options{Plugin=} name */
221   POOLMEM* sys_fname{nullptr};       /**< System filename */
222   POOLMEM* fname_save{nullptr};      /**< Save when stripping path */
223   POOLMEM* link_save{nullptr};       /**< Save when stripping path */
224   POOLMEM* ignoredir_fname{nullptr}; /**< Used to ignore directories */
225   char* digest{nullptr};  /**< Set to file digest when the file is a hardlink */
226   struct stat statp{};    /**< Stat packet */
227   uint32_t digest_len{0}; /**< Set to the digest len when the file is a hardlink*/
228   int32_t digest_stream{0}; /**< Set to digest type when the file is hardlink */
229   int32_t FileIndex{0};     /**< FileIndex of this file */
230   int32_t LinkFI{0};        /**< FileIndex of main hard linked file */
231   int32_t delta_seq{0};     /**< Delta Sequence number */
232   int32_t object_index{0};  /**< Object index */
233   int32_t object_len{0};    /**< Object length */
234   int32_t object_compression{0};  /**< Type of compression for object */
235   int type{0};                    /**< FT_ type from above */
236   int ff_errno{0};                /**< Errno */
237   BareosWinFilePacket bfd;        /**< Bareos file descriptor */
238   time_t save_time{0};            /**< Start of incremental time */
239   bool accurate_found{false};     /**< Found in the accurate hash (valid after
240                                        CheckChanges()) */
241   bool dereference{false};        /**< Follow links (not implemented) */
242   bool null_output_device{false}; /**< Using null output device */
243   bool incremental{false};        /**< Incremental save */
244   bool no_read{false};            /**< Do not read this file when using Plugin */
245   char VerifyOpts[MAX_OPTS]{};
246   char AccurateOpts[MAX_OPTS]{};
247   char BaseJobOpts[MAX_OPTS]{};
248   struct s_included_file* included_files_list{nullptr};
249   struct s_excluded_file* excluded_files_list{nullptr};
250   struct s_excluded_file* excluded_paths_list{nullptr};
251   findFILESET* fileset{nullptr};
252   int (*FileSave)(JobControlRecord*,
253                   FindFilesPacket*,
254                   bool){};   /**< User's callback */
255   int (*PluginSave)(JobControlRecord*,
256                     FindFilesPacket*,
257                     bool){}; /**< User's callback */
258   bool (*CheckFct)(
259       JobControlRecord*,
260       FindFilesPacket*){};   /**< Optional user fct to check file changes */
261 
262   /*
263    * Values set by AcceptFile while processing Options
264    */
265   char flags[FOPTS_BYTES]{}; /**< Backup options */
266   uint32_t Compress_algo{0}; /**< Compression algorithm. 4 letters stored as an integer */
267   int Compress_level{0};     /**< Compression level */
268   int StripPath{0};          /**< Strip path count */
269   struct s_sz_matching* size_match{nullptr}; /**< Perform size matching ? */
270   bool cmd_plugin{false}; /**< Set if we have a command plugin */
271   bool opt_plugin{false}; /**< Set if we have an option plugin */
272   alist fstypes;          /**< Allowed file system types */
273   alist drivetypes;       /**< Allowed drive types */
274 
275   /*
276    * List of all hard linked files found
277    */
278   htable* linkhash{nullptr};       /**< Hard linked files */
279   struct CurLink* linked{nullptr}; /**< Set if this file is hard linked */
280 
281   /*
282    * Darwin specific things.
283    * To avoid clutter, we always include rsrc_bfd and volhas_attrlist.
284    */
285   BareosWinFilePacket rsrc_bfd; /**< Fd for resource forks */
286   bool volhas_attrlist{false};  /**< Volume supports getattrlist() */
287   HfsPlusInfo hfsinfo;          /**< Finder Info and resource fork size */
288 };
289 /* clang-format on */
290 
291 FindFilesPacket* init_find_files();
292 void SetFindOptions(FindFilesPacket* ff, bool incremental, time_t mtime);
293 void SetFindChangedFunction(FindFilesPacket* ff,
294                             bool CheckFct(JobControlRecord* jcr,
295                                           FindFilesPacket* ff));
296 int FindFiles(JobControlRecord* jcr,
297               FindFilesPacket* ff,
298               int file_sub(JobControlRecord*, FindFilesPacket* ff_pkt, bool),
299               int PluginSub(JobControlRecord*, FindFilesPacket* ff_pkt, bool));
300 bool MatchFiles(JobControlRecord* jcr,
301                 FindFilesPacket* ff,
302                 int sub(JobControlRecord*, FindFilesPacket* ff_pkt, bool));
303 int TermFindFiles(FindFilesPacket* ff);
304 bool IsInFileset(FindFilesPacket* ff);
305 bool AcceptFile(FindFilesPacket* ff);
306 findIncludeExcludeItem* allocate_new_incexe(void);
307 findIncludeExcludeItem* new_exclude(findFILESET* fileset);
308 findIncludeExcludeItem* new_include(findFILESET* fileset);
309 findIncludeExcludeItem* new_preinclude(findFILESET* fileset);
310 findIncludeExcludeItem* new_preexclude(findFILESET* fileset);
311 findFOPTS* start_options(FindFilesPacket* ff);
312 void NewOptions(FindFilesPacket* ff, findIncludeExcludeItem* incexe);
313 
314 
315 #include "acl.h"
316 #include "xattr.h"
317 
318 #endif /* __FILES_H */
319