file systems, or multiple file system setups in a single run without any
 help of external scripts.
 
+
+Syntax
+------
+
 Syntax for defining a section is the following:
 
-[section_name]
+       [section_name]
 
 Section name should consist of alphanumeric characters and '_'. Anything
 else is forbidden and the section will not be recognised.
 
 Each section in the configuration file should contain options in the format
 
-OPTION=value
+       OPTION=value
 
 'OPTION' must not contain any white space characters. 'value' can contain
 any character you want with one simple limitation - characters ' and " can
 have to be specified in each and every sections. However caution should be
 exercised not to leave unwanted options set from previous sections.
 
+
+Results
+-------
+
 For every section xfstests will run with specified options and will produce
 separate results in the '$RESULT_BASE/$section_name' directory.
 
+
+Multiple file systems
+---------------------
+
+Having different file systems in different config sections is allowed. When
+FSTYP differs in the following section the FSTYP file system will be created
+automatically before running the test.
+
+Note that if MOUNT_OPTIONS, MKFS_OPTIONS, or FSCK_OPTIONS are not directly
+specified in the section it will be reset to the default for a given file
+system.
+
+You can also force the file system recreation by specifying RECREATE_TEST_DEV.
+
+
+Example
+-------
+
 Here is an example of config file with sections:
 
 [ext4_4k_block_size]
 SCRATCH_MNT=/mnt/test1
 MKFS_OPTIONS="-q -F -b4096"
 FSTYP=ext4
+RESULT_BASE="`pwd`/results/`date +%d%m%y_%H%M%S`"
 
 [ext4_1k_block_size]
 MKFS_OPTIONS="-q -F -b1024"
 [ext4_nojournal]
 MKFS_OPTIONS="-q -F -b4096 -O ^has_journal"
 
-[ext4_discard_ssd]
-MKFS_OPTIONS="-q -F -b4096"
-TEST_DEV=/dev/sdc
-SCRATCH_DEV=/dev/sdd
-MOUNT_OPTIONS="-o discard"
+[xfs_filesystem]
+MKFS_OPTIONS="-f"
+FSTYP=xfs
+
+[ext3_filesystem]
+FSTYP=ext3
+MOUNT_OPTIONS="-o noatime"
 
        done
 fi
 
-_prepare_test_list
-
 # we need common/rc
 if ! . ./common/rc
 then
        rm -f $tmp.*
 }
 
+_prepare_test_list
+
 if $OPTIONS_HAVE_SECTIONS; then
        trap "_summary; exit \$status" 0 1 2 3 15
 else
 fi
 
 for section in $HOST_OPTIONS_SECTIONS; do
+       OLD_FSTYP=$FSTYP
        get_next_config $section
-       init_rc
 
        mkdir -p $RESULT_BASE
        if [ ! -d $RESULT_BASE ]; then
                exit 1;
        fi
 
+       if $OPTIONS_HAVE_SECTIONS; then
+               echo "SECTION       -- $section"
+       fi
+
+       if $RECREATE_TEST_DEV || [ "$OLD_FSTYP" != "$FSTYP" ]; then
+               echo "RECREATING    -- $FSTYP on $TEST_DEV"
+               umount $TEST_DEV 2> /dev/null
+               if ! _test_mkfs >$tmp.err 2>&1
+               then
+                       echo "our local _test_mkfs routine ..."
+                       cat $tmp.err
+                       echo "check: failed to mkfs \$TEST_DEV using specified options"
+                       exit 1
+               fi
+               out=`_mount_or_remount_rw "$MOUNT_OPTIONS" $TEST_DEV $TEST_DIR`
+               if [ $? -ne 1 ]; then
+                       echo $out
+                       exit 1
+               fi
+               _prepare_test_list
+       fi
+
+       init_rc
+
        seq="check"
        check="$RESULT_BASE/check"
 
        [ -f $check.time ] || touch $check.time
 
        # print out our test configuration
-       if $OPTIONS_HAVE_SECTIONS; then
-               echo "SECTION       -- $section"
-       fi
        echo "FSTYP         -- `_full_fstyp_details`"
        echo "PLATFORM      -- `_full_platform_details`"
        if [ ! -z "$SCRATCH_DEV" ]; then
 
 export MALLOCLIB=${MALLOCLIB:=/usr/lib/libefence.a}
 export LOCAL_CONFIGURE_OPTIONS=${LOCAL_CONFIGURE_OPTIONS:=--enable-readline=yes}
 
+export RECREATE_TEST_DEV=false
+
 # $1 = prog to look for, $2* = default pathnames if not found in $PATH
 set_prog_path()
 {
         ;;
 esac
 
+_mount_opts()
+{
+       # SELinux adds extra xattrs which can mess up our expected output.
+       # So, mount with a context, and they won't be created
+       # # nfs_t is a "liberal" context so we can use it.
+       if [ -x /usr/sbin/selinuxenabled ] && /usr/sbin/selinuxenabled; then
+               SELINUX_MOUNT_OPTIONS="-o context=system_u:object_r:nfs_t:s0"
+               export SELINUX_MOUNT_OPTIONS
+       fi
+
+       case $FSTYP in
+       xfs)
+               export MOUNT_OPTIONS=$XFS_MOUNT_OPTIONS
+               ;;
+       udf)
+               export MOUNT_OPTIONS=$UDF_MOUNT_OPTIONS
+               ;;
+       nfs)
+               export MOUNT_OPTIONS=$NFS_MOUNT_OPTIONS
+               ;;
+       ext2|ext3|ext4|ext4dev)
+               # acls & xattrs aren't turned on by default on ext$FOO
+               export MOUNT_OPTIONS="-o acl,user_xattr $EXT_MOUNT_OPTIONS"
+               ;;
+       reiserfs)
+               # acls & xattrs aren't turned on by default on reiserfs
+               export MOUNT_OPTIONS="-o acl,user_xattr $REISERFS_MOUNT_OPTIONS"
+               ;;
+       gfs2)
+               # acls aren't turned on by default on gfs2
+               export MOUNT_OPTIONS="-o acl $GFS2_MOUNT_OPTIONS"
+               ;;
+       *)
+               ;;
+       esac
+}
+
+_mkfs_opts()
+{
+       case $FSTYP in
+       xfs)
+               export MKFS_OPTIONS=$XFS_MKFS_OPTIONS
+               ;;
+       udf)
+               [ ! -z "$udf_fsize" ] && \
+                       UDF_MKFS_OPTIONS="$UDF_MKFS_OPTIONS -s $udf_fsize"
+               export MKFS_OPTIONS=$UDF_MKFS_OPTIONS
+               ;;
+       nfs)
+               export MKFS_OPTIONS=$NFS_MKFS_OPTIONS
+               ;;
+       reiserfs)
+               export MKFS_OPTIONS="$REISERFS_MKFS_OPTIONS -q"
+               ;;
+       gfs2)
+               export MKFS_OPTIONS="$GFS2_MKFS_OPTIONS -O -p lock_nolock"
+               ;;
+       jfs)
+               export MKFS_OPTIONS="$JFS_MKFS_OPTIONS -q"
+               ;;
+       *)
+               ;;
+       esac
+}
+
+_fsck_opts()
+{
+       case $FSTYP in
+       ext2|ext3|ext4|ext4dev)
+               export FSCK_OPTIONS="-nf"
+               ;;
+       reiserfs)
+               export FSCK_OPTIONS="--yes"
+               ;;
+       *)
+               export FSCK_OPTIONS="-n"
+               ;;
+       esac
+}
+
+[ -z "$FSTYP" ] && export FSTYP=xfs
+[ -z "$MOUNT_OPTIONS" ] && _mount_opts
+[ -z "$MKFS_OPTIONS" ] && _mkfs_opts
+[ -z "$FSCK_OPTIONS" ] && _fsck_opts
+
 known_hosts()
 {
        [ "$HOST_CONFIG_DIR" ] || HOST_CONFIG_DIR=`pwd`/configs
 }
 
 get_next_config() {
+       local OLD_FSTYP=$FSTYP
+       local OLD_MOUNT_OPTIONS=$MOUNT_OPTIONS
+       local OLD_MKFS_OPTIONS=$MKFS_OPTIONS
+       local OLD_FSCK_OPTIONS=$FSCK_OPTIONS
+
+       unset MOUNT_OPTIONS
+       unset MKFS_OPTIONS
+       unset FSCK_OPTIONS
+
        parse_config_section $1
 
+       if [ -n "$OLD_FSTYP" ] && [ $OLD_FSTYP != $FSTYP ]; then
+               [ -z "$MOUNT_OPTIONS" ] && _mount_opts
+               [ -z "$MKFS_OPTIONS" ] && _mkfs_opts
+               [ -z "$FSCK_OPTIONS" ] && _fsck_opts
+       else
+               [ -z "$MOUNT_OPTIONS" ] && export MOUNT_OPTIONS=$OLD_MOUNT_OPTIONS
+               [ -z "$MKFS_OPTIONS" ] && export MKFS_OPTIONS=$OLD_MKFS_OPTIONS
+               [ -z "$FSCK_OPTIONS" ] && export FSCK_OPTIONS=$OLD_FSCK_OPTIONS
+       fi
+
        # set default RESULT_BASE
        if [ -z "$RESULT_BASE" ]; then
                export RESULT_BASE="$here/results/"
 
     esac
 }
 
-[ -z "$FSTYP" ] && FSTYP=xfs
-[ -z "$MOUNT_OPTIONS" ] && _mount_opts
-[ -z "$MKFS_OPTIONS" ] && _mkfs_opts
-[ -z "$FSCK_OPTIONS" ] && _fsck_opts
-
-
 # we need common/config
 if [ "$iam" != "check" ]
 then
        fi
        return 0
 }
+
 _scratch_mkfs_ext4()
 {
        local tmp_dir=/tmp/
        return $mkfs_status
 }
 
+_test_mkfs()
+{
+    case $FSTYP in
+    nfs*)
+       # do nothing for nfs
+       ;;
+    udf)
+        $MKFS_UDF_PROG $MKFS_OPTIONS $* $TEST_DEV > /dev/null
+       ;;
+    btrfs)
+        $MKFS_BTRFS_PROG $MKFS_OPTIONS $* $TEST_DEV > /dev/null
+       ;;
+    *)
+       yes | $MKFS_PROG -t $FSTYP -- $MKFS_OPTIONS $* $TEST_DEV
+       ;;
+    esac
+}
+
 _scratch_mkfs()
 {
     case $FSTYP in
     _notrun "not suitable for this filesystem type: $FSTYP"
 }
 
+
 # tests whether $FSTYP is one of the supported OSes for a test
 #
 _supported_os()