]> git.sur5r.net Git - bacula/bacula/blob - bacula/patches/testing/accurate-db.patch
ebl Add accurate mode using DB Berkeley
[bacula/bacula] / bacula / patches / testing / accurate-db.patch
1 Index: src/dird/next_vol.c
2 ===================================================================
3 --- src/dird/next_vol.c (revision 7286)
4 +++ src/dird/next_vol.c (working copy)
5 @@ -94,28 +94,30 @@
6                  */
7                 if (prune) {
8                    Dmsg0(150, "Call prune_volumes\n");
9 -                  prune_volumes(jcr, InChanger, mr);
10 +                  ok = prune_volumes(jcr, InChanger, mr);
11                 }
12 -               ok = recycle_oldest_purged_volume(jcr, InChanger, mr);
13 -               if (!ok && create) {
14 -                  Dmsg4(050, "after prune volumes_vol ok=%d index=%d InChanger=%d Vstat=%s\n",
15 -                        ok, index, InChanger, mr->VolStatus);
16 -                  /*
17 -                   * 5. Try pulling a volume from the Scratch pool
18 -                   */ 
19 -                  ok = get_scratch_volume(jcr, InChanger, mr);
20 -               }
21 -               /*
22 -                * If we are using an Autochanger and have not found
23 -                * a volume, retry looking for any volume. 
24 -                */
25 -               if (InChanger) {
26 -                  InChanger = false;
27 -                  if (!ok) {
28 -                     continue;           /* retry again accepting any volume */
29 -                  }
30 -               }
31 -            }
32 +              if (!ok) {
33 +                 ok = recycle_oldest_purged_volume(jcr, InChanger, mr);
34 +                 if (!ok && create) {
35 +                    Dmsg4(050, "after prune volumes_vol ok=%d index=%d InChanger=%d Vstat=%s\n",
36 +                          ok, index, InChanger, mr->VolStatus);
37 +                    /*
38 +                     * 5. Try pulling a volume from the Scratch pool
39 +                     */ 
40 +                    ok = get_scratch_volume(jcr, InChanger, mr);
41 +                    Dmsg4(050, "after get scratch volume ok=%d index=%d InChanger=%d Vstat=%s\n",
42 +                          ok, index, InChanger, mr->VolStatus);
43 +                 }
44 +                 /*
45 +                  * If we are using an Autochanger and have not found
46 +                  * a volume, retry looking for any volume. 
47 +                  */
48 +                 if (!ok && InChanger) {
49 +                    InChanger = false;
50 +                    continue;           /* retry again accepting any volume */
51 +                 }
52 +              }
53 +           }
54           }
55  
56  
57 Index: src/dird/autoprune.c
58 ===================================================================
59 --- src/dird/autoprune.c        (revision 7286)
60 +++ src/dird/autoprune.c        (working copy)
61 @@ -176,6 +176,17 @@
62              prune_list.num_ids = 0;             /* reset count */
63           }
64           ok = is_volume_purged(ua, &lmr);
65 +
66 +        /* 
67 +         * Check if this volume is available (InChanger + StorageId) 
68 +         * If not, just skip this volume and try the next one
69 +         */
70 +        if (ok && InChanger) {
71 +           if (!lmr.InChanger || (lmr.StorageId != mr->StorageId)) {
72 +              ok = false;              /* skip this volume, ie not loadable */
73 +           }
74 +        }
75 +
76           /*
77            * If purged and not moved to another Pool, 
78            *   then we stop pruning and take this volume.
79 Index: src/filed/accurate.c
80 ===================================================================
81 --- src/filed/accurate.c        (revision 7286)
82 +++ src/filed/accurate.c        (working copy)
83 @@ -36,7 +36,7 @@
84  static int dbglvl=200;
85  
86  typedef struct PrivateCurFile {
87 -#ifndef USE_TCADB
88 +#ifdef USE_HTABLE
89     hlink link;
90  #endif
91     char *fname;                        /* not stored with tchdb mode */
92 @@ -45,9 +45,9 @@
93     bool seen;
94  } CurFile;
95  
96 +
97  #ifdef USE_TCADB
98 -static void realfree(void *p); /* used by tokyo code */
99 -
100 +static void realfree(void *p); /* used by tokyo/db code */
101  /*
102   * Update hash element seen=1
103   */
104 @@ -190,10 +190,150 @@
105     return true;
106  }
107  
108 -#else  /* HTABLE mode */
109 +#endif /* USE_TCADB */
110 +#ifdef USE_DB
111  
112 +/*
113 + * Update hash element seen=1
114 + */
115  static bool accurate_mark_file_as_seen(JCR *jcr, CurFile *elt)
116  {
117 +   bool ret=true;
118 +   DBT dbkey, dbdata;
119 +
120 +   elt->seen = 1;
121 +
122 +   dbkey.data = elt->fname;
123 +   dbkey.size = (u_int32_t)strlen(elt->fname)+1;
124 +   dbdata.data = elt;
125 +   dbdata.size = sizeof(CurFile);
126 +   if ((ret = jcr->file_list->put(jcr->file_list, NULL, &dbkey, &dbdata, 0))) {
127 +      Jmsg(jcr, M_ERROR, 1, _("Can't update accurate hash disk ERR=%i\n"), ret);
128 +      return 0;
129 +   }
130 +
131 +   return 1;
132 +}
133 +
134 +static bool accurate_lookup(JCR *jcr, char *fname, CurFile *ret)
135 +{
136 +   ret->seen = 0;
137 +   DBT dbkey, dbdata;
138 +   /* Zero out the DBTs before using them. */
139 +   memset(&dbkey, 0, sizeof(DBT));
140 +   memset(&dbdata, 0, sizeof(DBT));
141 +
142 +   dbkey.data = fname;
143 +   dbkey.ulen = strlen(fname)+1;
144 +   
145 +   dbdata.data = ret;
146 +   dbdata.ulen = sizeof(CurFile);
147 +   dbdata.flags = DB_DBT_USERMEM;
148 +
149 +   if (jcr->file_list->get(jcr->file_list, NULL, &dbkey, &dbdata, 0) == 0) {
150 +      return 1;
151 +   } else {
152 +      return 0;
153 +   }
154 +}
155 +
156 +/* Create tokyo dbm hash file 
157 + * If something goes wrong, we cancel accurate mode.
158 + */
159 +static bool accurate_init(JCR *jcr, int nbfile)
160 +{
161 +   int ret;
162 +
163 +   if ((ret = db_create(&jcr->file_list, NULL, 0)) != 0) {
164 +      Jmsg(jcr, M_ERROR, 1, _("Can't open accurate hash disk\n"));
165 +      return 0;
166 +   }
167 +
168 +   jcr->file_list->set_errfile(jcr->file_list, stderr);
169 +   jcr->file_list->set_errpfx(jcr->file_list, "hash");
170 +
171 +   if ((ret = jcr->file_list->set_cachesize(jcr->file_list, 0, 32 * 1024 * 1024, 0)) != 0) {
172 +      Jmsg(jcr, M_ERROR, 1, _("Can't setup hash disk cache size\n"));
173 +   }
174 +
175 +   jcr->hash_name  = get_pool_memory(PM_MESSAGE);
176 +   make_unique_filename(&jcr->hash_name, jcr->JobId, "accurate");
177 +
178 +   if ((ret = jcr->file_list->open(jcr->file_list,
179 +                                  NULL, jcr->hash_name, NULL, DB_BTREE, DB_CREATE, 0600)) != 0) {
180 +      jcr->file_list->close(jcr->file_list, DB_NOSYNC);
181 +      jcr->file_list=NULL;
182 +      free_pool_memory(jcr->hash_name);
183 +      jcr->hash_name = NULL;
184 +      Jmsg(jcr, M_ERROR, 1, _("Can't setup hash disk cache size\n"));
185 +      return 0;
186 +   }
187 +
188 +   return jcr->file_list != NULL;
189 +}
190 +
191 +/* This function is called at the end of backup
192 + * We walk over all hash disk element, and we check
193 + * for elt.seen.
194 + */
195 +bool accurate_send_deleted_list(JCR *jcr)
196 +{
197 +   CurFile elt;
198 +   FF_PKT *ff_pkt;
199 +   int stream = STREAM_UNIX_ATTRIBUTES;
200 +   DBC *cursorp=NULL;
201 +   DBT dbkey, dbdata;
202 +   /* Zero out the DBTs before using them. */
203 +   memset(&dbkey, 0, sizeof(DBT));
204 +   memset(&dbdata, 0, sizeof(DBT));
205 +   dbdata.data = &elt;
206 +   dbdata.ulen = sizeof(CurFile);
207 +   dbdata.flags = DB_DBT_USERMEM;
208 +
209 +   if (!jcr->accurate || jcr->JobLevel == L_FULL) {
210 +      goto bail_out;
211 +   }
212 +
213 +   if (jcr->file_list == NULL) {
214 +      goto bail_out;
215 +   }
216 +
217 +   ff_pkt = init_find_files();
218 +   ff_pkt->type = FT_DELETED;
219 +
220 +   /* traverse records */
221 +   jcr->file_list->cursor(jcr->file_list, NULL, &cursorp, 0); 
222 +
223 +   while(cursorp->c_get(cursorp, &dbkey, &dbdata, DB_NEXT) == 0) {
224 +      if (!elt.seen) { /* already seen */
225 +        ff_pkt->fname = (char *) dbkey.data;
226 +        ff_pkt->statp.st_mtime = elt.mtime;
227 +        ff_pkt->statp.st_ctime = elt.ctime;
228 +        encode_and_send_attributes(jcr, ff_pkt, stream);
229 +      }
230 +   }
231 +   cursorp->c_close(cursorp);
232 +
233 +   term_find_files(ff_pkt);
234 +bail_out:
235 +
236 +   if (jcr->file_list) {
237 +      jcr->file_list->close(jcr->file_list, DB_NOSYNC);
238 +      if (!bstrcmp(jcr->hash_name, "*")) {
239 +        unlink(jcr->hash_name);
240 +      }
241 +      free_pool_memory(jcr->hash_name);
242 +      jcr->hash_name = NULL;
243 +      jcr->file_list = NULL;
244 +   }
245 +   return true;
246 +}
247 +
248 +#endif /* USE_DB */
249 +#ifdef USE_HTABLE
250 +
251 +static bool accurate_mark_file_as_seen(JCR *jcr, CurFile *elt)
252 +{
253     CurFile *temp = (CurFile *)jcr->file_list->lookup(elt->fname);
254     temp->seen = 1;             /* records are in memory */
255     return true;
256 @@ -286,7 +426,22 @@
257        Jmsg(jcr, M_ERROR, 1, _("Can't update accurate hash disk ERR=%s\n"));
258        ret = false;
259     }
260 -#else  /* HTABLE */
261 +#endif
262 +#ifdef USE_DB
263 +   DBT dbkey, dbdata;
264 +   memset(&dbkey, 0, sizeof(DBT));
265 +   memset(&dbdata, 0, sizeof(DBT));
266 +   dbkey.data = elt.fname;
267 +   dbkey.size = (u_int32_t)strlen(elt.fname)+1;
268 +   dbdata.data = &elt;
269 +   dbdata.size = sizeof(CurFile);
270 +   if ((ret = jcr->file_list->put(jcr->file_list, NULL, &dbkey, &dbdata, 0))) {
271 +      Jmsg(jcr, M_ERROR, 1, _("Can't update accurate hash disk ERR=%i\n"), ret);
272 +      return false;
273 +   }
274 +
275 +#endif
276 +#ifdef USE_HTABLE
277     CurFile *item;
278     /* we store CurFile, fname and ctime/mtime in the same chunk */
279     item = (CurFile *)jcr->file_list->hash_malloc(sizeof(CurFile)+strlen(fname)+1);
280 Index: src/filed/filed.h
281 ===================================================================
282 --- src/filed/filed.h   (revision 7286)
283 +++ src/filed/filed.h   (working copy)
284 @@ -37,7 +37,11 @@
285  #define FILE_DAEMON 1
286  #ifdef USE_TCADB                     /* hash disk based */
287  # include <tcadb.h>
288 -#else
289 +#endif
290 +#ifdef  USE_DB
291 +# include <db.h>
292 +#endif
293 +#ifdef USE_HTABLE
294  # include "lib/htable.h"
295  #endif
296  #include "filed_conf.h"
297 Index: src/baconfig.h
298 ===================================================================
299 --- src/baconfig.h      (revision 7286)
300 +++ src/baconfig.h      (working copy)
301 @@ -113,6 +113,12 @@
302  
303  #endif /* HAVE_WIN32 */
304  
305 +/* Select db backend for accurate mode */
306 +#ifndef USE_TCADB
307 +# ifndef USE_DB
308 +#  define USE_HTABLE
309 +# endif
310 +#endif
311  
312  #ifdef ENABLE_NLS
313     #include <libintl.h>
314 Index: src/win32/build-depkgs-mingw32
315 ===================================================================
316 --- src/win32/build-depkgs-mingw32      (revision 7286)
317 +++ src/win32/build-depkgs-mingw32      (working copy)
318 @@ -519,7 +519,7 @@
319     process_cmd_utils
320     process_mkisofs
321     process_dvd_rw_tools
322 -   process_qt4
323 +#   process_qt4
324  else
325     for dependency in "$@"
326     do
327 Index: src/jcr.h
328 ===================================================================
329 --- src/jcr.h   (revision 7286)
330 +++ src/jcr.h   (working copy)
331 @@ -344,7 +344,12 @@
332  #ifdef USE_TCADB
333     TCADB *file_list;                  /* Previous file list (accurate mode) */
334     POOLMEM *hash_name;
335 -#else
336 +#endif
337 +#ifdef USE_DB
338 +   DB *file_list;
339 +   POOLMEM *hash_name;
340 +#endif
341 +#ifdef USE_HTABLE
342     htable *file_list;                 /* Previous file list (accurate mode) */
343  #endif
344  #endif /* FILE_DAEMON */