1#!/usr/bin/env bash 2# group: rw 3# 4# Test FUSE exports' allow-other option 5# 6# Copyright (C) 2021 Red Hat, Inc. 7# 8# This program is free software; you can redistribute it and/or modify 9# it under the terms of the GNU General Public License as published by 10# the Free Software Foundation; either version 2 of the License, or 11# (at your option) any later version. 12# 13# This program is distributed in the hope that it will be useful, 14# but WITHOUT ANY WARRANTY; without even the implied warranty of 15# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16# GNU General Public License for more details. 17# 18# You should have received a copy of the GNU General Public License 19# along with this program. If not, see <http://www.gnu.org/licenses/>. 20# 21 22seq=$(basename "$0") 23echo "QA output created by $seq" 24 25status=1 # failure is the default! 26 27_cleanup() 28{ 29 _cleanup_qemu 30 _cleanup_test_img 31 rm -f "$EXT_MP" 32} 33trap "_cleanup; exit \$status" 0 1 2 3 15 34 35# get standard environment, filters and checks 36. ../common.rc 37. ../common.filter 38. ../common.qemu 39 40_supported_fmt generic 41 42_supported_proto file # We create the FUSE export manually 43 44sudo -n -u nobody true || \ 45 _notrun 'Password-less sudo as nobody required to test allow_other' 46 47# $1: Export ID 48# $2: Options (beyond the node-name and ID) 49# $3: Expected return value (defaults to 'return') 50# $4: Node to export (defaults to 'node-format') 51fuse_export_add() 52{ 53 allow_other_not_supported='option allow_other only allowed if' 54 55 output=$( 56 success_or_failure=yes _send_qemu_cmd $QEMU_HANDLE \ 57 "{'execute': 'block-export-add', 58 'arguments': { 59 'type': 'fuse', 60 'id': '$1', 61 'node-name': '${4:-node-format}', 62 $2 63 } }" \ 64 "${3:-return}" \ 65 "$allow_other_not_supported" \ 66 | _filter_imgfmt 67 ) 68 69 if echo "$output" | grep -q "$allow_other_not_supported"; then 70 # Shut down qemu gracefully so it can unmount the export 71 _send_qemu_cmd $QEMU_HANDLE \ 72 "{'execute': 'quit'}" \ 73 'return' 74 75 wait=yes _cleanup_qemu 76 77 _notrun "allow_other not supported" 78 fi 79 80 echo "$output" 81} 82 83EXT_MP="$TEST_DIR/fuse-export" 84 85_make_test_img 64k 86touch "$EXT_MP" 87 88echo 89echo '=== Test permissions ===' 90 91# $1: allow-other value ('on'/'off'/'auto') 92run_permission_test() 93{ 94 _launch_qemu \ 95 -blockdev \ 96 "$IMGFMT,node-name=node-format,file.driver=file,file.filename=$TEST_IMG" 97 98 _send_qemu_cmd $QEMU_HANDLE \ 99 "{'execute': 'qmp_capabilities'}" \ 100 'return' 101 102 fuse_export_add 'export' \ 103 "'mountpoint': '$EXT_MP', 104 'allow-other': '$1'" 105 106 # Should always work 107 echo '(Removing all permissions)' 108 chmod 000 "$EXT_MP" 2>&1 | _filter_testdir | _filter_imgfmt 109 stat -c 'Permissions post-chmod: %a' "$EXT_MP" 110 111 # Should always work 112 echo '(Granting u+r)' 113 chmod u+r "$EXT_MP" 2>&1 | _filter_testdir | _filter_imgfmt 114 stat -c 'Permissions post-chmod: %a' "$EXT_MP" 115 116 # Should only work with allow-other: Otherwise, no permissions can be 117 # granted to the group or others 118 echo '(Granting read permissions for everyone)' 119 chmod 444 "$EXT_MP" 2>&1 | _filter_testdir | _filter_imgfmt 120 stat -c 'Permissions post-chmod: %a' "$EXT_MP" 121 122 echo 'Doing operations as nobody:' 123 # Change to TEST_DIR, so nobody will not have to attempt a lookup 124 pushd "$TEST_DIR" >/dev/null 125 126 # This is already prevented by the permissions (without allow-other, FUSE 127 # exports always have o-r), but test it anyway 128 sudo -n -u nobody cat fuse-export >/dev/null 129 130 # If the only problem were the lack of permissions, we should still be able 131 # to stat the export as nobody; it should not work without allow-other, 132 # though 133 sudo -n -u nobody \ 134 stat -c 'Permissions seen by nobody: %a' fuse-export 2>&1 \ 135 | _filter_imgfmt 136 137 # To prove the point, revoke read permissions for others and try again 138 chmod o-r fuse-export 2>&1 | _filter_testdir | _filter_imgfmt 139 140 # Should fail 141 sudo -n -u nobody cat fuse-export >/dev/null 142 # Should work with allow_other 143 sudo -n -u nobody \ 144 stat -c 'Permissions seen by nobody: %a' fuse-export 2>&1 \ 145 | _filter_imgfmt 146 147 popd >/dev/null 148 149 _send_qemu_cmd $QEMU_HANDLE \ 150 "{'execute': 'quit'}" \ 151 'return' 152 153 wait=yes _cleanup_qemu 154} 155 156# 'auto' should behave exactly like 'on', because 'on' tests that 157# allow_other works (otherwise, this test is skipped) 158for ao in off on auto; do 159 echo 160 echo "--- allow-other=$ao ---" 161 162 run_permission_test "$ao" 163done 164 165# success, all done 166echo "*** done" 167rm -f $seq.full 168status=0 169