test out xfs_inactive_attrs in log replay for iunlink processing.
authorTim Shimmin <tes@sgi.com>
Mon, 17 Sep 2007 06:14:40 +0000 (06:14 +0000)
committerTim Shimmin <tes@sgi.com>
Mon, 17 Sep 2007 06:14:40 +0000 (06:14 +0000)
Merge of master-melb:xfs-cmds:29701a by kenmcd.

  Update args to use command options for multi_open_unlink.
  Change a sleep to a wait as we were just sleeping to account
  for the death of a process - should really wait for its death.

121
181 [new file with mode: 0755]
181.out [new file with mode: 0644]
group
src/Makefile
src/multi_open_unlink.c

diff --git a/121 b/121
index dd98d6559a9d3facbf60878c346356ce091ec4cd..b760be7560574168fe10d2446c152d9d89895680 100755 (executable)
--- a/121
+++ b/121
@@ -50,7 +50,7 @@ _scratch_mount >>$seq.full 2>&1 \
 num_files=200
 delay=5
 echo "open and unlink $num_files files"
-src/multi_open_unlink $SCRATCH_MNT/test_file $num_files $delay &
+src/multi_open_unlink -f $SCRATCH_MNT/test_file -n $num_files -s $delay &
 
 # time to create and unlink all the files
 sleep 3
@@ -60,7 +60,7 @@ src/godown -v -f $SCRATCH_MNT >> $seq.full
 
 # time for multi_open_unlink to exit out after its delay
 # so we have no references and can unmount
-sleep 3
+wait 2>/dev/null
 
 echo "unmount"
 umount $SCRATCH_MNT
diff --git a/181 b/181
new file mode 100755 (executable)
index 0000000..30c33f4
--- /dev/null
+++ b/181
@@ -0,0 +1,115 @@
+#! /bin/sh
+# FS QA Test No. 181
+#
+# Like 121 only creating large EAs
+# As part of the iunlink processing in recovery it will call VN_RELE
+# which will inactivate the inodes and if they have EAs (which they
+# will here) also call xfs_inactive_attrs.
+# We want to test out this xfs_inactive_attrs code being called in recovery.
+#
+#-----------------------------------------------------------------------
+# Copyright (c) 2007 Silicon Graphics, Inc.  All Rights Reserved.
+#-----------------------------------------------------------------------
+#
+# creator
+owner=tes@sgi.com
+
+seq=`basename $0`
+echo "QA output created by $seq"
+
+_cleanup()
+{
+    rm -f $tmp.*
+    [ -n "$pid" ] && kill $pid
+}
+
+pid=""
+here=`pwd`
+tmp=/tmp/$$
+status=1       # failure is the default!
+trap "_cleanup; exit \$status" 0 1 2 3 15
+
+# get standard environment, filters and checks
+. ./common.rc
+. ./common.filter
+. ./common.log
+
+# real QA test starts here
+_supported_fs xfs
+_supported_os IRIX Linux
+
+rm -f $seq.full
+rm -f $tmp.log
+
+_require_scratch
+
+echo "mkfs"
+_scratch_mkfs_xfs >>$seq.full 2>&1 \
+    || _fail "mkfs scratch failed"
+
+echo "mount"
+_scratch_mount >>$seq.full 2>&1 \
+    || _fail "mount failed: $MOUNT_OPTIONS"
+
+# num_files must be greater than 64 (XFS_AGI_UNLINKED_BUCKETS)
+# so that there will be at least one linked list from one of
+# the 64 buckets, so that we can decode a di_next_unlinked field
+num_files=200
+num_eas=1
+ea_val_size=`expr 32 \* 1024`
+
+# sleep for ages and we will kill this pid when we are ready
+delay=100
+
+echo "open and unlink $num_files files with EAs"
+src/multi_open_unlink -f $SCRATCH_MNT/test_file -n $num_files -s $delay -e $num_eas -v $ea_val_size &
+pid=$!
+
+# time to create and unlink all the files
+sleep 10
+
+echo "godown"
+src/godown -v -f $SCRATCH_MNT >> $seq.full
+
+# kill the multi_open_unlink
+kill $pid 2>/dev/null
+wait $pid 2>/dev/null
+pid=""
+
+echo "unmount"
+umount $SCRATCH_MNT
+
+echo "logprint after going down..."
+_print_logstate
+
+echo "mount with replay"
+_scratch_mount $mnt >>$seq.full 2>&1 \
+    || _fail "mount failed: $mnt $MOUNT_OPTIONS"
+
+echo "godown"
+src/godown -v -f $SCRATCH_MNT >> $seq.full
+
+echo "unmount"
+umount $SCRATCH_MNT
+
+echo "logprint after going down..."
+_print_logstate
+
+echo "logprint to check for CLEAR_AGI_BUCKET..."
+if _scratch_xfs_logprint -t | tee -a $seq.full | grep CLEAR; then
+       echo 'CLEAR_AGI_BUCKET transactions found!!'
+       echo 'Are you running with an old xfs kernel - where the bug still exists?'
+else
+       echo 'No CLEAR_AGI_BUCKET found in transactions - great - test passed :)'
+fi
+
+# clean up dirty log with log recovery on mount
+_scratch_mount >> $seq.full 2>&1 \
+    || _fail "mount failed"
+
+# should now be peaches
+_check_scratch_fs
+
+# success, all done
+status=0
+exit
diff --git a/181.out b/181.out
new file mode 100644 (file)
index 0000000..716f1b9
--- /dev/null
+++ b/181.out
@@ -0,0 +1,15 @@
+QA output created by 181
+mkfs
+mount
+open and unlink 200 files with EAs
+godown
+unmount
+logprint after going down...
+dirty log
+mount with replay
+godown
+unmount
+logprint after going down...
+dirty log
+logprint to check for CLEAR_AGI_BUCKET...
+No CLEAR_AGI_BUCKET found in transactions - great - test passed :)
diff --git a/group b/group
index 1ee502b82ddc10831a8f420be50c7ad4b56b0e4e..8b5bb0bc5c6e82d485c0563a4e2b284270cd5cff 100644 (file)
--- a/group
+++ b/group
@@ -268,3 +268,4 @@ filestreams dgc@sgi.com
 178 mkfs other auto
 179 metadata rw auto
 180 metadata rw auto
+181 log auto
index 0ce115c695102cd389b9c5883742e96f8ce1caa5..637ed5d37ebbeda6160662cd8247854a205ca217 100644 (file)
@@ -74,7 +74,7 @@ itrash:       itrash.o
        $(LINKTEST)
 
 multi_open_unlink: multi_open_unlink.o
-       $(LINKTEST)
+       $(LINKTEST) $(LIBATTR) $(LDLIBS)
 
 #scaleread: scaleread.o $(LDLIBS)
 #      $(LINKTEST)
@@ -85,10 +85,10 @@ acl_get: acl_get.o $(LIBACL) $(LIBATTR)
 dmiperf: dmiperf.o $(LIBATTR)
        $(LINKTEST) $(LIBATTR) $(LDLIBS)
 
-preallo_rw_pattern_reader: 
+preallo_rw_pattern_reader:
        $(CC) -DREAD iopat.c -o preallo_rw_pattern_reader
 
-preallo_rw_pattern_writer: 
+preallo_rw_pattern_writer:
        $(CC) -DWRITE iopat.c -o preallo_rw_pattern_writer
 
 ftrunc: ftrunc.o
@@ -99,7 +99,7 @@ trunc: trunc.o
 
 fs_perms: fs_perms.o
        $(LINKTEST)
-       
+
 testx: testx.o
        $(LINKTEST)
 
index 8c77bfddd332fb0b60e58e93489fdd618ac37a20..2e90704e1cb1fb502aaf1a01d76c220d97df65fc 100644 (file)
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <fcntl.h>
+#include <attr/attributes.h>
+
+#define MAX_EA_NAME 30
 
 /*
  * multi_open_unlink path_prefix num_files sleep_time
- * e.g.  
+ * e.g.
  *   $ multi_open_unlink file 100 60
  *   Creates 100 files: file.1, file.2, ..., file.100
- *   unlinks them all but doesn't close them all until after 60 seconds. 
+ *   unlinks them all but doesn't close them all until after 60 seconds.
  */
 
+void
+usage(char *prog)
+{
+       fprintf(stderr, "Usage: %s [-e num-eas] [-f path_prefix] [-n num_files] [-s sleep_time] [-v ea-valuesize] \n", prog);
+       exit(1);
+}
+
 int
 main(int argc, char *argv[])
 {
-       char *given_path;
+       char *given_path = "file";
        char path[PATH_MAX];
        char *prog = argv[0];
-       int sleep_time;
-       int num_files;
+       int sleep_time = 60;
+       int num_files = 100;
+       int num_eas = 0;
+       int value_size = ATTR_MAX_VALUELEN;
        int fd = -1;
-       int i;
+       int i,j,c;
 
-       if (argc != 4) {
-               fprintf(stderr, "Usage: %s path_prefix num_files sleep_time\n", prog);
-               return 1;
+       while ((c = getopt(argc, argv, "e:f:n:s:v:")) != EOF) {
+               switch (c) {
+                       case 'e':   /* create eas */
+                               num_eas = atoi(optarg);
+                               break;
+                       case 'f':   /* file prefix */
+                               given_path = optarg;
+                               break;
+                       case 'n':   /* number of files */
+                               num_files = atoi(optarg);
+                               break;
+                       case 's':   /* sleep time */
+                               sleep_time = atoi(optarg);
+                               break;
+                       case 'v':  /* value size on eas */
+                               value_size = atoi(optarg);
+                               break;
+                       case '?':
+                               usage(prog);
+               }
        }
 
-       given_path = argv[1];
-       num_files = atoi(argv[2]);
-       sleep_time = atoi(argv[3]);
-
         /* create and unlink a bunch of files */
        for (i = 0; i < num_files; i++) {
                sprintf(path, "%s.%d", given_path, i+1);
@@ -69,8 +94,33 @@ main(int argc, char *argv[])
                        return 1;
                }
 
+               /* set the EAs */
+               for (j = 0; j < num_eas; j++) {
+                       int sts;
+                       char *attrvalue;
+                       char attrname[MAX_EA_NAME];
+                       int flags = 0;
+
+                       snprintf(attrname, MAX_EA_NAME, "user.name.%d", j);
+
+                       attrvalue = calloc(value_size, 1);
+                       if (attrvalue == NULL) {
+                               fprintf(stderr, "%s: failed to create EA value of size %d on path \"%s\": %s\n",
+                                       prog, value_size, path, strerror(errno));
+                               return 1;
+                       }
+
+                       sts = attr_set(path, attrname, attrvalue, value_size, flags);
+                       if (sts == -1) {
+                               fprintf(stderr, "%s: failed to create EA \"%s\" of size %d on path \"%s\": %s\n",
+                                       prog, attrname, value_size, path, strerror(errno));
+                               return 1;
+                       }
+               }
+
                if (unlink(path) == -1) {
-                       fprintf(stderr, "%s: failed to unlink \"%s\": %s\n", prog, path, strerror(errno));
+                       fprintf(stderr, "%s: failed to unlink \"%s\": %s\n",
+                               prog, path, strerror(errno));
                        return 1;
                }
        }