1 /*
2    Bacula(R) - The Network Backup Solution
3 
4    Copyright (C) 2000-2020 Kern Sibbald
5 
6    The original author of Bacula is Kern Sibbald, with contributions
7    from many others, a complete list can be found in the file AUTHORS.
8 
9    You may use this file and others of this release according to the
10    license defined in the LICENSE file, which includes the Affero General
11    Public License, v3.0 ("AGPLv3") and some additional permissions and
12    terms pursuant to its AGPLv3 Section 7.
13 
14    This notice must be preserved when any source code is
15    conveyed and/or propagated.
16 
17    Bacula(R) is a registered trademark of Kern Sibbald.
18 */
19 /*
20  *
21  *  Program to test cache path
22  *
23  *   Eric Bollengier, August 2009
24  *
25  *
26  */
27 
28 #include "bacula.h"
29 #include "cats/cats.h"
30 #include "cats/bvfs.h"
31 #include "findlib/find.h"
32 
33 /* Local variables */
34 static BDB *db;
35 static const char *file = "COPYRIGHT";
36 static DBId_t fnid=0;
37 static const char *db_name = "regress";
38 static const char *db_user = "regress";
39 static const char *db_password = "";
40 static const char *db_host = NULL;
41 static const char *db_ssl_mode = NULL;
42 static const char *db_ssl_key = NULL;
43 static const char *db_ssl_cert = NULL;
44 static const char *db_ssl_ca = NULL;
45 static const char *db_ssl_capath = NULL;
46 static const char *db_ssl_cipher = NULL;
47 
usage()48 static void usage()
49 {
50    fprintf(stderr, _(
51 PROG_COPYRIGHT
52 "\n%sVersion: %s (%s)\n"
53 "       -d <nn>           set debug level to <nn>\n"
54 "       -dt               print timestamp in debug output\n"
55 "       -n <name>         specify the database name (default bacula)\n"
56 "       -u <user>         specify database user name (default bacula)\n"
57 "       -P <password      specify database password (default none)\n"
58 "       -h <host>         specify database host (default NULL)\n"
59 "       -k <sslkey>       path name to the key file (default NULL)\n"
60 "       -e <sslcert>      path name to the certificate file (default NULL)\n"
61 "       -a <sslca>        path name to the CA certificate file (default NULL)\n"
62 "       -w <working>      specify working directory\n"
63 "       -j <jobids>       specify jobids\n"
64 "       -p <path>         specify path\n"
65 "       -f <file>         specify file\n"
66 "       -l <limit>        maximum tuple to fetch\n"
67 "       -T                truncate cache table before starting\n"
68 "       -v                verbose\n"
69 "       -?                print this message\n\n"), 2001, "", VERSION, BDATE);
70    exit(1);
71 }
72 
result_handler(void * ctx,int fields,char ** row)73 static int result_handler(void *ctx, int fields, char **row)
74 {
75    Bvfs *vfs = (Bvfs *)ctx;
76    ATTR *attr = vfs->get_attr();
77    char empty[] = "A A A A A A A A A A A A A A";
78 
79    memset(&attr->statp, 0, sizeof(struct stat));
80    decode_stat((row[BVFS_LStat] && row[BVFS_LStat][0])?row[BVFS_LStat]:empty,
81                &attr->statp, sizeof(attr->statp),  &attr->LinkFI);
82 
83    if (bvfs_is_dir(row) || bvfs_is_file(row)) {
84       /* display clean stuffs */
85 
86       if (bvfs_is_dir(row)) {
87          pm_strcpy(attr->ofname, bvfs_basename_dir(row[BVFS_Name]));
88       } else {
89          /* if we see the requested file, note his filenameid */
90          if (bstrcmp(row[BVFS_Name], file)) {
91             fnid = str_to_int64(row[BVFS_FilenameId]);
92          }
93          pm_strcpy(attr->ofname, row[BVFS_Name]);
94       }
95       print_ls_output(vfs->get_jcr(), attr);
96 
97    } else {
98       Pmsg5(0, "JobId=%s FileId=%s\tMd5=%s\tVolName=%s\tVolInChanger=%s\n",
99             row[BVFS_JobId], row[BVFS_FileId], row[BVFS_Md5], row[BVFS_VolName],
100             row[BVFS_VolInchanger]);
101 
102       pm_strcpy(attr->ofname, file);
103       print_ls_output(vfs->get_jcr(), attr);
104    }
105    return 0;
106 }
107 
108 
109 /* number of thread started */
110 
main(int argc,char * argv[])111 int main (int argc, char *argv[])
112 {
113    int ch;
114    char *jobids = (char *)"1";
115    char *path=NULL, *client=NULL;
116    uint64_t limit=0;
117    bool clean=false;
118    setlocale(LC_ALL, "");
119    bindtextdomain("bacula", LOCALEDIR);
120    textdomain("bacula");
121    init_stack_dump();
122 
123    Dmsg0(0, "Starting bvfs_test tool\n");
124 
125    my_name_is(argc, argv, "bvfs_test");
126    init_msg(NULL, NULL);
127 
128    OSDependentInit();
129 
130    while ((ch = getopt(argc, argv, "h:o:k:e:a:c:l:d:n:P:Su:vf:w:?j:p:f:T")) != -1) {
131       switch (ch) {
132       case 'd':                    /* debug level */
133          if (*optarg == 't') {
134             dbg_timestamp = true;
135          } else {
136             debug_level = atoi(optarg);
137             if (debug_level <= 0) {
138                debug_level = 1;
139             }
140          }
141          break;
142       case 'l':
143          limit = str_to_int64(optarg);
144          break;
145 
146       case 'c':
147          client = optarg;
148          break;
149 
150       case 'h':
151          db_host = optarg;
152          break;
153 
154       case 'o':
155          db_ssl_mode = optarg;
156          break;
157 
158       case 'k':
159          db_ssl_key= optarg;
160          break;
161 
162       case 'e':
163          db_ssl_cert= optarg;
164          break;
165 
166       case 'a':
167          db_ssl_ca= optarg;
168          break;
169 
170       case 'n':
171          db_name = optarg;
172          break;
173 
174       case 'w':
175          working_directory = optarg;
176          break;
177 
178       case 'u':
179          db_user = optarg;
180          break;
181 
182       case 'P':
183          db_password = optarg;
184          break;
185 
186       case 'v':
187          verbose++;
188          break;
189 
190       case 'p':
191          path = optarg;
192          break;
193 
194       case 'f':
195          file = optarg;
196          break;
197 
198       case 'j':
199          jobids = optarg;
200          break;
201 
202       case 'T':
203          clean = true;
204          break;
205 
206       case '?':
207       default:
208          usage();
209 
210       }
211    }
212    argc -= optind;
213    argv += optind;
214 
215    if (argc != 0) {
216       Pmsg0(0, _("Wrong number of arguments: \n"));
217       usage();
218    }
219    JCR *bjcr = new_jcr(sizeof(JCR), NULL);
220    bjcr->JobId = getpid();
221    bjcr->setJobType(JT_CONSOLE);
222    bjcr->setJobLevel(L_FULL);
223    bjcr->JobStatus = JS_Running;
224    bjcr->client_name = get_pool_memory(PM_FNAME);
225    pm_strcpy(bjcr->client_name, "Dummy.Client.Name");
226    bstrncpy(bjcr->Job, "bvfs_test", sizeof(bjcr->Job));
227 
228    if ((db = db_init_database(NULL, NULL, db_name, db_user, db_password,
229                               db_host, 0, NULL,
230                               db_ssl_mode, db_ssl_key,
231                               db_ssl_cert, db_ssl_ca,
232                               db_ssl_capath, db_ssl_cipher,
233                               false, false)) == NULL) {
234       Emsg0(M_ERROR_TERM, 0, _("Could not init Bacula database\n"));
235    }
236    Dmsg1(0, "db_type=%s\n", db_get_engine_name(db));
237 
238    if (!db_open_database(NULL, db)) {
239       Emsg0(M_ERROR_TERM, 0, db_strerror(db));
240    }
241    Dmsg0(200, "Database opened\n");
242    if (verbose) {
243       Pmsg2(000, _("Using Database: %s, User: %s\n"), db_name, db_user);
244    }
245 
246    bjcr->db = db;
247 
248    if (clean) {
249       Pmsg0(0, "Clean old table\n");
250       db_sql_query(db, "DELETE FROM PathHierarchy", NULL, NULL);
251       db_sql_query(db, "UPDATE Job SET HasCache=0", NULL, NULL);
252       db_sql_query(db, "DELETE FROM PathVisibility", NULL, NULL);
253       bvfs_update_cache(bjcr, db);
254    }
255 
256    Bvfs fs(bjcr, db);
257    fs.set_handler(result_handler, &fs);
258 
259    fs.set_jobids(jobids);
260    fs.update_cache();
261    if (limit)
262       fs.set_limit(limit);
263 
264    if (path) {
265       fs.ch_dir(path);
266       fs.ls_special_dirs();
267       fs.ls_dirs();
268       while (fs.ls_files()) {
269          fs.next_offset();
270       }
271 
272       if (fnid && client) {
273          alist clients(1, not_owned_by_alist);
274          clients.append(client);
275          Pmsg0(0, "---------------------------------------------\n");
276          Pmsg1(0, "Getting file version for %s\n", file);
277          fs.get_all_file_versions(fs.get_pwd(), fnid, &clients);
278       }
279 
280       exit (0);
281    }
282 
283 
284    Pmsg0(0, "list /\n");
285    fs.ch_dir("/");
286    fs.ls_special_dirs();
287    fs.ls_dirs();
288    fs.ls_files();
289 
290    Pmsg0(0, "list /tmp/\n");
291    fs.ch_dir("/tmp/");
292    fs.ls_special_dirs();
293    fs.ls_dirs();
294    fs.ls_files();
295 
296    Pmsg0(0, "list /tmp/regress/\n");
297    fs.ch_dir("/tmp/regress/");
298    fs.ls_special_dirs();
299    fs.ls_files();
300    fs.ls_dirs();
301 
302    Pmsg0(0, "list /tmp/regress/build/\n");
303    fs.ch_dir("/tmp/regress/build/");
304    fs.ls_special_dirs();
305    fs.ls_dirs();
306    fs.ls_files();
307 
308    fs.get_all_file_versions(1, 347, (char*)"zog4-fd");
309 
310    char p[200];
311    strcpy(p, "/tmp/toto/rep/");
312    bvfs_parent_dir(p);
313    if(strcmp(p, "/tmp/toto/")) {
314       Pmsg0(000, "Error in bvfs_parent_dir\n");
315    }
316    bvfs_parent_dir(p);
317    if(strcmp(p, "/tmp/")) {
318       Pmsg0(000, "Error in bvfs_parent_dir\n");
319    }
320    bvfs_parent_dir(p);
321    if(strcmp(p, "/")) {
322       Pmsg0(000, "Error in bvfs_parent_dir\n");
323    }
324    bvfs_parent_dir(p);
325    if(strcmp(p, "")) {
326       Pmsg0(000, "Error in bvfs_parent_dir\n");
327    }
328    bvfs_parent_dir(p);
329    if(strcmp(p, "")) {
330       Pmsg0(000, "Error in bvfs_parent_dir\n");
331    }
332 
333    return 0;
334 }
335