Whamcloud - gitweb
New tag 2.15.91
[fs/lustre-release.git] / lustre / tests / sanity-krb5.sh
index 656fb2e..c0418b2 100755 (executable)
@@ -318,6 +318,7 @@ run_test 3 "local cache under DLM lock"
 test_5() {
        local file1=$DIR/$tdir/$tfile-1
        local file2=$DIR/$tdir/$tfile-2
+       local file3=$DIR/$tdir/$tfile-3
        local wait_time=$((TIMEOUT + TIMEOUT / 2))
 
        mkdir $DIR/$tdir || error "mkdir $DIR/$tdir failed"
@@ -328,25 +329,44 @@ test_5() {
        [ -f $file1 ] || error "$file1 not found"
 
        # flush context
-       $RUNAS $LFS flushctx $MOUNT || error "can't flush context"
+       $RUNAS $LFS flushctx $MOUNT || error "can't flush context (1)"
 
        # stop lsvcgssd
        send_sigint $(comma_list $(mdts_nodes)) $LSVCGSSD
        sleep 5
        check_gss_daemon_nodes $(comma_list $(mdts_nodes)) $LSVCGSSD &&
-               error "$LSVCGSSD still running"
+               error "$LSVCGSSD still running (1)"
+
+       # daemon should restart automatically, at least on newer servers
+       $RUNAS touch $file2
+       if [ $? -ne 0 ]; then
+               echo "$RUNAS touch $file2 failed"
+               (( MDS1_VERSION < $(version_code 2.15.61) )) ||
+                       error "$LSVCGSSD should restart automatically"
+       else
+               echo "$RUNAS touch $file2 succeeded"
+       fi
 
-       $RUNAS touch $file2 && error "should fail without $LSVCGSSD"
+       # flush context
+       if (( MDS1_VERSION >= $(version_code 2.15.61) )); then
+               $RUNAS $LFS flushctx $MOUNT || error "can't flush context (2)"
+       fi
+
+       # stop lsvcgssd
+       send_sigint $(comma_list $(mdts_nodes)) $LSVCGSSD
+       sleep 5
+       check_gss_daemon_nodes $(comma_list $(mdts_nodes)) $LSVCGSSD &&
+               error "$LSVCGSSD still running (2)"
 
        # restart lsvcgssd, expect touch succeed
        echo "restart $LSVCGSSD and recovering"
        start_gss_daemons $(comma_list $(mdts_nodes)) $LSVCGSSD "-vvv"
        sleep 5
        check_gss_daemon_nodes $(comma_list $(mdts_nodes)) $LSVCGSSD
-       $RUNAS touch $file2 || error "should not fail now"
-       [ -f $file2 ] || error "$file2 not found"
+       $RUNAS touch $file3 || error "should not fail now"
+       [ -f $file3 ] || error "$file3 not found"
 }
-run_test 5 "lsvcgssd dead, operations fail"
+run_test 5 "lsvcgssd dead, operations pass"
 
 test_6() {
        local nfile=10
@@ -398,7 +418,7 @@ test_8()
        stack_trap \
                "do_facet $SINGLEMDS $LCTL set_param at_history=$atoldbase" EXIT
 
-       mkdir -p $DIR/$tdir
+       mkdir_on_mdt0 $DIR/$tdir
        chmod a+w $DIR/$tdir
 
        $RUNAS ls $DIR/$tdir
@@ -439,6 +459,93 @@ test_8()
 }
 run_test 8 "Early reply sent for slow gss context negotiation"
 
+test_9() {
+       local test9user=$(getent passwd $RUNAS_ID | cut -d: -f1)
+
+       $LFS mkdir -i 0 -c 1 $DIR/$tdir || error "mkdir $DIR/$tdir failed"
+       chmod 0777 $DIR/$tdir || error "chmod $DIR/$tdir failed"
+       $RUNAS ls -ld $DIR/$tdir
+
+       # Add group, and client to new group, on client only.
+       # Server is not aware.
+       groupadd -g 5000 grptest9
+       stack_trap "groupdel grptest9" EXIT
+
+       usermod -g grptest9 $test9user
+       stack_trap "usermod -g $test9user $test9user" EXIT
+       id $RUNAS_ID
+       # Thanks to Kerberos, client should not be able to create file
+       # with primary group not known on server side
+       $RUNAS touch $DIR/$tdir/fileA &&
+               error "server should not trust client's primary gid"
+       do_facet mds1 "lctl set_param mdt.*.identity_flush=-1"
+
+       do_facet mds1 groupadd -g 5000 grptest9
+       stack_trap "do_facet mds1 groupdel grptest9 || true" EXIT
+       do_facet mds1 usermod -a -G grptest9 $test9user
+       stack_trap "do_facet mds1 gpasswd -d $test9user grptest9 || true" EXIT
+       id $RUNAS_ID
+       do_facet mds1 "id $RUNAS_ID"
+       # Thanks to Kerberos, client should be able to create file
+       # with primary group taken as one of supp groups, as long as
+       # server side knows the supp groups.
+       $RUNAS touch $DIR/$tdir/fileA ||
+               error "server should know client's supp gid"
+       ls -l $DIR/$tdir
+       do_facet mds1 "lctl set_param mdt.*.identity_flush=-1"
+       do_facet mds1 gpasswd -d $test9user grptest9
+       do_facet mds1 groupdel grptest9
+       usermod -g $test9user $test9user
+
+       usermod -a -G grptest9 $test9user
+       stack_trap "gpasswd -d $test9user grptest9" EXIT
+       id $RUNAS_ID
+       $RUNAS touch $DIR/$tdir/fileB
+       ls -l $DIR/$tdir
+       # Thanks to Kerberos, client should not be able to chgrp
+       $RUNAS chgrp grptest9 $DIR/$tdir/fileB &&
+               error "server should not trust client's supp gid"
+       ls -l $DIR/$tdir
+       do_facet mds1 "lctl set_param mdt.*.identity_flush=-1"
+}
+run_test 9 "Do not trust primary and supp gids from client"
+
+test_10() {
+       local count
+
+       $LFS mkdir -i 0 -c $MDSCOUNT $DIR/$tdir ||
+               error "mkdir $DIR/$tdir failed"
+       chmod 0777 $DIR/$tdir || error "chmod $DIR/$tdir failed"
+       $RUNAS ls -ld $DIR/$tdir || error "ls -ld $DIR/$tdir failed"
+       $RUNAS grep lgssc /proc/keys
+
+       # get rid of gss context and credentials for user
+       $RUNAS $LFS flushctx -k -r $MOUNT || error "can't flush context (1)"
+       $RUNAS grep lgssc /proc/keys
+       stack_trap restore_krb5_cred EXIT
+
+       # restore krb credentials
+       restore_krb5_cred
+
+       # revoke session keyring for user and access to fs in the same su -
+       su - $(id -n -u $RUNAS_ID) -c "keyctl revoke @s && ls -ld $DIR/$tdir" ||
+               error "revoke + ls failed"
+       $RUNAS grep lgssc /proc/keys
+
+       # refcount on lgssc keys should be 2
+       for ref in $($RUNAS grep lgssc /proc/keys | awk '$4~"perm"{print $3}');\
+         do
+               [[ $ref == 2 ]] || error "bad refcnt $ref on key"
+       done
+
+       # get rid of gss context for user
+       $RUNAS $LFS flushctx $MOUNT || error "can't flush context (2)"
+       $RUNAS grep lgssc /proc/keys
+       count=$($RUNAS grep lgssc /proc/keys | grep -v "Running as" | wc -l)
+       [[ $count == 0 ]] || error "remaining $count keys for user"
+}
+run_test 10 "Support revoked session keyring"
+
 #
 # following tests will manipulate flavors and may end with any flavor set,
 # so each test should not assume any start flavor.
@@ -798,6 +905,102 @@ test_151() {
 }
 run_test 151 "secure mgs connection: server flavor control"
 
+exit_152() {
+       zconf_umount $HOSTNAME $MOUNT
+
+       # remove mgs rule
+       set_rule _mgs any any
+
+       zconf_mount $HOSTNAME $MOUNT
+       if [ "$MOUNT_2" ]; then
+               zconf_mount $HOSTNAME $MOUNT2
+       fi
+}
+
+test_152() {
+       local mount_opts
+       local count
+
+       (( MDS1_VERSION >= $(version_code 2.15.64) )) ||
+               skip "Need MDS >= 2.15.64 for user context with MGS"
+
+       stack_trap exit_152 EXIT
+
+       if is_mounted $MOUNT2; then
+               umount_client $MOUNT2 || error "umount $MOUNT2 failed"
+       fi
+
+       zconf_umount $HOSTNAME $MOUNT || error "umount $MOUNT failed"
+
+       # set mgs rule to only accept krb5p
+       set_rule _mgs any any krb5p
+
+       # start gss daemon on mgs node
+       combined_mgs_mds || start_gss_daemons $mgs_HOST $LSVCGSSD "-vvv"
+
+       # re-mount client with mgssec=krb5p
+       mount_opts="${MOUNT_OPTS:+$MOUNT_OPTS,}mgssec=krb5p"
+       zconf_mount $HOSTNAME $MOUNT $mount_opts ||
+               error "unable to mount client"
+
+       $RUNAS $LFS check mgts || error "check mgts as user failed"
+       $RUNAS grep lgssc /proc/keys
+
+       $RUNAS $LFS flushctx $MOUNT || error "flushctx as user failed"
+       $RUNAS grep lgssc /proc/keys
+       count=$($RUNAS grep lgssc /proc/keys | grep -v "Running as" | wc -l)
+       [[ $count == 0 ]] || error "remaining $count keys for user"
+}
+run_test 152 "secure mgs connection: user access"
+
+test_200() {
+       local nid=$(lctl list_nids | grep ${NETTYPE} | head -n1)
+       local nidstr="peer_nid: ${nid},"
+       local count
+
+       lfs df -h
+       do_facet $SINGLEMDS $LCTL get_param -n \
+               mdt.*-MDT0000.gss.srpc_serverctx | grep "$nidstr"
+       count=$(do_facet $SINGLEMDS $LCTL get_param -n \
+               mdt.*-MDT0000.gss.srpc_serverctx | grep "$nidstr" |
+               grep -c 'delta: -')
+       echo "found $count expired reverse contexts (1)"
+       # We can have up to 3 expired contexts in the normal case:
+       # - the newest one, that is just about to be renewed
+       # - the previous one that had expired
+       # - the one currently referenced in the sec, not updated in the absence
+       #   of client activity.
+       (( count < 4 )) || error "expired reverse contexts should be <= 3 (1)"
+
+       # unmount to get rid of old context
+       umount_client $MOUNT || error "umount $MOUNT failed"
+       kdestroy
+       stack_trap "mount_client $MOUNT ${MOUNT_OPTS} || true" EXIT
+       if is_mounted $MOUNT2; then
+               umount_client $MOUNT2 || error "umount $MOUNT2 failed"
+               stack_trap "mount_client $MOUNT2 ${MOUNT_OPTS}" EXIT
+       fi
+
+       # update ticket lifetime to be 45s
+       stack_trap "/usr/bin/cp -f /etc/krb5.conf.bkp /etc/krb5.conf" EXIT
+       sed -i.bkp s+[^#]ticket_lifetime.*+ticket_lifetime\ =\ 45s+ \
+               /etc/krb5.conf
+       # establish new context, and wait 3x lifetime
+       mount_client $MOUNT ${MOUNT_OPTS} || error "remount failed"
+       lfs df -h
+       sleep 135
+       # re-activate connections, and look for reverse contexts on server side
+       lfs df -h
+       do_facet $SINGLEMDS $LCTL get_param -n \
+               mdt.*-MDT0000.gss.srpc_serverctx | grep "$nidstr"
+       count=$(do_facet $SINGLEMDS $LCTL get_param -n \
+               mdt.*-MDT0000.gss.srpc_serverctx | grep "$nidstr" |
+               grep -c 'delta: -')
+       echo "found $count expired reverse contexts (2)"
+       (( count < 4 )) || error "expired reverse contexts should be <= 3 (2)"
+}
+run_test 200 "check expired reverse gss contexts"
+
 complete_test $SECONDS
 set_flavor_all null
 cleanup_gss