]> git.sur5r.net Git - bacula/bacula/blob - bacula/src/tools/testls.c
Change copyright as per agreement with FSFE + update copyright year
[bacula/bacula] / bacula / src / tools / testls.c
1 /*
2    Bacula(R) - The Network Backup Solution
3
4    Copyright (C) 2000-2016 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  * Test program for listing files during regression testing
21  *   Links have their permissions and time bashed since they cannot
22  *   be set by Bacula.
23  *
24  *  Kern Sibbald, MM
25  *
26  */
27
28 #include "bacula.h"
29 #include "findlib/find.h"
30
31 /* Dummy functions */
32 int generate_job_event(JCR *jcr, const char *event) { return 1; }
33 void generate_plugin_event(JCR *jcr, bEventType eventType, void *value) { }
34
35
36 /* Global variables */
37 int attrs = 0;
38
39 static JCR *jcr;
40 static int num_files = 0;
41
42 static int print_file(JCR *jcr, FF_PKT *ff, bool);
43 static void print_ls_output(char *fname, char *link, int type, struct stat *statp);
44 static int count_files(JCR *jcr, FF_PKT *ff, bool top_level);
45
46 static void usage()
47 {
48    fprintf(stderr, _(
49 "\n"
50 "Usage: testls [-d debug_level] [-] [pattern1 ...]\n"
51 "       -a          print extended attributes (Win32 debug)\n"
52 "       -d <nn>     set debug level to <nn>\n"
53 "       -dt         print timestamp in debug output\n"
54 "       -e          specify file of exclude patterns\n"
55 "       -i          specify file of include patterns\n"
56 "       -q          quiet, don't print filenames (debug)\n"
57 "       -           read pattern(s) from stdin\n"
58 "       -?          print this message.\n"
59 "\n"
60 "Patterns are file inclusion -- normally directories.\n"
61 "Debug level >= 1 prints each file found.\n"
62 "Debug level >= 10 prints path/file for catalog.\n"
63 "Errors always printed.\n"
64 "Files/paths truncated is number with len > 255.\n"
65 "Truncation is only in catalog.\n"
66 "\n"));
67
68    exit(1);
69 }
70
71
72 int main(int argc, char *const *argv)
73 {
74    FF_PKT *ff;
75    char name[1000];
76    bool quiet = false;
77    int i, ch;
78    char *inc = NULL;
79    char *exc = NULL;
80    FILE *fd;
81
82    setlocale(LC_ALL, "");
83    bindtextdomain("bacula", LOCALEDIR);
84    textdomain("bacula");
85    lmgr_init_thread();
86
87    while ((ch = getopt(argc, argv, "ad:e:i:q?")) != -1) {
88       switch (ch) {
89       case 'a':                       /* print extended attributes *debug* */
90          attrs = 1;
91          break;
92
93       case 'd':                       /* set debug level */
94          if (*optarg == 't') {
95             dbg_timestamp = true;
96          } else {
97             debug_level = atoi(optarg);
98             if (debug_level <= 0) {
99                debug_level = 1;
100             }
101          }
102          break;
103
104       case 'e':                       /* exclude patterns */
105          exc = optarg;
106          break;
107
108       case 'i':                       /* include patterns */
109          inc = optarg;
110          break;
111
112       case 'q':
113          quiet = true;
114          break;
115
116       case '?':
117       default:
118          usage();
119
120       }
121    }
122    argc -= optind;
123    argv += optind;
124
125    jcr = new_jcr(sizeof(JCR), NULL);
126
127    ff = init_find_files();
128    if (argc == 0 && !inc) {
129       add_fname_to_include_list(ff, 0, "/"); /* default to / */
130    } else {
131       for (i=0; i < argc; i++) {
132          if (strcmp(argv[i], "-") == 0) {
133              while (fgets(name, sizeof(name)-1, stdin)) {
134                 strip_trailing_junk(name);
135                 add_fname_to_include_list(ff, 0, name);
136               }
137               continue;
138          }
139          add_fname_to_include_list(ff, 0, argv[i]);
140       }
141    }
142    if (inc) {
143       fd = fopen(inc, "rb");
144       if (!fd) {
145          printf(_("Could not open include file: %s\n"), inc);
146          exit(1);
147       }
148       while (fgets(name, sizeof(name)-1, fd)) {
149          strip_trailing_junk(name);
150          add_fname_to_include_list(ff, 0, name);
151       }
152       fclose(fd);
153    }
154
155    if (exc) {
156       fd = fopen(exc, "rb");
157       if (!fd) {
158          printf(_("Could not open exclude file: %s\n"), exc);
159          exit(1);
160       }
161       while (fgets(name, sizeof(name)-1, fd)) {
162          strip_trailing_junk(name);
163          add_fname_to_exclude_list(ff, name);
164       }
165       fclose(fd);
166    }
167    if (quiet) {
168       match_files(jcr, ff, count_files);
169    } else {
170       match_files(jcr, ff, print_file);
171    }
172    printf(_("Files seen = %d\n"), num_files);
173    term_include_exclude_files(ff);
174    term_find_files(ff);
175
176    free_jcr(jcr);
177    term_last_jobs_list();             /* free jcr chain */
178    close_memory_pool();
179    lmgr_cleanup_main();
180    sm_dump(false);
181    exit(0);
182 }
183
184 static int count_files(JCR *jcr, FF_PKT *ff, bool top_level)
185 {
186    num_files++;
187    return 1;
188 }
189
190 static int print_file(JCR *jcr, FF_PKT *ff, bool top_level) 
191 {
192
193    switch (ff->type) {
194    case FT_LNKSAVED:
195    case FT_REGE:
196    case FT_REG:
197    case FT_LNK:
198    case FT_DIREND:
199    case FT_SPEC:
200       print_ls_output(ff->fname, ff->link, ff->type, &ff->statp);
201       break;
202    case FT_DIRBEGIN:
203       break;
204    case FT_NOACCESS:
205       printf(_("Err: Could not access %s: %s\n"), ff->fname, strerror(errno));
206       break;
207    case FT_NOFOLLOW:
208       printf(_("Err: Could not follow ff->link %s: %s\n"), ff->fname, strerror(errno));
209       break;
210    case FT_NOSTAT:
211       printf(_("Err: Could not stat %s: %s\n"), ff->fname, strerror(errno));
212       break;
213    case FT_NOCHG:
214       printf(_("Skip: File not saved. No change. %s\n"), ff->fname);
215       break;
216    case FT_ISARCH:
217       printf(_("Err: Attempt to backup archive. Not saved. %s\n"), ff->fname);
218       break;
219    case FT_NORECURSE:
220       printf(_("Recursion turned off. Directory not entered. %s\n"), ff->fname);
221       break;
222    case FT_NOFSCHG:
223       printf(_("Skip: File system change prohibited. Directory not entered. %s\n"), ff->fname);
224       break;
225    case FT_NOOPEN:
226       printf(_("Err: Could not open directory %s: %s\n"), ff->fname, strerror(errno));
227       break;
228    default:
229       printf(_("Err: Unknown file ff->type %d: %s\n"), ff->type, ff->fname);
230       break;
231    }
232    num_files++;
233    return 1;
234 }
235
236 static void print_ls_output(char *fname, char *link, int type, struct stat *statp)
237 {
238    char buf[2000];
239    char ec1[30];
240    char *p, *f;
241    int n;
242
243    if (type == FT_LNK) {
244       statp->st_mtime = 0;
245       statp->st_mode |= 0777;
246    }
247    p = encode_mode(statp->st_mode, buf);
248    n = sprintf(p, " %2d ", (uint32_t)statp->st_nlink);
249    p += n;
250    n = sprintf(p, "%-4d %-4d", (int)statp->st_uid, (int)statp->st_gid);
251    p += n;
252    n = sprintf(p, "%10.10s ", edit_uint64(statp->st_size, ec1));
253    p += n;
254    if (S_ISCHR(statp->st_mode) || S_ISBLK(statp->st_mode)) {
255       n = sprintf(p, "%4x ", (int)statp->st_rdev);
256    } else {
257       n = sprintf(p, "     ");
258    }
259    p += n;
260    p = encode_time(statp->st_mtime, p);
261    *p++ = ' ';
262    /* Copy file name */
263    for (f=fname; *f && (p-buf) < (int)sizeof(buf); )
264       *p++ = *f++;
265    if (type == FT_LNK) {
266       *p++ = '-';
267       *p++ = '>';
268       *p++ = ' ';
269       /* Copy link name */
270       for (f=link; *f && (p-buf) < (int)sizeof(buf); )
271          *p++ = *f++;
272    }
273    *p++ = '\n';
274    *p = 0;
275    fputs(buf, stdout);
276 }
277
278 bool python_set_prog(JCR*, char const*) { return false; }