From 44bf3c8222ca0dc2c61af3bb6344223724b5f01f Mon Sep 17 00:00:00 2001 From: Tim Shimmin Date: Fri, 26 May 2006 04:02:17 +0000 Subject: [PATCH] Test out pv#953263 by creating AGI unlinked lists for recovery and looking in logprint for CLEAR_AGI_BUCKET transactions. Merge of master-melb:xfs-cmds:26042a by kenmcd. Test for pv#953263. --- 121 | 89 +++++++++++++++++++++++++++++++++++++++++ 121.out | 14 +++++++ group | 3 +- src/Makefile | 6 ++- src/multi_open_unlink.c | 81 +++++++++++++++++++++++++++++++++++++ 5 files changed, 191 insertions(+), 2 deletions(-) create mode 100755 121 create mode 100644 121.out create mode 100644 src/multi_open_unlink.c diff --git a/121 b/121 new file mode 100755 index 00000000..cfc6386f --- /dev/null +++ b/121 @@ -0,0 +1,89 @@ +#! /bin/sh +# FS QA Test No. 121 +# +# To test log replay for the unlinked list. +# So we create unlinked and still referenced inodes +# and make sure that no clearing of the unlinked AGI buckets +# are happening. +# See pv#953263. +# +#----------------------------------------------------------------------- +# Copyright (c) 2006 Silicon Graphics, Inc. All Rights Reserved. +#----------------------------------------------------------------------- +# +# creator +owner=tes@sgi.com + +seq=`basename $0` +echo "QA output created by $seq" + +here=`pwd` +tmp=/tmp/$$ +status=1 # failure is the default! +trap "rm -f $tmp.*; 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 +delay=5 +echo "open and unlink $num_files files" +src/multi_open_unlink $SCRATCH_MNT/test_file $num_files $delay & + +# time to create and unlink all the files +sleep 3 + +echo "godown" +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 + +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..." +xfs_logprint -t $SCRATCH_DEV | grep CLEAR + +# success, all done +status=0 +exit diff --git a/121.out b/121.out new file mode 100644 index 00000000..fcc7209f --- /dev/null +++ b/121.out @@ -0,0 +1,14 @@ +QA output created by 121 +mkfs +mount +open and unlink 200 files +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... diff --git a/group b/group index 888760d7..1955b67b 100644 --- a/group +++ b/group @@ -196,4 +196,5 @@ aio nathans@sgi.com 117 attr auto 118 quota 119 log v2log -120 auto \ No newline at end of file +120 auto +121 log auto diff --git a/src/Makefile b/src/Makefile index 84d34681..c82e8289 100644 --- a/src/Makefile +++ b/src/Makefile @@ -9,7 +9,8 @@ TARGETS = dirstress fill fill2 getpagesize holes lstat64 \ nametest permname randholes runas truncfile usemem \ mmapcat append_reader append_writer dirperf metaperf \ devzero feature alloc fault fstest t_access_root \ - godown resvtest writemod makeextents itrash + godown resvtest writemod makeextents itrash \ + multi_open_unlink LINUX_TARGETS = loggen xfsctl bstat t_mtab getdevicesize @@ -69,6 +70,9 @@ resvtest: resvtest.o itrash: itrash.o $(LINKTEST) +multi_open_unlink: multi_open_unlink.o + $(LINKTEST) + #scaleread: scaleread.o $(LDLIBS) # $(LINKTEST) diff --git a/src/multi_open_unlink.c b/src/multi_open_unlink.c new file mode 100644 index 00000000..8c77bfdd --- /dev/null +++ b/src/multi_open_unlink.c @@ -0,0 +1,81 @@ +/* + * Copyright (c) 2006 Silicon Graphics, Inc. + * All Rights Reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* + * multi_open_unlink path_prefix num_files sleep_time + * 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. + */ + +int +main(int argc, char *argv[]) +{ + char *given_path; + char path[PATH_MAX]; + char *prog = argv[0]; + int sleep_time; + int num_files; + int fd = -1; + int i; + + if (argc != 4) { + fprintf(stderr, "Usage: %s path_prefix num_files sleep_time\n", prog); + return 1; + } + + 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); + + /* if file already exists then error out */ + if (access(path, F_OK) == 0) { + fprintf(stderr, "%s: file \"%s\" already exists\n", prog, path); + return 1; + } + + fd = open(path, O_RDWR|O_CREAT|O_EXCL); + if (fd == -1) { + fprintf(stderr, "%s: failed to create \"%s\": %s\n", prog, path, strerror(errno)); + return 1; + } + + if (unlink(path) == -1) { + fprintf(stderr, "%s: failed to unlink \"%s\": %s\n", prog, path, strerror(errno)); + return 1; + } + } + + sleep(sleep_time); + + return 0; +} -- 2.39.5