+
+ #
+ # Make sure the fileSize was correct. See above for comments about
+ # rsync.
+ #
+ if ( $a->{nWrite} != $a->{fileSize} ) {
+ #
+ # Oops, fileSize was wrong, so our MD5 digest was wrong and our
+ # effort to match files likely failed. This is ugly, but our
+ # only choice at this point is to re-write the entire file with
+ # the correct length. We need to rename the file, open it for
+ # reading, and then re-write the file with the correct length.
+ #
+
+ #print("Doing big file fixup ($a->{fileSize} != $a->{nWrite})\n");
+
+ my($fh, $fileName);
+ $a->{fileSize} = $a->{nWrite};
+
+ if ( defined($a->{fhOut}) ) {
+ if ( $a->{fileName} =~ /(.*)\// ) {
+ $fileName = $1;
+ } else {
+ $fileName = ".";
+ }
+ #
+ # Find a unique target temporary file name
+ #
+ my $i = 0;
+ while ( -f "$fileName/t$$.$i" ) {
+ $i++;
+ }
+ $fileName = "$fileName/t$$.$i";
+ $a->{fhOut}->close();
+ if ( !rename($a->{fileName}, $fileName)
+ || !defined($fh = BackupPC::FileZIO->open($fileName, 0,
+ $a->{compress})) ) {
+ push(@{$a->{errors}}, "Can't rename $a->{fileName} -> $fileName"
+ . " or open during size fixup");
+ }
+ #print("Using temporary name $fileName\n");
+ } elsif ( defined($a->{files}) && defined($a->{files}[0]) ) {
+ #
+ # We haven't written anything yet, so just use the
+ # compare file to copy from.
+ #
+ $fh = $a->{files}[0]->{fh};
+ $fh->rewind;
+ #print("Using compare file $a->{files}[0]->{name}\n");
+ }
+ if ( defined($fh) ) {
+ my $poolWrite = BackupPC::PoolWrite->new($a->{bpc}, $a->{fileName},
+ $a->{fileSize}, $a->{compress});
+ my $nRead = 0;
+
+ while ( $nRead < $a->{fileSize} ) {
+ my $thisRead = $a->{fileSize} - $nRead < $BufSize
+ ? $a->{fileSize} - $nRead : $BufSize;
+ my $data;
+ my $n = $fh->read(\$data, $thisRead);
+ if ( $n != $thisRead ) {
+ push(@{$a->{errors}},
+ "Unable to read $thisRead bytes during resize"
+ . " from temp $fileName (got $n)");
+ last;
+ }
+ $poolWrite->write(\$data);
+ $nRead += $thisRead;
+ }
+ $fh->close;
+ unlink($fileName) if ( defined($fileName) );
+ if ( @{$a->{errors}} ) {
+ $poolWrite->close;
+ return (0, $a->{digest}, -s $a->{fileName}, $a->{errors});
+ } else {
+ return $poolWrite->close;
+ }
+ }