Index: os-prober/linux-boot-prober =================================================================== --- os-prober.orig/linux-boot-prober +++ os-prober/linux-boot-prober @@ -67,7 +67,12 @@ if [ "$type" = btrfs ]; then fi if [ -z "$mpoint" ]; then # mount the btrfs root - if ! mount -o subvol=$subvol -t btrfs -U $UUID "$tmpmnt" 2>/dev/null; then + + if [ -n "$subvol" ]; then + opts="-o subvol=$subvol" + fi + + if ! mount $opts -t btrfs -U $UUID "$tmpmnt" 2>/dev/null; then warn "error mounting btrfs subvol=$subvol UUID=$UUID" umount "$tmpmnt/boot" 2>/dev/null umount "$tmpmnt" 2>/dev/null Index: os-prober/os-probes/common/50mounted-tests =================================================================== --- os-prober.orig/os-probes/common/50mounted-tests +++ os-prober/os-probes/common/50mounted-tests @@ -114,6 +114,47 @@ if [ "$types" != "btrfs" ]; then exit 1 fi +probe_subvol () +{ + local subvol=$1 + local partition=$2 + local UUID=$3 + local tmpmnt=$4 + + mounted= + mpoint="$(grep btrfs /proc/self/mountinfo | grep "$partition " | grep "/$subvol " | cut -d ' ' -f 5)" + ret=1 + + if [ -n "$subvol" ]; then + opts="-o subvol=$subvol" + fi + + if [ -n "$mpoint" ]; then + if [ "x$mpoint" = "x/" ]; then + continue # this is the root for the running system + fi + mounted=1 + else + # again, do not mount btrfs ro + mount -t btrfs $opts -U "$UUID" "$tmpmnt" + mpoint="$tmpmnt" + fi + test="/usr/lib/os-probes/mounted/90linux-distro" + if [ -f "$test" ] && [ -x "$test" ]; then + debug "running subtest $test" + if "$test" "$partition" "$mpoint" btrfs "UUID=$UUID" "subvol=$subvol"; then + debug "os found by subtest $test on subvol $subvol" + ret=0 + fi + fi + if [ -z "$mounted" ]; then + if ! umount "$tmpmnt"; then + warn "failed to umount $tmpmnt" + fi + fi + return $ret +} + # all btrfs processing here. Handle both unmounted and # mounted subvolumes. if [ "$types" = btrfs ]; then @@ -136,45 +177,23 @@ if [ "$types" = btrfs ]; then rmdir "$tmpmnt" || true exit 1 fi - if [ -z "$subvols" ]; then - debug "no subvols found on btrfs volume $UUID" - exit 1 - fi + found= - for subvol in $subvols; do - debug "begin btrfs processing for $UUID subvol=$subvol" - if [ "$subvol" != "$defaultvol" ]; then - if echo "$rosubvols" | grep -q -x "$subvol"; then - continue - fi - if echo "$sssubvols" | grep -q -x "$subvol"; then - continue - fi - fi - mounted= - mpoint="$(grep btrfs /proc/self/mountinfo | grep "$partition " | grep "/$subvol " | cut -d ' ' -f 5)" - if [ -n "$mpoint" ]; then - if [ "x$mpoint" = "x/" ]; then - continue # this is the root for the running system - fi - mounted=1 - else - # again, do not mount btrfs ro - mount -t btrfs -o subvol="$subvol" -U "$UUID" "$tmpmnt" - mpoint="$tmpmnt" - fi - test="/usr/lib/os-probes/mounted/90linux-distro" - if [ -f "$test" ] && [ -x "$test" ]; then - debug "running subtest $test" - if "$test" "$partition" "$mpoint" btrfs "UUID=$UUID" "subvol=$subvol"; then - debug "os found by subtest $test on subvol $subvol" - found=1 - fi + # Always probe subvol or root set as default + if probe_subvol "$defaultvol" "$partition" "$UUID" "$tmpmnt"; then + found=1 + fi + + # Probe any other OS on subvol + for subvol in $subvols; do + if echo "$rosubvols" | grep -q -x "$subvol" || + echo "$sssubvols" | grep -q -x "$subvol" || + echo "$defaultvol" | grep -q -x "$subvol"; then + continue fi - if [ -z "$mounted" ]; then - if ! umount "$tmpmnt"; then - warn "failed to umount $tmpmnt" - fi + debug "begin btrfs processing for $UUID subvol=$subvol" + if probe_subvol "$subvol" "$partition" "$UUID" "$tmpmnt"; then + found=1 fi done rmdir "$tmpmnt" || true