Imported Upstream version 3.1.0
[debian/amanda] / perl / Amanda / Logfile.pm
1 # This file was automatically generated by SWIG (http://www.swig.org).
2 # Version 1.3.39
3 #
4 # Do not make changes to this file unless you know what you are doing--modify
5 # the SWIG interface file instead.
6
7 package Amanda::Logfile;
8 use base qw(Exporter);
9 use base qw(DynaLoader);
10 require Amanda::Cmdline;
11 package Amanda::Logfilec;
12 bootstrap Amanda::Logfile;
13 package Amanda::Logfile;
14 @EXPORT = qw();
15
16 # ---------- BASE METHODS -------------
17
18 package Amanda::Logfile;
19
20 sub TIEHASH {
21     my ($classname,$obj) = @_;
22     return bless $obj, $classname;
23 }
24
25 sub CLEAR { }
26
27 sub FIRSTKEY { }
28
29 sub NEXTKEY { }
30
31 sub FETCH {
32     my ($self,$field) = @_;
33     my $member_func = "swig_${field}_get";
34     $self->$member_func();
35 }
36
37 sub STORE {
38     my ($self,$field,$newval) = @_;
39     my $member_func = "swig_${field}_set";
40     $self->$member_func($newval);
41 }
42
43 sub this {
44     my $ptr = shift;
45     return tied(%$ptr);
46 }
47
48
49 # ------- FUNCTION WRAPPERS --------
50
51 package Amanda::Logfile;
52
53 *open_logfile = *Amanda::Logfilec::open_logfile;
54 *close_logfile = *Amanda::Logfilec::close_logfile;
55 *get_logline = *Amanda::Logfilec::get_logline;
56 *log_add = *Amanda::Logfilec::log_add;
57 *find_log = *Amanda::Logfilec::find_log;
58 *search_logfile = *Amanda::Logfilec::search_logfile;
59 *search_holding_disk = *Amanda::Logfilec::search_holding_disk;
60 *dumps_match = *Amanda::Logfilec::dumps_match;
61 *dumps_match_dumpspecs = *Amanda::Logfilec::dumps_match_dumpspecs;
62 *match_host = *Amanda::Logfilec::match_host;
63 *match_disk = *Amanda::Logfilec::match_disk;
64 *match_datestamp = *Amanda::Logfilec::match_datestamp;
65 *match_level = *Amanda::Logfilec::match_level;
66
67 ############# Class : Amanda::Logfile::find_result_t ##############
68
69 package Amanda::Logfile::find_result_t;
70 use vars qw(@ISA %OWNER %ITERATORS %BLESSEDMEMBERS);
71 @ISA = qw( Amanda::Logfile );
72 %OWNER = ();
73 %ITERATORS = ();
74 sub DESTROY {
75     return unless $_[0]->isa('HASH');
76     my $self = tied(%{$_[0]});
77     return unless defined $self;
78     delete $ITERATORS{$self};
79     if (exists $OWNER{$self}) {
80         Amanda::Logfilec::delete_find_result_t($self);
81         delete $OWNER{$self};
82     }
83 }
84
85 *swig_timestamp_get = *Amanda::Logfilec::find_result_t_timestamp_get;
86 *swig_timestamp_set = *Amanda::Logfilec::find_result_t_timestamp_set;
87 *swig_hostname_get = *Amanda::Logfilec::find_result_t_hostname_get;
88 *swig_hostname_set = *Amanda::Logfilec::find_result_t_hostname_set;
89 *swig_diskname_get = *Amanda::Logfilec::find_result_t_diskname_get;
90 *swig_diskname_set = *Amanda::Logfilec::find_result_t_diskname_set;
91 *swig_level_get = *Amanda::Logfilec::find_result_t_level_get;
92 *swig_level_set = *Amanda::Logfilec::find_result_t_level_set;
93 *swig_label_get = *Amanda::Logfilec::find_result_t_label_get;
94 *swig_label_set = *Amanda::Logfilec::find_result_t_label_set;
95 *swig_filenum_get = *Amanda::Logfilec::find_result_t_filenum_get;
96 *swig_filenum_set = *Amanda::Logfilec::find_result_t_filenum_set;
97 *swig_status_get = *Amanda::Logfilec::find_result_t_status_get;
98 *swig_status_set = *Amanda::Logfilec::find_result_t_status_set;
99 *swig_dump_status_get = *Amanda::Logfilec::find_result_t_dump_status_get;
100 *swig_dump_status_set = *Amanda::Logfilec::find_result_t_dump_status_set;
101 *swig_message_get = *Amanda::Logfilec::find_result_t_message_get;
102 *swig_message_set = *Amanda::Logfilec::find_result_t_message_set;
103 *swig_partnum_get = *Amanda::Logfilec::find_result_t_partnum_get;
104 *swig_partnum_set = *Amanda::Logfilec::find_result_t_partnum_set;
105 *swig_totalparts_get = *Amanda::Logfilec::find_result_t_totalparts_get;
106 *swig_totalparts_set = *Amanda::Logfilec::find_result_t_totalparts_set;
107 *swig_sec_get = *Amanda::Logfilec::find_result_t_sec_get;
108 *swig_sec_set = *Amanda::Logfilec::find_result_t_sec_set;
109 *swig_kb_get = *Amanda::Logfilec::find_result_t_kb_get;
110 *swig_kb_set = *Amanda::Logfilec::find_result_t_kb_set;
111 *swig_orig_kb_get = *Amanda::Logfilec::find_result_t_orig_kb_get;
112 *swig_orig_kb_set = *Amanda::Logfilec::find_result_t_orig_kb_set;
113 sub new {
114     my $pkg = shift;
115     my $self = Amanda::Logfilec::new_find_result_t(@_);
116     bless $self, $pkg if defined($self);
117 }
118
119 sub DISOWN {
120     my $self = shift;
121     my $ptr = tied(%$self);
122     delete $OWNER{$ptr};
123 }
124
125 sub ACQUIRE {
126     my $self = shift;
127     my $ptr = tied(%$self);
128     $OWNER{$ptr} = 1;
129 }
130
131
132 # ------- VARIABLE STUBS --------
133
134 package Amanda::Logfile;
135
136 *L_BOGUS = *Amanda::Logfilec::L_BOGUS;
137 *L_FATAL = *Amanda::Logfilec::L_FATAL;
138 *L_ERROR = *Amanda::Logfilec::L_ERROR;
139 *L_WARNING = *Amanda::Logfilec::L_WARNING;
140 *L_INFO = *Amanda::Logfilec::L_INFO;
141 *L_SUMMARY = *Amanda::Logfilec::L_SUMMARY;
142 *L_START = *Amanda::Logfilec::L_START;
143 *L_FINISH = *Amanda::Logfilec::L_FINISH;
144 *L_DISK = *Amanda::Logfilec::L_DISK;
145 *L_DONE = *Amanda::Logfilec::L_DONE;
146 *L_PART = *Amanda::Logfilec::L_PART;
147 *L_PARTPARTIAL = *Amanda::Logfilec::L_PARTPARTIAL;
148 *L_SUCCESS = *Amanda::Logfilec::L_SUCCESS;
149 *L_PARTIAL = *Amanda::Logfilec::L_PARTIAL;
150 *L_FAIL = *Amanda::Logfilec::L_FAIL;
151 *L_STRANGE = *Amanda::Logfilec::L_STRANGE;
152 *L_CHUNK = *Amanda::Logfilec::L_CHUNK;
153 *L_CHUNKSUCCESS = *Amanda::Logfilec::L_CHUNKSUCCESS;
154 *L_STATS = *Amanda::Logfilec::L_STATS;
155 *L_MARKER = *Amanda::Logfilec::L_MARKER;
156 *L_CONT = *Amanda::Logfilec::L_CONT;
157 *P_UNKNOWN = *Amanda::Logfilec::P_UNKNOWN;
158 *P_PLANNER = *Amanda::Logfilec::P_PLANNER;
159 *P_DRIVER = *Amanda::Logfilec::P_DRIVER;
160 *P_REPORTER = *Amanda::Logfilec::P_REPORTER;
161 *P_DUMPER = *Amanda::Logfilec::P_DUMPER;
162 *P_CHUNKER = *Amanda::Logfilec::P_CHUNKER;
163 *P_TAPER = *Amanda::Logfilec::P_TAPER;
164 *P_AMFLUSH = *Amanda::Logfilec::P_AMFLUSH;
165 *P_AMDUMP = *Amanda::Logfilec::P_AMDUMP;
166 *P_AMIDXTAPED = *Amanda::Logfilec::P_AMIDXTAPED;
167 *P_AMFETCHDUMP = *Amanda::Logfilec::P_AMFETCHDUMP;
168 *P_AMCHECKDUMP = *Amanda::Logfilec::P_AMCHECKDUMP;
169 *amanda_log_trace_log = *Amanda::Logfilec::amanda_log_trace_log;
170
171 @EXPORT_OK = ();
172 %EXPORT_TAGS = ();
173
174
175 =head1 NAME
176
177 Amanda::Logfile - manage Amanda trace logs
178
179 =head1 SYNOPSIS
180
181   use Amanda::Logfile qw( :constants );
182   use Amanda::Config qw( :getconf config_dir_relative );
183
184   for my $logfile (Amanda::Logfile::find_log()) {
185     $logfile = config_dir_relative(getconf($CNF_LOGDIR)) . "/" . $logfile;
186
187     my $hdl = Amanda::Logfile::open_logfile($logfile);
188     while (my ($type, $prog, $str) = Amanda::Logfile::get_logline($hdl)) {
189       if ($type == $L_INFO) {
190         my $pname = Amanda::Logfile::program_t_to_string($prog);
191         print "Found info line from $pname: $str\n";
192       }
193     }
194     Amanda::Logfile::close_logfile($hdl);
195
196     my @dumps = Amanda::Logfile::search_logfile("TapeLabel-001", "19780615", $logfile, 1);
197
198     my @matching = Amanda::Logfile::dumps_match([@dumps], "myhost", "/usr", undef, undef, 0);
199     for my $dump (@matching) {
200       print "$dump->{'label'}:$dump->{'filenum'} = $dump->{'hostname'}:$dump->{'disk'}\n";
201     }
202   }
203
204 =head1 RAW LOGFILE ACCESS
205
206 This section corresponds to the C C<logfile> module.
207
208 Raw access to logfiles is accomplished by opening a logfile and
209 fetching log lines one by one via the C<get_logline> function.
210
211 A log line is represented by a list C<($type, $prog, $string)> where C<$type>
212 is one of the C<L_*> constants (available in export tag C<logtype_t>), C<$prog>
213 is one of the C<P_*> constants (available in export tag C<program_t>), and
214 C<$str> is the remainder of the line. Both sets of constants are also available
215 in the usual C<constants> export tag.  Both families of constants can be
216 converted to symbolic names with C<logtype_t_to_string> and
217 C<program_t_to_string>, respectively.
218
219 =head2 FUNCTIONS
220
221 Use these functions to read a logfile:
222
223 =over
224
225 =item C<open_logfile($filename)>
226
227 Opens a logfile for reading, returning an opaque log file
228 handle. Returns C<undef> and sets C<$!> on failure.
229
230 =item C<close_logfile($handle)>
231
232 Closes a log file handle.
233
234 =item C<get_logline($handle)>
235
236 Returns a list as described above representing the next log line in
237 C<$handle>, or nothing at the end of the logfile.
238
239 =back
240
241 To write a logfile, call C<log_add($logtype, $string)>.  On the first
242 call, this function opens and locks C<$logdir/log>; subsequent calls
243 just append to this file.  As such, this function is only appropriate
244 for situations where C<amlogroll> will be invoked later to rename
245 C<$logdir/log> to C<$logdir/log.$timestamp.$n>.
246
247 All of the functions in this section can be imported by name if
248 desired.
249
250 =head2 Amanda::Find::find_result_t objects
251
252 These objects contain information about dumps, as read from logfiles.
253 Instance variables are:
254
255 =over
256
257 =item C<timestamp>
258
259 =item C<hostname>
260
261 =item C<diskname>
262
263 =item C<level>
264
265 =item C<label>
266
267 =item C<filenum>
268
269 =item C<status>
270
271 =item C<partnum>
272
273 =item C<totalparts>
274
275 =item C<sec>
276
277 =item C<kb>
278
279 =back
280
281 Note that the format for these variables are based on that found in
282 the logfiles.  In particular, C<timestamp> is the timestamp for the run
283 in which the client dump took place, and not for the timestamp of the
284 logfile.
285
286 =head1 HIGHER-LEVEL FUNCTIONS
287
288 Functions in this section extract information from logfiles.
289
290 =over
291
292 =item C<find_log()>
293
294 Return a list of logfiles for active tapes.  The tapelist must be loaded
295 before this function is called (see L<Amanda::Tapelist>).  This function uses
296 the C API which indexes logfiles with tapes.  If there is no corresponding
297 tape, the logfile will not be found.
298
299 =item C<find_all_logs([dir])>
300
301 Return a list of all logs the configuration.  An optional directory argument
302 can be specified, if not present, C<find_all_logs> checks C<LOGDIR>.
303
304 =item C<find_latest_log([dir])>
305
306 Returns the most recent logfile in the list of logfiles returned by
307 C<find_all_logs>.  The optional directory argument is passed to
308 C<find_all_logs>.
309
310 =item C<search_logfile($label, $datestamp, $logfile, $add_missing_disks)>
311
312 Return all results in C<$logfile> matching C<$label> and
313 C<$datestamp>.  If C<$add_missing_disks> is true, then any disks in
314 the logfile not present in the disklist are added to the disklist;
315 otherwise, such dumps are skipped.
316
317 =item C<search_holding_disk()>
318
319 Return results for all holding-disk files.  Results are similar to those from
320 search_logfile.
321
322 =item C<dumps_match([@results], $hostname, $diskname, $datestamp, $level, $ok)>
323
324 Return a filtered version of C<@results> containing only results that
325 match the given expressions.  If C<$ok> is true, don't match partial
326 results.  Note that C<$level> is given as a string, since it is a
327 match expression.
328
329 =item C<dumps_match_dumpspecs([@results], [@dumpspecs], $ok)>
330
331 Return a filtered version of C<@results>, containing only results that match
332 one or more of the dumpspecs.  C<$ok> is as for C<dumps_match>.  Supplying no
333 dumpspecs will result in an empty return value.  If multiple dumpspecs match
334 the same result, that result will be returned multiple times.
335
336 =back
337
338 All of these functions can be imported by name.
339
340 =head1 MATCHING
341
342 The following functions are available to match strings against patterns using
343 the rules described in amanda(8):
344
345   match_host($pat, $str);
346   match_disk($pat, $str);
347   match_datestamp($pat, $str);
348   match_level($pat, $str);
349
350 =head1 DEBUG LOGGING HANDLER
351
352 This package provides C<$amanda_log_trace_log>, which sends C<die>
353 messages (and any C<g_error> or C<g_critical> calls from C) to the
354 trace log.  Use it like this:
355
356   use Amanda::Logfile qw( $amanda_log_trace_log );
357   # ...
358   Amanda::Debug::add_amanda_log_handler($amanda_log_trace_log);
359
360 =cut
361
362
363
364 push @EXPORT_OK, qw(open_logfile get_logline close_logfile
365     log_add);
366
367 push @EXPORT_OK, qw(logtype_t_to_string);
368 push @{$EXPORT_TAGS{"logtype_t"}}, qw(logtype_t_to_string);
369
370 my %_logtype_t_VALUES;
371 #Convert an enum value to a single string
372 sub logtype_t_to_string {
373     my ($enumval) = @_;
374
375     for my $k (keys %_logtype_t_VALUES) {
376         my $v = $_logtype_t_VALUES{$k};
377
378         #is this a matching flag?
379         if ($enumval == $v) {
380             return $k;
381         }
382     }
383
384 #default, just return the number
385     return $enumval;
386 }
387
388 push @EXPORT_OK, qw($L_BOGUS);
389 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_BOGUS);
390
391 $_logtype_t_VALUES{"L_BOGUS"} = $L_BOGUS;
392
393 push @EXPORT_OK, qw($L_FATAL);
394 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_FATAL);
395
396 $_logtype_t_VALUES{"L_FATAL"} = $L_FATAL;
397
398 push @EXPORT_OK, qw($L_ERROR);
399 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_ERROR);
400
401 $_logtype_t_VALUES{"L_ERROR"} = $L_ERROR;
402
403 push @EXPORT_OK, qw($L_WARNING);
404 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_WARNING);
405
406 $_logtype_t_VALUES{"L_WARNING"} = $L_WARNING;
407
408 push @EXPORT_OK, qw($L_INFO);
409 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_INFO);
410
411 $_logtype_t_VALUES{"L_INFO"} = $L_INFO;
412
413 push @EXPORT_OK, qw($L_SUMMARY);
414 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_SUMMARY);
415
416 $_logtype_t_VALUES{"L_SUMMARY"} = $L_SUMMARY;
417
418 push @EXPORT_OK, qw($L_START);
419 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_START);
420
421 $_logtype_t_VALUES{"L_START"} = $L_START;
422
423 push @EXPORT_OK, qw($L_FINISH);
424 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_FINISH);
425
426 $_logtype_t_VALUES{"L_FINISH"} = $L_FINISH;
427
428 push @EXPORT_OK, qw($L_DISK);
429 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_DISK);
430
431 $_logtype_t_VALUES{"L_DISK"} = $L_DISK;
432
433 push @EXPORT_OK, qw($L_DONE);
434 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_DONE);
435
436 $_logtype_t_VALUES{"L_DONE"} = $L_DONE;
437
438 push @EXPORT_OK, qw($L_PART);
439 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_PART);
440
441 $_logtype_t_VALUES{"L_PART"} = $L_PART;
442
443 push @EXPORT_OK, qw($L_PARTPARTIAL);
444 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_PARTPARTIAL);
445
446 $_logtype_t_VALUES{"L_PARTPARTIAL"} = $L_PARTPARTIAL;
447
448 push @EXPORT_OK, qw($L_SUCCESS);
449 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_SUCCESS);
450
451 $_logtype_t_VALUES{"L_SUCCESS"} = $L_SUCCESS;
452
453 push @EXPORT_OK, qw($L_PARTIAL);
454 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_PARTIAL);
455
456 $_logtype_t_VALUES{"L_PARTIAL"} = $L_PARTIAL;
457
458 push @EXPORT_OK, qw($L_FAIL);
459 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_FAIL);
460
461 $_logtype_t_VALUES{"L_FAIL"} = $L_FAIL;
462
463 push @EXPORT_OK, qw($L_STRANGE);
464 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_STRANGE);
465
466 $_logtype_t_VALUES{"L_STRANGE"} = $L_STRANGE;
467
468 push @EXPORT_OK, qw($L_CHUNK);
469 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_CHUNK);
470
471 $_logtype_t_VALUES{"L_CHUNK"} = $L_CHUNK;
472
473 push @EXPORT_OK, qw($L_CHUNKSUCCESS);
474 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_CHUNKSUCCESS);
475
476 $_logtype_t_VALUES{"L_CHUNKSUCCESS"} = $L_CHUNKSUCCESS;
477
478 push @EXPORT_OK, qw($L_STATS);
479 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_STATS);
480
481 $_logtype_t_VALUES{"L_STATS"} = $L_STATS;
482
483 push @EXPORT_OK, qw($L_MARKER);
484 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_MARKER);
485
486 $_logtype_t_VALUES{"L_MARKER"} = $L_MARKER;
487
488 push @EXPORT_OK, qw($L_CONT);
489 push @{$EXPORT_TAGS{"logtype_t"}}, qw($L_CONT);
490
491 $_logtype_t_VALUES{"L_CONT"} = $L_CONT;
492
493 #copy symbols in logtype_t to constants
494 push @{$EXPORT_TAGS{"constants"}},  @{$EXPORT_TAGS{"logtype_t"}};
495
496 push @EXPORT_OK, qw(program_t_to_string);
497 push @{$EXPORT_TAGS{"program_t"}}, qw(program_t_to_string);
498
499 my %_program_t_VALUES;
500 #Convert an enum value to a single string
501 sub program_t_to_string {
502     my ($enumval) = @_;
503
504     for my $k (keys %_program_t_VALUES) {
505         my $v = $_program_t_VALUES{$k};
506
507         #is this a matching flag?
508         if ($enumval == $v) {
509             return $k;
510         }
511     }
512
513 #default, just return the number
514     return $enumval;
515 }
516
517 push @EXPORT_OK, qw($P_UNKNOWN);
518 push @{$EXPORT_TAGS{"program_t"}}, qw($P_UNKNOWN);
519
520 $_program_t_VALUES{"P_UNKNOWN"} = $P_UNKNOWN;
521
522 push @EXPORT_OK, qw($P_PLANNER);
523 push @{$EXPORT_TAGS{"program_t"}}, qw($P_PLANNER);
524
525 $_program_t_VALUES{"P_PLANNER"} = $P_PLANNER;
526
527 push @EXPORT_OK, qw($P_DRIVER);
528 push @{$EXPORT_TAGS{"program_t"}}, qw($P_DRIVER);
529
530 $_program_t_VALUES{"P_DRIVER"} = $P_DRIVER;
531
532 push @EXPORT_OK, qw($P_REPORTER);
533 push @{$EXPORT_TAGS{"program_t"}}, qw($P_REPORTER);
534
535 $_program_t_VALUES{"P_REPORTER"} = $P_REPORTER;
536
537 push @EXPORT_OK, qw($P_DUMPER);
538 push @{$EXPORT_TAGS{"program_t"}}, qw($P_DUMPER);
539
540 $_program_t_VALUES{"P_DUMPER"} = $P_DUMPER;
541
542 push @EXPORT_OK, qw($P_CHUNKER);
543 push @{$EXPORT_TAGS{"program_t"}}, qw($P_CHUNKER);
544
545 $_program_t_VALUES{"P_CHUNKER"} = $P_CHUNKER;
546
547 push @EXPORT_OK, qw($P_TAPER);
548 push @{$EXPORT_TAGS{"program_t"}}, qw($P_TAPER);
549
550 $_program_t_VALUES{"P_TAPER"} = $P_TAPER;
551
552 push @EXPORT_OK, qw($P_AMFLUSH);
553 push @{$EXPORT_TAGS{"program_t"}}, qw($P_AMFLUSH);
554
555 $_program_t_VALUES{"P_AMFLUSH"} = $P_AMFLUSH;
556
557 push @EXPORT_OK, qw($P_AMDUMP);
558 push @{$EXPORT_TAGS{"program_t"}}, qw($P_AMDUMP);
559
560 $_program_t_VALUES{"P_AMDUMP"} = $P_AMDUMP;
561
562 push @EXPORT_OK, qw($P_AMIDXTAPED);
563 push @{$EXPORT_TAGS{"program_t"}}, qw($P_AMIDXTAPED);
564
565 $_program_t_VALUES{"P_AMIDXTAPED"} = $P_AMIDXTAPED;
566
567 push @EXPORT_OK, qw($P_AMFETCHDUMP);
568 push @{$EXPORT_TAGS{"program_t"}}, qw($P_AMFETCHDUMP);
569
570 $_program_t_VALUES{"P_AMFETCHDUMP"} = $P_AMFETCHDUMP;
571
572 push @EXPORT_OK, qw($P_AMCHECKDUMP);
573 push @{$EXPORT_TAGS{"program_t"}}, qw($P_AMCHECKDUMP);
574
575 $_program_t_VALUES{"P_AMCHECKDUMP"} = $P_AMCHECKDUMP;
576
577 #copy symbols in program_t to constants
578 push @{$EXPORT_TAGS{"constants"}},  @{$EXPORT_TAGS{"program_t"}};
579
580 push @EXPORT_OK, qw(find_log search_logfile dumps_match
581     match_host match_disk match_datestamp match_level);
582
583 push @EXPORT_OK, qw($amanda_log_trace_log);
584
585 push @EXPORT_OK, qw(find_all_logs find_latest_log);
586
587
588 sub find_all_logs
589 {
590     my $logdir = shift @_ || config_dir_relative(getconf($CNF_LOGDIR));
591
592     opendir my $logdh, $logdir or die("can't read $logdir");
593     my @logfiles = sort grep { m{^log\.\d+\.\d+$} } readdir $logdh;
594
595     return @logfiles;
596 }
597
598 sub find_latest_log
599 {
600     my $logdir = shift @_;
601     my @logs = find_all_logs($logdir || ());
602     return $logs[-1];
603 }
604
605 1;