dde998219a8ca22d2112832bd9d9a8ad5f0fd8eb
[debian/amanda] / dumper-src / gnutar.pl.in
1 #!@PERL@
2 #
3
4 # Run perl.
5 eval '(exit $?0)' && eval 'exec @PERL@ -S $0 ${1+"$@"}'
6         & eval 'exec @PERL@ -S $0 $argv:q'
7                 if 0;
8
9 delete @ENV{'IFS', 'CDPATH', 'ENV', 'BASH_ENV', 'PATH'};
10 $ENV{'PATH'} = "/usr/bin:/usr/sbin:/sbin:/bin";
11
12 $debug=1;
13 push(@INC, "@DUMPER_DIR@");
14
15 use File::Copy;
16 use IPC::Open3;
17 use Sys::Hostname;
18
19
20 open(DEBUG,">>@AMANDA_DBGDIR@/gnutar.$$.debug") if ($debug==1);
21
22 $prefix='@prefix@';
23 $exec_prefix="@exec_prefix@";
24 $libexecdir="@libexecdir@";
25 $USE_VERSION_SUFFIXES='@USE_VERSION_SUFFIXES@';
26 $suf = '';
27 if ( $USE_VERSION_SUFFIXES =~ /^yes$/i ) {
28    $suf='-@VERSION@';
29 }
30
31 $host = hostname;
32 $host =~ s/\..*$//;
33 $runtar="${libexecdir}/runtar${suf}";
34 $gnulist = '@GNUTAR_LISTED_INCREMENTAL_DIR@';
35 $gnutar = $runtar;
36
37
38
39 $level_incrementals = 9;
40
41 @index_generation = ("direct","parse","output","image");
42 @parse_estimate   = ("direct","parse");
43 @parse_backup     = ("direct","parse");
44 @backup_type      = ("full","level","diff");
45
46
47 #$user_support  = "";
48 #$group_support = "";
49
50 #$user_selfcheck  = "";
51 #$group_selfcheck = "";
52
53 #$user_estimate  = "";
54 #$group_estimate = "";
55
56 #$user_estimate_parse  = "";
57 #$group_estimate_parse = "";
58
59 $user_backup  = "root";
60 #$group_backup = "";
61
62 #$user_backup_parse  = "";
63 #$group_backup_parse = "";
64
65 #$user_index_from_output  = "";
66 #$group_index_from_output = "";
67
68 #$user_index_from_image  = "";
69 #$group_index_from_image = "";
70
71 #$user_restore  = "";
72 #$group_restore = "";
73
74 #$user_print_command  = "";
75 #$group_print_command = "";
76
77 $user_default  = "amanda";
78 $group_default = "amanda";
79
80
81 sub command_selfcheck {
82 print DEBUG "STDOUT: OK selfcheck\n" if ($debug == 1);
83    print "OK selfcheck\n";
84 }
85
86 sub command_estimate_full {
87    my($disk)    = @_;
88    command_estimate_level(0, $disk);
89 }
90
91 sub command_estimate_level {
92    my($level, $disk) = @_;
93    my($listdir) = "$host$disk";
94    $listdir     =~ s/\//_/g;
95    if($level == 0) {
96       open(GNULIST, ">${gnulist}/${listdir}_${level}.new") || die();
97       close(GNULIST) || die();
98    }
99    else {
100       my($prev_level) = $level - 1;
101       copy("${gnulist}/${listdir}_${prev_level}", "${gnulist}/${listdir}_${level}.new");
102    }
103    if($option_estimate_direct == 1) {
104       command_estimate_opt_direct($disk, $level, $listdir);
105    }
106    else {
107       command_estimate_opt_parse($disk, $level, $listdir);
108    }
109 }
110
111 #sub command_estimate_diff {
112 #}
113
114 sub command_estimate_opt_direct {
115    my($disk, $level, $listdir) = @_;
116    my($size) = -1;
117 print DEBUG "$gnutar --create --directory $disk --listed-incremental ${gnulist}/${listdir}_${level}.new --sparse --one-file-system --ignore-failed-read --totals --file /dev/null .\n" if ($debug == 1);
118    open3(\*WTRFH, '>&STDOUT', \*ESTIMATE, "$gnutar --create --directory $disk --listed-incremental ${gnulist}/${listdir}_${level}.new --sparse --one-file-system --ignore-failed-read --totals --file /dev/null .") || die();
119
120    $size = parse_estimate(ESTIMATE);
121    close(ESTIMATE);
122    output_size($size);
123    unlink "${gnulist}/${listdir}_${level}.new";
124    exit 0;
125 }
126
127 sub command_estimate_opt_parse {
128    my($disk, $level, $listdir) = @_;
129
130    open3(\*WTRFH, '>&STDOUT',\*ESTIMATE,"$gnutar --create --directory $disk --listed-incremental ${gnulist}/${listdir}_${level}.new --sparse --one-file-system --ignore-failed-read --totals --file /dev/null .");
131
132    while (<ESTIMATE>) {
133 print DEBUG "READ: $_" if ($debug == 1);
134 print DEBUG "STDOUT: $_" if ($debug == 1);
135       print $_;
136    }
137    close(ESTIMATE);
138    close(WTRFH);
139
140    unlink "${gnulist}/${listdir}_${level}.new";
141 }
142
143 sub command_estimate_parse {
144    my($size) = parse_estimate(STDIN);
145    output_size($size);
146    exit 0;
147 }
148
149 sub parse_estimate {
150    my($fh) = @_;
151    my($size) = -1;
152    while(<$fh>) {
153 print DEBUG "READ: $_" if ($debug == 1);
154       if ($_ =~ /^Total bytes written: (\d*)$/) {
155          $size = $1;
156          last;
157       }
158    }
159    return $size;
160 }
161
162 sub output_size {
163    my($size) = @_;
164    if($size == -1) {
165 print DEBUG "STDOUT: -1 -1\n" if ($debug == 1);
166       print "-1 -1\n";
167       exit 2;
168    }
169    else {
170       my($ksize) = $size / 1024;
171 print DEBUG "STDOUT: $ksize 1024\n" if ($debug == 1);
172       print "$ksize 1024\n";
173    }
174 }
175
176 sub command_backup_full {
177    my($disk)    = @_;
178    command_backup_level(0, $disk);
179 }
180
181 sub command_backup_level {
182    my($level, $disk) = @_;
183    my($listdir) = "$host$disk";
184    my($verbose) = "";
185    $listdir     =~ s/\//_/g;
186
187    if($level == 0) {
188       open(GNULIST, ">${gnulist}/${listdir}_${level}.new") || die();
189       close(GNULIST) || die();
190    }
191    else {
192       my($prev_level) = $level - 1;
193       copy("${gnulist}/${listdir}_${prev_level}", 
194            "${gnulist}/${listdir}_${level}.new");
195    }
196
197    if($option_index_direct == 1 || $option_index_parse == 1) {
198       $verbose = "--verbose";
199    }
200    my($cmd) = "$gnutar --create $verbose --directory $disk --listed-incremental ${gnulist}/${listdir}_${level}.new --sparse --one-file-system --ignore-failed-read --totals --file - .";
201
202    if($option_backup_parse == 1 && $option_index_direct == 0 &&
203                                    $option_index_parse  == 0) {
204       system($cmd);
205    }
206    else {
207       open3(\*WTRFH, '>&STDOUT', \*INDEX, $cmd) || die();
208
209       if($option_index_direct == 1 || $option_index_parse == 1) {
210          open(INDEXOUT, '>&=3') || die();
211          parse_backup(INDEX, STDERR, INDEXOUT);
212          close(INDEXOUT);
213       }
214       else {
215          parse_backup(INDEX, STDERR, undef);
216       }
217       close(INDEX);
218       close(WTRFH);
219    }
220
221    if(!defined($option_no_record)) {
222       rename "${gnulist}/${listdir}_${level}.new", 
223              "${gnulist}/${listdir}_${level}";
224    }
225    else {
226       unlink "${gnulist}/${listdir}_${level}.new";
227    }
228    exit 0;
229 }
230
231 #sub command_backup_diff {
232 #}
233
234 sub command_backup_parse {
235    $option_backup_direct = 1;
236    $option_backup_parse  = 0;
237    parse_backup(STDIN, STDOUT, undef);
238    exit 0;
239 }
240
241 sub parse_backup {
242    my($fhin, $fhout, $indexout) = @_;
243    my($size) = -1;
244    while(<$fhin>) {
245 print DEBUG "READ: $_" if ($debug == 1);
246       if ( /^\.\//) {
247          if(defined($indexout)) {
248             if($option_index_direct == 1) {
249                s/^\.//;
250 print DEBUG "INDEXOUT: $_" if ($debug == 1);
251                print $indexout $_;
252             }
253             elsif($option_index_parse == 1) {
254 print DEBUG "INDEXOUT: $_" if ($debug == 1);
255                print $indexout $_;
256             }
257          }
258       }
259       else {
260          if (/^Total bytes written: (\d*)$/) {
261             $size = $1;
262             if(defined($fhout) && $option_backup_parse == 1) {
263 print DEBUG "FHOUT: $_" if ($debug == 1);
264                print $fhout $_;
265             }
266          }
267          elsif(defined($fhout)) {
268             if($option_backup_direct == 1) {
269 print DEBUG "FHOUT: $_" if ($debug == 1);
270                print $fhout $_;
271             }
272             elsif($option_backup_parse == 1) {
273 print DEBUG "FHOUT: $_" if ($debug == 1);
274                print $fhout $_;
275             }
276          }
277       }
278    }
279    if(defined($fhout) && $option_backup_direct == 1) {
280       if ($size == -1) {
281 print DEBUG "FHOUT: $command -1 -1\n" if ($debug == 1);
282          print $fhout "$command -1 -1\n";
283       }
284       else {
285          my($ksize) = $size/1024;
286 print DEBUG "FHOUT: $ksize 1024\n" if ($debug == 1);
287          print $fhout "$ksize 1024\n";
288       }
289    }
290 }
291
292 sub command_index_from_output {
293    index_from_output(STDIN, STDOUT);
294    exit 0;
295 }
296
297 sub index_from_output {
298    my($fhin, $fhout) = @_;
299    my($size) = -1;
300    while(<$fhin>) {
301 print DEBUG "READ: $_" if ($debug == 1);
302       next if /^Total bytes written:/;
303       next if !/^\.\//;
304       s/^\.//;
305 print DEBUG "FHOUT: $_" if ($debug == 1);
306       print $fhout $_;
307    }
308 }
309
310 sub command_index_from_image {
311    open(INDEX, "$gnutar --list --file - |") || die();
312    index_from_output(INDEX, STDOUT);
313 }
314
315 #sub command_restore {
316 #}
317
318 sub command_print_command {
319 }
320
321 require "generic-dumper"