mirror of https://github.com/digint/btrbk
btrbk: moved get_receive_targets_fsroot() out of get_receive_targets(), while cleaning up
parent
774e6ef842
commit
5a06a85619
121
btrbk
121
btrbk
|
@ -1835,28 +1835,24 @@ sub get_receive_targets($$;@)
|
||||||
my $src_vol = shift || die;
|
my $src_vol = shift || die;
|
||||||
my %opts = @_;
|
my %opts = @_;
|
||||||
my $droot_subvols = vinfo_subvol_list($droot);
|
my $droot_subvols = vinfo_subvol_list($droot);
|
||||||
my @ret_receive_targets;
|
my @ret;
|
||||||
my @all_receive_targets;
|
|
||||||
my $unexpected_count = 0;
|
my $unexpected_count = 0;
|
||||||
|
|
||||||
if($src_vol->{node}{is_root}) {
|
if($src_vol->{node}{is_root}) {
|
||||||
DEBUG "Skip search for targets: source subvolume is btrfs root: $src_vol->{PRINT}";
|
DEBUG "Skip search for targets: source subvolume is btrfs root: $src_vol->{PRINT}";
|
||||||
return @ret_receive_targets;
|
return @ret;
|
||||||
}
|
}
|
||||||
unless($src_vol->{node}{readonly}) {
|
unless($src_vol->{node}{readonly}) {
|
||||||
DEBUG "Skip search for targets: source subvolume is not read-only: $src_vol->{PRINT}";
|
DEBUG "Skip search for targets: source subvolume is not read-only: $src_vol->{PRINT}";
|
||||||
return @ret_receive_targets;
|
return @ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
# find matches by comparing uuid / received_uuid
|
# find matches by comparing uuid / received_uuid
|
||||||
my $uuid = $src_vol->{node}{uuid};
|
my $uuid = $src_vol->{node}{uuid};
|
||||||
my $received_uuid;
|
my $received_uuid = $src_vol->{node}{received_uuid};
|
||||||
if($src_vol->{node}{received_uuid} ne '-') {
|
$received_uuid = undef if($received_uuid eq '-');
|
||||||
TRACE "get_receive_targets: source subvolume has received_uuid";
|
TRACE "get_receive_targets: src_vol=\"$src_vol->{PRINT}\", droot=\"$droot->{PRINT}\"";
|
||||||
$received_uuid = $src_vol->{node}{received_uuid};
|
|
||||||
}
|
|
||||||
|
|
||||||
die("subvolume info not present: $uuid") unless($uuid_cache{$uuid});
|
|
||||||
foreach (@$droot_subvols) {
|
foreach (@$droot_subvols) {
|
||||||
next unless($_->{node}{readonly});
|
next unless($_->{node}{readonly});
|
||||||
my $matched = undef;
|
my $matched = undef;
|
||||||
|
@ -1866,43 +1862,64 @@ sub get_receive_targets($$;@)
|
||||||
elsif(defined($received_uuid) && ($_->{node}{received_uuid} eq $received_uuid)) {
|
elsif(defined($received_uuid) && ($_->{node}{received_uuid} eq $received_uuid)) {
|
||||||
$matched = 'by-received_uuid';
|
$matched = 'by-received_uuid';
|
||||||
}
|
}
|
||||||
if($matched) {
|
next unless($matched);
|
||||||
push(@all_receive_targets, $_);
|
|
||||||
if($opts{exact_match} && (not exists($_->{BTRBK_RAW}))) {
|
|
||||||
unless($_->{direct_leaf} && ($_->{NAME} eq $src_vol->{NAME})) {
|
|
||||||
TRACE "get_receive_targets: $matched: skip non-exact match: $_->{PRINT}";
|
|
||||||
WARN "Receive target of \"$src_vol->{PRINT}\" exists at unexpected location: $_->{PRINT}" if($opts{warn_unexpected});
|
|
||||||
$unexpected_count++;
|
|
||||||
next;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
TRACE "get_receive_targets: $matched: Found receive target: $_->{SUBVOL_PATH}";
|
|
||||||
push(@ret_receive_targets, $_);
|
|
||||||
}
|
|
||||||
|
|
||||||
if($opts{warn_unexpected}) {
|
TRACE "get_receive_targets: $matched: Found receive target: $_->{SUBVOL_PATH}";
|
||||||
# search in filesystem for matching received_uuid
|
push(@{$opts{seen}}, $_) if($opts{seen});
|
||||||
my @fs_match = grep({ (not $_->{is_root}) &&
|
if($opts{exact_match} && !exists($_->{BTRBK_RAW})) {
|
||||||
(($_->{received_uuid} eq $uuid) ||
|
if($_->{direct_leaf} && ($_->{NAME} eq $src_vol->{NAME})) {
|
||||||
(defined($received_uuid) && ($_->{received_uuid} eq $received_uuid)))
|
TRACE "get_receive_targets: exact_match: $_->{SUBVOL_PATH}";
|
||||||
} values(%{$droot->{node}{TREE_ROOT}{ID_HASH}}) );
|
}
|
||||||
foreach my $node (@fs_match) {
|
else {
|
||||||
next if(scalar grep( { $_->{node}{id} == $node->{id} } @all_receive_targets));
|
TRACE "get_receive_targets: $matched: skip non-exact match: $_->{PRINT}";
|
||||||
my $text;
|
WARN "Receive target of \"$src_vol->{PRINT}\" exists at unexpected location: $_->{PRINT}" if($opts{warn});
|
||||||
my @url = get_cached_url_by_uuid($node->{uuid});
|
next;
|
||||||
if(scalar(@url)) {
|
|
||||||
$text = vinfo($url[0])->{PRINT};
|
|
||||||
} else {
|
|
||||||
$text = '"' . _fs_path($node) . "\" (in filesystem at \"$droot->{PRINT}\")";
|
|
||||||
}
|
|
||||||
WARN "Receive target of \"$src_vol->{PRINT}\" exists at unexpected location: $text";
|
|
||||||
$unexpected_count++;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
${$opts{ret_unexpected}} = $unexpected_count if(ref $opts{ret_unexpected});
|
push(@ret, $_);
|
||||||
}
|
}
|
||||||
DEBUG "Found " . scalar(@ret_receive_targets) . " receive targets in \"$droot->{PRINT}/\" for: $src_vol->{PRINT}";
|
DEBUG "Found " . scalar(@ret) . " receive targets in \"$droot->{PRINT}/\" for: $src_vol->{PRINT}";
|
||||||
return @ret_receive_targets;
|
return @ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
sub get_receive_targets_fsroot($$@)
|
||||||
|
{
|
||||||
|
my $droot = shift // die;
|
||||||
|
my $src_vol = shift // die;
|
||||||
|
my %opts = @_;
|
||||||
|
my $id = $src_vol->{node}{id};
|
||||||
|
my $uuid = $src_vol->{node}{uuid};
|
||||||
|
my $received_uuid = $src_vol->{node}{received_uuid};
|
||||||
|
$received_uuid = undef if(defined($received_uuid) && ($received_uuid eq '-'));
|
||||||
|
|
||||||
|
my @unexpected;
|
||||||
|
my @exclude;
|
||||||
|
@exclude = map { $_->{node}{id} } @{$opts{exclude}} if($opts{exclude});
|
||||||
|
|
||||||
|
TRACE "get_receive_target_fsroot: uuid=$uuid, received_uuid=" . ($received_uuid // '-') . " exclude id={ " . join(', ', @exclude) . " }";
|
||||||
|
|
||||||
|
# search in filesystem for matching received_uuid
|
||||||
|
foreach my $node (
|
||||||
|
grep({ (not $_->{is_root}) &&
|
||||||
|
(($_->{received_uuid} eq $uuid) ||
|
||||||
|
(defined($received_uuid) && ($_->{received_uuid} eq $received_uuid)))
|
||||||
|
} values(%{$droot->{node}{TREE_ROOT}{ID_HASH}}) ) )
|
||||||
|
{
|
||||||
|
next if(scalar grep($_ == $node->{id}, @exclude));
|
||||||
|
push @unexpected, $node;
|
||||||
|
if($opts{warn}) {
|
||||||
|
my $text;
|
||||||
|
my @url = get_cached_url_by_uuid($node->{uuid});
|
||||||
|
if(scalar(@url)) {
|
||||||
|
$text = vinfo($url[0])->{PRINT};
|
||||||
|
} else {
|
||||||
|
$text = '"' . _fs_path($node) . "\" (in filesystem at \"$droot->{PRINT}\")";
|
||||||
|
}
|
||||||
|
WARN "Receive target of \"$src_vol->{PRINT}\" exists at unexpected location: $text";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return \@unexpected;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2643,18 +2660,17 @@ sub macro_archive_target($$$;$)
|
||||||
my @schedule;
|
my @schedule;
|
||||||
|
|
||||||
# NOTE: this is pretty much the same as "resume missing"
|
# NOTE: this is pretty much the same as "resume missing"
|
||||||
my $abort_unexpected_location = 0;
|
my @unexpected_location;
|
||||||
foreach my $svol (@{vinfo_subvol_list($sroot, sort => 'path')})
|
foreach my $svol (@{vinfo_subvol_list($sroot, sort => 'path')})
|
||||||
{
|
{
|
||||||
next unless($svol->{node}{readonly});
|
next unless($svol->{node}{readonly});
|
||||||
next unless($svol->{btrbk_direct_leaf} && ($svol->{BTRBK_BASENAME} eq $snapshot_name));
|
next unless($svol->{btrbk_direct_leaf} && ($svol->{BTRBK_BASENAME} eq $snapshot_name));
|
||||||
|
|
||||||
my $unexpected_count = 0;
|
my $warning_seen = [];
|
||||||
my @receive_targets = get_receive_targets($droot, $svol, exact_match => 1, warn_unexpected => 1, ret_unexpected => \$unexpected_count);
|
my @receive_targets = get_receive_targets($droot, $svol, exact_match => 1, warn => 1, seen => $warning_seen );
|
||||||
# don't abort right here, we want to warn about all unexpected targets
|
push @unexpected_location, get_receive_targets_fsroot($droot, $svol, exclude => $warning_seen, warn => 1); # warn if unexpected on fs
|
||||||
$abort_unexpected_location += $unexpected_count;
|
|
||||||
next if(scalar(@receive_targets));
|
|
||||||
|
|
||||||
|
next if(scalar(@receive_targets));
|
||||||
DEBUG "Adding archive candidate: $svol->{PRINT}";
|
DEBUG "Adding archive candidate: $svol->{PRINT}";
|
||||||
|
|
||||||
push @schedule, { value => $svol,
|
push @schedule, { value => $svol,
|
||||||
|
@ -2664,7 +2680,7 @@ sub macro_archive_target($$$;$)
|
||||||
}
|
}
|
||||||
|
|
||||||
# this is a bit harsh, disabled for now
|
# this is a bit harsh, disabled for now
|
||||||
# if($abort_unexpected_location) {
|
# if(scalar(@unexpected_location) {
|
||||||
# ABORTED($droot, "Receive targets of archive candidates exist at unexpected location");
|
# ABORTED($droot, "Receive targets of archive candidates exist at unexpected location");
|
||||||
# WARN "Skipping archiving of \"$sroot->{PRINT}/${snapshot_name}.*\": $abrt";
|
# WARN "Skipping archiving of \"$sroot->{PRINT}/${snapshot_name}.*\": $abrt";
|
||||||
# return undef;
|
# return undef;
|
||||||
|
@ -4498,7 +4514,10 @@ MAIN:
|
||||||
|
|
||||||
foreach my $child (@snapshot_children)
|
foreach my $child (@snapshot_children)
|
||||||
{
|
{
|
||||||
next if(scalar(get_receive_targets($droot, $child, exact_match => 1, warn_unexpected => 1)));
|
my $warning_seen = [];
|
||||||
|
my @receive_targets = get_receive_targets($droot, $child, exact_match => 1, warn => 1, seen => $warning_seen );
|
||||||
|
get_receive_targets_fsroot($droot, $child, exclude => $warning_seen, warn => 1); # warn on unexpected on fs
|
||||||
|
next if(scalar(@receive_targets));
|
||||||
|
|
||||||
if(my $err_vol = vinfo_subvol($droot, $child->{NAME})) {
|
if(my $err_vol = vinfo_subvol($droot, $child->{NAME})) {
|
||||||
WARN "Target subvolume \"$err_vol->{PRINT}\" exists, but is not a receive target of \"$child->{PRINT}\"";
|
WARN "Target subvolume \"$err_vol->{PRINT}\" exists, but is not a receive target of \"$child->{PRINT}\"";
|
||||||
|
|
Loading…
Reference in New Issue