From 7ddfb40719e239ce1bcbcd2bdeedc843483a8302 Mon Sep 17 00:00:00 2001 From: CentOS Sources Date: Mar 05 2015 13:21:44 +0000 Subject: import gfs2-utils-3.1.7-6.el7 --- diff --git a/.gfs2-utils.metadata b/.gfs2-utils.metadata index 995608c..b9bded1 100644 --- a/.gfs2-utils.metadata +++ b/.gfs2-utils.metadata @@ -1 +1 @@ -646baa99ee0f8dd4075d0e2c920cb66feb9d3404 SOURCES/gfs2-utils-3.1.6.tar.gz +eef8cf193ba4ca8edb32cab40307e702ab73fc2c SOURCES/gfs2-utils-3.1.7.tar.gz diff --git a/.gitignore b/.gitignore index 4f5c39d..603e861 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1 @@ -SOURCES/gfs2-utils-3.1.6.tar.gz +SOURCES/gfs2-utils-3.1.7.tar.gz diff --git a/SOURCES/bz1000066-gfs2_utils_tests_Switch_to_autotest.patch b/SOURCES/bz1000066-gfs2_utils_tests_Switch_to_autotest.patch deleted file mode 100644 index 7c17c60..0000000 --- a/SOURCES/bz1000066-gfs2_utils_tests_Switch_to_autotest.patch +++ /dev/null @@ -1,399 +0,0 @@ -commit 5cfd080b0830e4d16ea8edcfbb8a0b5dce23c964 -Author: Andrew Price -Date: Mon Aug 19 12:59:58 2013 +0100 - - gfs2-utils tests: Switch to autotest - - Replaces the custom tool_tests.sh test harness with the Autotest - framework provided by Autoconf. See doc/README.tests for details. - - This is just a straight rework of the existing tests as Autotest test - groups. - - Resolves: rhbz#1000066 - - Signed-off-by: Andrew Price - -diff --git a/.gitignore b/.gitignore -index 26d89d0..ae72f2b 100644 ---- a/.gitignore -+++ b/.gitignore -@@ -44,7 +44,13 @@ gfs2/tune/tunegfs2 - test-driver - tests/check_libgfs2 - tests/testvol --tests/tests.log -+tests/testsuite.log -+tests/testsuite.dir -+tests/testsuite.trs -+tests/atconfig -+tests/atlocal -+tests/package.m4 -+tests/testsuite - ABOUT-NLS - po/Makevars.template - po/POTFILES -diff --git a/configure.ac b/configure.ac -index 911dd88..628d85e 100644 ---- a/configure.ac -+++ b/configure.ac -@@ -203,6 +203,7 @@ CPPFLAGS="-I\$(top_builddir)/make -I\$(top_srcdir)/make \ - -I. $ENV_CPPFLAGS" - LDFLAGS="$ENV_LDFLAGS" - -+AC_CONFIG_TESTDIR([tests], [gfs2/libgfs2:gfs2/mkfs:gfs2/fsck:gfs2/edit:gfs2/convert:gfs2/tune:tests]) - AC_CONFIG_FILES([Makefile - gfs2/Makefile - gfs2/include/Makefile -@@ -216,6 +217,7 @@ AC_CONFIG_FILES([Makefile - gfs2/scripts/Makefile - doc/Makefile - tests/Makefile -+ tests/atlocal - po/Makefile.in - ]) - -diff --git a/doc/README.tests b/doc/README.tests -new file mode 100644 -index 0000000..fa35803 ---- /dev/null -+++ b/doc/README.tests -@@ -0,0 +1,42 @@ -+Working with the gfs2-utils test suite -+-------------------------------------- -+ -+The test suite in the tests directory of the gfs2-utils source tree is based on -+the Autotest framework provided by Autoconf. The basic idea is that the -+testsuite.at file is the main source file for the tests, written in m4 and -+generating a bourne shell script called testsuite. -+ -+When run, either using 'make check' or directly from within the tests -+directory, the testsuite script sources atconfig and atlocal for configuration -+and then runs the whole testsuite or a specified set of tests (see ./testsuite -+-h for help). -+ -+A number of GFS2-specific convenience macros have been defined in testsuite.at -+to make defining new tests quick and easy. Also, some variables have been -+defined in atlocal.in so that full paths to programs do not have to be included -+in each test. Configuration should be specified in atlocal.in as atconfig is -+generated by the configure script and atlocal is generated from atlocal.in at -+build time. -+ -+To keep the test suite organised, the testsuite.at file sources the actual -+tests from other files, e.g. mkfs.at. -+ -+A single test, specified as a test group in Autotest terms, follows the form -+ -+ AT_SETUP([Test title]) -+ ...test goes here... -+ AT_CLEANUP -+ -+so, when adding tests, this is generally all that is required unless the tests -+do not fit into an existing category, in which case AT_BANNER can be used to -+group them, and they can be organised into a new .at file and sourced from -+testsuite.at. -+ -+Since the tests can be run individually (e.g. ./testsuite 15) any new tests -+which require the dummy volume $GFS_TGT to be present should call GFS_TGT_REGEN -+before attempting to use it. -+ -+Documentation for Autotest, including the AT_* macros used to define tests, can -+be found in the autoconf manual at: -+ -+ http://www.gnu.org/software/autoconf/manual/index.html -diff --git a/tests/Makefile.am b/tests/Makefile.am -index af01c49..3336304 100644 ---- a/tests/Makefile.am -+++ b/tests/Makefile.am -@@ -1,15 +1,64 @@ --TESTS_ENVIRONMENT = TOPBUILDDIR=$(top_builddir) --EXTRA_DIST = tool_tests.sh --CLEANFILES = tests.log -+EXTRA_DIST = $(TESTSUITE_AT) package.m4 $(TESTSUITE) atlocal atconfig -+DISTCLEANFILES = atlocal atconfig -+CLEANFILES = testvol - - if BUILD_TESTS --check_PROGRAMS = check_libgfs2 --check_libgfs2_SOURCES = check_meta.c \ -- $(top_srcdir)/gfs2/libgfs2/libgfs2.h --check_libgfs2_CFLAGS = -I$(top_srcdir)/gfs2/libgfs2 \ -- -I$(top_srcdir)/gfs2/include \ -- @check_CFLAGS@ --check_libgfs2_LDADD = $(top_builddir)/gfs2/libgfs2/libgfs2.la @check_LIBS@ -+check_PROGRAMS = check_libgfs2 -+ -+check_libgfs2_SOURCES = \ -+ check_meta.c \ -+ $(top_srcdir)/gfs2/libgfs2/libgfs2.h -+ -+check_libgfs2_CFLAGS = \ -+ -I$(top_srcdir)/gfs2/libgfs2 \ -+ -I$(top_srcdir)/gfs2/include \ -+ @check_CFLAGS@ -+ -+check_libgfs2_LDADD = \ -+ $(top_builddir)/gfs2/libgfs2/libgfs2.la \ -+ @check_LIBS@ - endif - --TESTS = $(check_PROGRAMS) tool_tests.sh -+# The `:;' works around a Bash 3.2 bug when the output is not writable. -+$(srcdir)/package.m4: $(top_srcdir)/configure.ac -+ :;{ \ -+ echo '# Signature of the current package.' && \ -+ echo 'm4_define([AT_PACKAGE_NAME],' && \ -+ echo ' [$(PACKAGE_NAME)])' && \ -+ echo 'm4_define([AT_PACKAGE_TARNAME],' && \ -+ echo ' [$(PACKAGE_TARNAME)])' && \ -+ echo 'm4_define([AT_PACKAGE_VERSION],' && \ -+ echo ' [$(PACKAGE_VERSION)])' && \ -+ echo 'm4_define([AT_PACKAGE_STRING],' && \ -+ echo ' [$(PACKAGE_STRING)])' && \ -+ echo 'm4_define([AT_PACKAGE_BUGREPORT],' && \ -+ echo ' [$(PACKAGE_BUGREPORT)])'; \ -+ echo 'm4_define([AT_PACKAGE_URL],' && \ -+ echo ' [$(PACKAGE_URL)])'; \ -+ } >'$(srcdir)/package.m4' -+ -+TESTSUITE_AT = \ -+ testsuite.at \ -+ mkfs.at \ -+ libgfs2.at -+ -+TESTSUITE = $(srcdir)/testsuite -+ -+check-local: atconfig atlocal $(TESTSUITE) -+ $(SHELL) '$(TESTSUITE)' $(TESTSUITEFLAGS) -+ -+installcheck-local: atconfig atlocal $(TESTSUITE) -+ $(SHELL) '$(TESTSUITE)' AUTOTEST_PATH='$(sbindir):tests' $(TESTSUITEFLAGS) -+ -+clean-local: -+ test ! -f '$(TESTSUITE)' || $(SHELL) '$(TESTSUITE)' --clean -+ -+atconfig: $(top_builddir)/config.status -+ cd $(top_builddir) && ./config.status tests/$@ -+ -+AUTOM4TE = $(SHELL) $(top_srcdir)/missing --run autom4te -+AUTOTEST = $(AUTOM4TE) --language=autotest -+ -+$(TESTSUITE): $(TESTSUITE_AT) package.m4 -+ $(AUTOTEST) -I '$(srcdir)' -o $@.tmp $@.at -+ mv $@.tmp $@ -diff --git a/tests/atlocal.in b/tests/atlocal.in -new file mode 100644 -index 0000000..660c87a ---- /dev/null -+++ b/tests/atlocal.in -@@ -0,0 +1,7 @@ -+GFS_TGT="$abs_builddir/testvol" -+GFS_TGT_SZ=10 -+ -+gfs_max_blocks() -+{ -+ printf $((GFS_TGT_SZ*1073741824/$1)) -+} -diff --git a/tests/libgfs2.at b/tests/libgfs2.at -new file mode 100644 -index 0000000..a6b478a ---- /dev/null -+++ b/tests/libgfs2.at -@@ -0,0 +1,5 @@ -+AT_BANNER([libgfs2 unit tests]) -+ -+AT_SETUP([Metadata check]) -+AT_CHECK([check_libgfs2], 0, [ignore], [ignore]) -+AT_CLEANUP -diff --git a/tests/mkfs.at b/tests/mkfs.at -new file mode 100644 -index 0000000..aff6a0d ---- /dev/null -+++ b/tests/mkfs.at -@@ -0,0 +1,64 @@ -+AT_TESTED([mkfs.gfs2]) -+AT_BANNER([mkfs.gfs2 tests]) -+ -+AT_SETUP([Locking protocol validation]) -+AT_CHECK([mkfs.gfs2 -O -p badprotocol $GFS_TGT], 255, [ignore], [ignore]) -+AT_CLEANUP -+ -+AT_SETUP([Resource group size validation]) -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -r 31 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -r 2049 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CLEANUP -+ -+AT_SETUP([Journal size validation]) -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -J 7 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -J 1025 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CLEANUP -+ -+AT_SETUP([Block count validation]) -+GFS_TGT_REGEN -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -b 512 $GFS_TGT $(($(gfs_max_blocks 512)+1))], 255, [ignore], [ignore]) -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -b 4096 $GFS_TGT $(($(gfs_max_blocks 4096)+1))], 255, [ignore], [ignore]) -+AT_CLEANUP -+ -+AT_SETUP([Quota change file size validation]) -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -c 0 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([mkfs.gfs2 -O -p lock_nolock -c 65 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CLEANUP -+ -+AT_SETUP([Locking protocols]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_dlm -t foo:bar $GFS_TGT]) -+AT_CLEANUP -+ -+AT_SETUP([Max. blocks, min. block size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 512 $GFS_TGT $(gfs_max_blocks 512)]) -+AT_CLEANUP -+ -+AT_SETUP([Max. blocks, max. block size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 4096 $GFS_TGT $(util_max_blocks 4096)]) -+AT_CLEANUP -+ -+AT_SETUP([Max. resource group size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -r 2048 $GFS_TGT]) -+AT_CLEANUP -+ -+AT_SETUP([Min. resource group size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -r 32 $GFS_TGT]) -+AT_CLEANUP -+ -+AT_SETUP([Max. journal size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -J 1024 $GFS_TGT]) -+AT_CLEANUP -+ -+AT_SETUP([Min. journal size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -J 8 $GFS_TGT]) -+AT_CLEANUP -+ -+AT_SETUP([Max. quota change file size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -c 64 $GFS_TGT]) -+AT_CLEANUP -+ -+AT_SETUP([Min. quota change file size]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -c 1 $GFS_TGT]) -+AT_CLEANUP -diff --git a/tests/testsuite.at b/tests/testsuite.at -new file mode 100644 -index 0000000..2c74985 ---- /dev/null -+++ b/tests/testsuite.at -@@ -0,0 +1,16 @@ -+# Regenerate the sparse file used for testing and skip the test if it fails -+m4_define([GFS_TGT_REGEN], -+[AT_CHECK([rm -f $GFS_TGT && truncate -s ${GFS_TGT_SZ}G ${GFS_TGT}], [ignore], [ignore], [ignore]) -+AT_SKIP_IF([test ! -f ${GFS_TGT}])]) -+ -+# Regenerate, check, fsck is used a lot so combine it into one macro -+m4_define([GFS_FSCK_CHECK], -+[GFS_TGT_REGEN -+AT_CHECK($1, 0, [ignore], [ignore]) -+AT_CHECK([fsck.gfs2 -n $GFS_TGT], 0, [ignore], [ignore])]) -+ -+AT_INIT([]) -+AT_COLOR_TESTS -+ -+m4_include([mkfs.at]) -+m4_include([libgfs2.at]) -diff --git a/tests/tool_tests.sh b/tests/tool_tests.sh -deleted file mode 100755 -index 7b9a5c3..0000000 ---- a/tests/tool_tests.sh -+++ /dev/null -@@ -1,94 +0,0 @@ --#!/bin/sh -- --# This script runs gfs2 utils with various options, checking exit codes against --# expected values. If any test fails to exit with an expected code, the exit code --# of the whole script will be non-zero but the tests will continue to be run. The --# sparse file which is used as the target of the tests can be configured by --# setting the environment variables TEST_TARGET (the filename) and TEST_TARGET_SZ --# (its apparent size in gigabytes). Defaults to "testvol" and 10GB. -- --MKFS="${TOPBUILDDIR}/gfs2/mkfs/mkfs.gfs2 -O" --FSCK="${TOPBUILDDIR}/gfs2/fsck/fsck.gfs2 -n" -- --# Name of the sparse file we'll use for testing --TEST_TARGET=${TEST_TARGET:-testvol} --# Log of test output --TEST_LOG=${TEST_LOG:-tests.log} --truncate -cs0 "${TEST_LOG}" --# Size, in GB, of the sparse file we'll create to run the tests --TEST_TARGET_SZ=${TEST_TARGET_SZ:-10} --[ $TEST_TARGET_SZ -gt 0 ] || { echo "Target size (in GB) must be greater than 0" >&2; exit 1; } --# Overall success (so we can keep going if one test fails) --TEST_RET=0 -- --fn_test() --{ -- local expected="$1" -- local cmd="$2" -- echo -n "** Test '$cmd'" | tee -a "${TEST_LOG}" -- $cmd &>> "${TEST_LOG}"; -- local ret=$? -- echo -n " (exp: $expected got: $ret) " | tee -a "${TEST_LOG}" -- if [ "$ret" != "$expected" ]; -- then -- echo "FAIL" | tee -a "${TEST_LOG}" -- TEST_RET=1 -- TEST_GRP_RET=1 -- else -- echo "PASS" | tee -a "${TEST_LOG}" -- fi --} -- --fn_rm_target() --{ -- fn_test 0 "rm -f $TEST_TARGET" --} -- --fn_recreate_target() --{ -- fn_rm_target -- fn_test 0 "truncate -s ${TEST_TARGET_SZ}G ${TEST_TARGET}" --} -- --util_max_blocks() --{ -- printf $((TEST_TARGET_SZ*1073741824/$1)) --} -- --# Tests start here --fn_recreate_target --fn_test 0 "$MKFS -p lock_nolock $TEST_TARGET" --fn_test 0 "$MKFS -p lock_dlm -t foo:bar $TEST_TARGET" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 255 "$MKFS -p badprotocol $TEST_TARGET" --fn_test 255 "$MKFS -p lock_nolock -r 31 $TEST_TARGET" --fn_test 255 "$MKFS -p lock_nolock -r 2049 $TEST_TARGET" --fn_test 0 "$MKFS -p lock_nolock -r 32 $TEST_TARGET" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 0 "$MKFS -p lock_nolock -r 2048 $TEST_TARGET" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 255 "$MKFS -p lock_nolock -b 512 $TEST_TARGET $(($(util_max_blocks 512)+1))" --fn_test 255 "$MKFS -p lock_nolock -b 4096 $TEST_TARGET $(($(util_max_blocks 4096)+1))" --fn_test 0 "$MKFS -p lock_nolock -b 512 $TEST_TARGET $(util_max_blocks 512)" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 0 "$MKFS -p lock_nolock -b 4096 $TEST_TARGET $(util_max_blocks 4096)" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 255 "$MKFS -p lock_nolock -J 7 $TEST_TARGET" --fn_test 255 "$MKFS -p lock_nolock -J 1025 $TEST_TARGET" --fn_test 0 "$MKFS -p lock_nolock -J 1024 $TEST_TARGET" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 0 "$MKFS -p lock_nolock -J 8 $TEST_TARGET" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 255 "$MKFS -p lock_nolock -c 0 $TEST_TARGET" --fn_test 255 "$MKFS -p lock_nolock -c 65 $TEST_TARGET" --fn_test 0 "$MKFS -p lock_nolock -c 1 $TEST_TARGET" --fn_test 0 "$FSCK $TEST_TARGET" --fn_test 0 "$MKFS -p lock_nolock -c 64 $TEST_TARGET" --fn_test 0 "$FSCK $TEST_TARGET" -- --# Tests end here -- --# Only remove the test file on success --[ "$TEST_RET" = "0" ] && fn_test 0 "rm -f $TEST_TARGET" --echo "Tool test output written to ${TEST_LOG}" --exit $TEST_RET diff --git a/SOURCES/bz1001583-1-fsck_gfs2_Allocate_enough_space_for_the_block_map.patch b/SOURCES/bz1001583-1-fsck_gfs2_Allocate_enough_space_for_the_block_map.patch deleted file mode 100644 index 4cb0e05..0000000 --- a/SOURCES/bz1001583-1-fsck_gfs2_Allocate_enough_space_for_the_block_map.patch +++ /dev/null @@ -1,45 +0,0 @@ -commit a8f380e9330ffa6d08b172041433ed46adc7b207 -Author: Andrew Price -Date: Mon Aug 19 15:23:57 2013 +0100 - - fsck.gfs2: Allocate enough space for the block map - - Building with gcc 4.8's address sanitizer and running the test suite - throws up an issue where the block map allocated in fsck.gfs2 is not - large enough when the required size is an odd number. For example, when - the number of blocks is 3, the mapsize (number of chars to allocate - memory for) would be (3 >> 1) which is too small as each block requires - 4 bits. This patch adds 1 to the mapsize, as suggested in an existing - comment, to ensure we have enough space in these situations. - - Note that this has (probably) never made fsck.gfs2 misbehave as it only - ever accessed 4 bits past the end of the block map and by chance that - memory was never being modified by anything else in the rare cases in - which it was used. - - Resolves: bz#1001583 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/fsck/util.c b/gfs2/fsck/util.c -index 408d89a..3e3050f 100644 ---- a/gfs2/fsck/util.c -+++ b/gfs2/fsck/util.c -@@ -534,15 +534,10 @@ static int gfs2_blockmap_create(struct gfs2_bmap *bmap, uint64_t size) - - /* Have to add 1 to BLOCKMAP_SIZE since it's 0-based and mallocs - * must be 1-based */ -- bmap->mapsize = BLOCKMAP_SIZE4(size); -+ bmap->mapsize = BLOCKMAP_SIZE4(size) + 1; - -- if (!(bmap->map = malloc(sizeof(char) * bmap->mapsize))) -+ if (!(bmap->map = calloc(bmap->mapsize, sizeof(char)))) - return -ENOMEM; -- if (!memset(bmap->map, 0, sizeof(char) * bmap->mapsize)) { -- free(bmap->map); -- bmap->map = NULL; -- return -ENOMEM; -- } - return 0; - } - diff --git a/SOURCES/bz1001583-2-libgfs2_Move_the_BLOCKMAP_macros_into_fsck_gfs2.patch b/SOURCES/bz1001583-2-libgfs2_Move_the_BLOCKMAP_macros_into_fsck_gfs2.patch deleted file mode 100644 index cd8c2ad..0000000 --- a/SOURCES/bz1001583-2-libgfs2_Move_the_BLOCKMAP_macros_into_fsck_gfs2.patch +++ /dev/null @@ -1,43 +0,0 @@ -commit f485b63bc2c0daa6b84d0c376fecb74c2d3784bd -Author: Andrew Price -Date: Mon Aug 19 16:21:28 2013 +0100 - - libgfs2: Move the BLOCKMAP_* macros into fsck.gfs2 - - These macros were only being used by fsck.gfs2 so they can safely be - moved into gfs2/fsck/util.h - - Resolves: bz#1001583 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/fsck/util.h b/gfs2/fsck/util.h -index 580acd8..276c726 100644 ---- a/gfs2/fsck/util.h -+++ b/gfs2/fsck/util.h -@@ -23,6 +23,10 @@ extern void dup_listent_delete(struct duptree *dt, struct inode_with_dups *id); - - extern const char *reftypes[ref_types + 1]; - -+#define BLOCKMAP_SIZE4(size) ((size) >> 1) -+#define BLOCKMAP_BYTE_OFFSET4(x) (((x) & 0x0000000000000001) << 2) -+#define BLOCKMAP_MASK4 (0xf) -+ - static inline uint8_t block_type(uint64_t bblock) - { - static unsigned char *byte; -diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h -index dd7420b..1548cf3 100644 ---- a/gfs2/libgfs2/libgfs2.h -+++ b/gfs2/libgfs2/libgfs2.h -@@ -68,10 +68,6 @@ __BEGIN_DECLS - - #endif /* __BYTE_ORDER == __LITTLE_ENDIAN */ - --#define BLOCKMAP_SIZE4(size) (size >> 1) --#define BLOCKMAP_BYTE_OFFSET4(x) ((x & 0x0000000000000001) << 2) --#define BLOCKMAP_MASK4 (0xf) -- - enum lgfs2_meta_type { - LGFS2_MT_GFS2_SB = 0, - LGFS2_MT_GFS_SB = 1, diff --git a/SOURCES/bz1003059-fsck_gfs2_Check_and_repair_per_node_contents_such_as_quota_changeX.patch b/SOURCES/bz1003059-fsck_gfs2_Check_and_repair_per_node_contents_such_as_quota_changeX.patch deleted file mode 100644 index a2cd6e6..0000000 --- a/SOURCES/bz1003059-fsck_gfs2_Check_and_repair_per_node_contents_such_as_quota_changeX.patch +++ /dev/null @@ -1,220 +0,0 @@ -commit e6c114baac5102d0ac8cc542565d56657593e3c5 -Author: Bob Peterson -Date: Tue Sep 3 11:21:00 2013 -0500 - - fsck.gfs2: Check and repair per_node contents such as quota_changeX - - This patch gives fsck.gfs2 the ability to check the system files that - are in the per_node directory: All the inum_rangeX, statfs_changeX - and quota_changeX files. If they're found to be corrupt, they are - deleted and rebuilt. - - rhbz#1003059 - -diff --git a/gfs2/fsck/pass2.c b/gfs2/fsck/pass2.c -index 727cc18..26f7d48 100644 ---- a/gfs2/fsck/pass2.c -+++ b/gfs2/fsck/pass2.c -@@ -1595,6 +1595,116 @@ struct metawalk_fxns pass2_fxns = { - .repair_leaf = pass2_repair_leaf, - }; - -+static int check_metalist_qc(struct gfs2_inode *ip, uint64_t block, -+ struct gfs2_buffer_head **bh, int h, -+ int *is_valid, int *was_duplicate, void *private) -+{ -+ *was_duplicate = 0; -+ *is_valid = 1; -+ *bh = bread(ip->i_sbd, block); -+ return meta_is_good; -+} -+ -+static int check_data_qc(struct gfs2_inode *ip, uint64_t metablock, -+ uint64_t block, void *private) -+{ -+ struct gfs2_buffer_head *bh; -+ -+ /* At this point, basic data block checks have already been done, -+ so we only need to make sure they're QC blocks. */ -+ if (!valid_block(ip->i_sbd, block)) -+ return -1; -+ -+ bh = bread(ip->i_sbd, block); -+ if (gfs2_check_meta(bh, GFS2_METATYPE_QC) != 0) { -+ log_crit(_("Error: quota_change block at %lld (0x%llx) is " -+ "the wrong metadata type.\n"), -+ (unsigned long long)block, (unsigned long long)block); -+ brelse(bh); -+ return -1; -+ } -+ brelse(bh); -+ return 0; -+} -+ -+struct metawalk_fxns quota_change_fxns = { -+ .check_metalist = check_metalist_qc, -+ .check_data = check_data_qc, -+}; -+ -+/* check_pernode_for - verify a file within the system per_node directory -+ * @x - index number X -+ * @per_node - pointer to the per_node inode -+ * @fn - system file name -+ * @filelen - the file length the system file needs to be -+ * @multiple - the file length must be a multiple (versus the exact value) -+ * @pass - a metawalk function for checking the data blocks (if any) -+ * @builder - a rebuild function for the file -+ * -+ * Returns: 0 if all went well, else error. */ -+static int check_pernode_for(int x, struct gfs2_inode *pernode, const char *fn, -+ unsigned long long filelen, int multiple, -+ struct metawalk_fxns *pass, -+ int builder(struct gfs2_inode *per_node, -+ unsigned int j)) -+{ -+ struct gfs2_inode *ip; -+ int error, valid_size = 1; -+ -+ log_debug(_("Checking system file %s\n"), fn); -+ error = gfs2_lookupi(pernode, fn, strlen(fn), &ip); -+ if (error) { -+ log_err(_("System file %s is missing.\n"), fn); -+ if (!query( _("Rebuild the system file? (y/n) "))) -+ return 0; -+ goto build_it; -+ } -+ if (!ip->i_di.di_size) -+ valid_size = 0; -+ else if (!multiple && ip->i_di.di_size != filelen) -+ valid_size = 0; -+ else if (multiple && (ip->i_di.di_size % filelen)) -+ valid_size = 0; -+ if (!valid_size) { -+ log_err(_("System file %s has an invalid size. Is %llu, " -+ "should be %llu.\n"), fn, ip->i_di.di_size, filelen); -+ if (!query( _("Rebuild the system file? (y/n) "))) -+ goto out_good; -+ fsck_inode_put(&ip); -+ goto build_it; -+ } -+ if (pass) { -+ error = check_metatree(ip, pass); -+ if (!error) -+ goto out_good; -+ log_err(_("System file %s has bad contents.\n"), fn); -+ if (!query( _("Delete and rebuild the system file? (y/n) "))) -+ goto out_good; -+ check_metatree(ip, &pass2_fxns_delete); -+ fsck_inode_put(&ip); -+ gfs2_dirent_del(pernode, fn, strlen(fn)); -+ goto build_it; -+ } -+out_good: -+ fsck_inode_put(&ip); -+ return 0; -+ -+build_it: -+ if (builder(pernode, x)) { -+ log_err(_("Error building %s\n"), fn); -+ return -1; -+ } -+ error = gfs2_lookupi(pernode, fn, strlen(fn), &ip); -+ if (error) { -+ log_err(_("Error rebuilding %s.\n"), fn); -+ return -1; -+ } -+ fsck_blockmap_set(ip, ip->i_di.di_num.no_addr, fn, gfs2_inode_file); -+ reprocess_inode(ip, fn); -+ log_err(_("System file %s rebuilt.\n"), fn); -+ goto out_good; -+} -+ - /* Check system directory inode */ - /* Should work for all system directories: root, master, jindex, per_node */ - static int check_system_dir(struct gfs2_inode *sysinode, const char *dirname, -@@ -1707,7 +1817,26 @@ static int check_system_dir(struct gfs2_inode *sysinode, const char *dirname, - sysinode->i_di.di_num.no_addr); - } - } -- return 0; -+ error = 0; -+ if (sysinode == sysinode->i_sbd->md.pinode) { -+ int j; -+ char fn[64]; -+ -+ /* Make sure all the per_node files are there, and valid */ -+ for (j = 0; j < sysinode->i_sbd->md.journals; j++) { -+ sprintf(fn, "inum_range%d", j); -+ error += check_pernode_for(j, sysinode, fn, 16, 0, -+ NULL, build_inum_range); -+ sprintf(fn, "statfs_change%d", j); -+ error += check_pernode_for(j, sysinode, fn, 24, 0, -+ NULL, build_statfs_change); -+ sprintf(fn, "quota_change%d", j); -+ error += check_pernode_for(j, sysinode, fn, 1048576, 1, -+ "a_change_fxns, -+ build_quota_change); -+ } -+ } -+ return error; - } - - /** -diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h -index 1548cf3..f864a08 100644 ---- a/gfs2/libgfs2/libgfs2.h -+++ b/gfs2/libgfs2/libgfs2.h -@@ -770,6 +770,10 @@ extern int do_init_statfs(struct gfs2_sbd *sdp); - extern int gfs2_check_meta(struct gfs2_buffer_head *bh, int type); - extern unsigned lgfs2_bm_scan(struct rgrp_tree *rgd, unsigned idx, - uint64_t *buf, uint8_t state); -+extern int build_inum_range(struct gfs2_inode *per_node, unsigned int j); -+extern int build_statfs_change(struct gfs2_inode *per_node, unsigned int j); -+extern int build_quota_change(struct gfs2_inode *per_node, unsigned int j); -+ - /* super.c */ - extern int check_sb(struct gfs2_sb *sb); - extern int read_sb(struct gfs2_sbd *sdp); -diff --git a/gfs2/libgfs2/structures.c b/gfs2/libgfs2/structures.c -index 2a8c6f7..e888f1e 100644 ---- a/gfs2/libgfs2/structures.c -+++ b/gfs2/libgfs2/structures.c -@@ -180,7 +180,7 @@ int build_jindex(struct gfs2_sbd *sdp) - return 0; - } - --static int build_inum_range(struct gfs2_inode *per_node, unsigned int j) -+int build_inum_range(struct gfs2_inode *per_node, unsigned int j) - { - struct gfs2_sbd *sdp = per_node->i_sbd; - char name[256]; -@@ -204,7 +204,7 @@ static int build_inum_range(struct gfs2_inode *per_node, unsigned int j) - return 0; - } - --static int build_statfs_change(struct gfs2_inode *per_node, unsigned int j) -+int build_statfs_change(struct gfs2_inode *per_node, unsigned int j) - { - struct gfs2_sbd *sdp = per_node->i_sbd; - char name[256]; -@@ -228,7 +228,7 @@ static int build_statfs_change(struct gfs2_inode *per_node, unsigned int j) - return 0; - } - --static int build_quota_change(struct gfs2_inode *per_node, unsigned int j) -+int build_quota_change(struct gfs2_inode *per_node, unsigned int j) - { - struct gfs2_sbd *sdp = per_node->i_sbd; - struct gfs2_meta_header mh; -diff --git a/gfs2/libgfs2/super.c b/gfs2/libgfs2/super.c -index eb97c40..f87734a 100644 ---- a/gfs2/libgfs2/super.c -+++ b/gfs2/libgfs2/super.c -@@ -119,6 +119,7 @@ int read_sb(struct gfs2_sbd *sdp) - sdp->sb_addr = GFS2_SB_ADDR * GFS2_BASIC_BLOCK / sdp->bsize; - sdp->sd_blocks_per_bitmap = (sdp->sd_sb.sb_bsize - sizeof(struct gfs2_meta_header)) - * GFS2_NBBY; -+ sdp->qcsize = GFS2_DEFAULT_QCSIZE; - - return 0; - } diff --git a/SOURCES/bz1028388-1-libgfs2_Add_sd_heightsize_bounds_checking_in_read_sb.patch b/SOURCES/bz1028388-1-libgfs2_Add_sd_heightsize_bounds_checking_in_read_sb.patch deleted file mode 100644 index 176f76a..0000000 --- a/SOURCES/bz1028388-1-libgfs2_Add_sd_heightsize_bounds_checking_in_read_sb.patch +++ /dev/null @@ -1,78 +0,0 @@ -commit 7d57e6d4aff2a0b356c92db1706b346329fabc45 -Author: Andrew Price -Date: Mon Oct 28 16:56:56 2013 +0000 - - libgfs2: Add sd_heightsize bounds checking in read_sb - - read_sb wasn't checking that x was less than the size of sd_heightsize - when looping over it. This patch adds a check for that. This resolves a - segfault in all tools which use read_sb, when the sb_bsize has been - zeroed in the superblock. - - A test case has been added for this scenario in tests/fsck.at - - Resolves: bz#1028388 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/libgfs2/super.c b/gfs2/libgfs2/super.c -index f87734a..8ffd144 100644 ---- a/gfs2/libgfs2/super.c -+++ b/gfs2/libgfs2/super.c -@@ -88,7 +88,7 @@ int read_sb(struct gfs2_sbd *sdp) - sdp->sd_hash_ptrs = sdp->sd_hash_bsize / sizeof(uint64_t); - sdp->sd_heightsize[0] = sdp->sd_sb.sb_bsize - sizeof(struct gfs2_dinode); - sdp->sd_heightsize[1] = sdp->sd_sb.sb_bsize * sdp->sd_diptrs; -- for (x = 2; ; x++){ -+ for (x = 2; x <= GFS2_MAX_META_HEIGHT; x++){ - space = sdp->sd_heightsize[x - 1] * sdp->sd_inptrs; - /* FIXME: Do we really need this first check?? */ - if (space / sdp->sd_inptrs != sdp->sd_heightsize[x - 1] || -diff --git a/tests/Makefile.am b/tests/Makefile.am -index 3336304..616a44e 100644 ---- a/tests/Makefile.am -+++ b/tests/Makefile.am -@@ -40,6 +40,7 @@ $(srcdir)/package.m4: $(top_srcdir)/configure.ac - TESTSUITE_AT = \ - testsuite.at \ - mkfs.at \ -+ fsck.at \ - libgfs2.at - - TESTSUITE = $(srcdir)/testsuite -diff --git a/tests/fsck.at b/tests/fsck.at -new file mode 100644 -index 0000000..34c5bd5 ---- /dev/null -+++ b/tests/fsck.at -@@ -0,0 +1,8 @@ -+AT_TESTED([fsck.gfs2]) -+AT_BANNER([fsck.gfs2 tests]) -+ -+AT_SETUP([Zeroed block size]) -+GFS_LANG_CHECK( -+ [mkfs.gfs2 -O -p lock_nolock $GFS_TGT], -+ [set sb { sb_bsize: 0 }]) -+AT_CLEANUP -diff --git a/tests/testsuite.at b/tests/testsuite.at -index 2c74985..fc90879 100644 ---- a/tests/testsuite.at -+++ b/tests/testsuite.at -@@ -9,8 +9,17 @@ m4_define([GFS_FSCK_CHECK], - AT_CHECK($1, 0, [ignore], [ignore]) - AT_CHECK([fsck.gfs2 -n $GFS_TGT], 0, [ignore], [ignore])]) - -+# Regenerate, mkfs, modify fs with gfs2l, fsck -+m4_define([GFS_LANG_CHECK], -+[GFS_TGT_REGEN -+AT_CHECK($1, 0, [ignore], [ignore]) -+AT_CHECK([echo "$2" | gfs2l ${GFS_TGT}], 0, [ignore], [ignore]) -+AT_CHECK([fsck.gfs2 -y $GFS_TGT], 1, [ignore], [ignore]) -+AT_CHECK([fsck.gfs2 -n $GFS_TGT], 0, [ignore], [ignore])]) -+ - AT_INIT([]) - AT_COLOR_TESTS - - m4_include([mkfs.at]) -+m4_include([fsck.at]) - m4_include([libgfs2.at]) diff --git a/SOURCES/bz1028388-2-fsck_gfs2_Fix_block_size_validation.patch b/SOURCES/bz1028388-2-fsck_gfs2_Fix_block_size_validation.patch deleted file mode 100644 index 5954048..0000000 --- a/SOURCES/bz1028388-2-fsck_gfs2_Fix_block_size_validation.patch +++ /dev/null @@ -1,75 +0,0 @@ -commit 32d72eb22fdf00c759df50e5fce49292d15be5ed -Author: Andrew Price -Date: Fri Nov 8 16:59:44 2013 +0000 - - fsck.gfs2: Fix block size validation - - The previous patch had an off-by-one error when looping over - sdp->sd_heightsize. This fixes that and adds an explicit sanity check - for sb_bsize. Some new tests are added to cover both valid and invalid - block size cases. - - Resolves: bz#1028388 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/libgfs2/super.c b/gfs2/libgfs2/super.c -index 8ffd144..d074236 100644 ---- a/gfs2/libgfs2/super.c -+++ b/gfs2/libgfs2/super.c -@@ -67,6 +67,9 @@ int read_sb(struct gfs2_sbd *sdp) - sdp->gfs1 = 1; - sdp->sd_fsb2bb_shift = sdp->sd_sb.sb_bsize_shift - GFS2_BASIC_BLOCK_SHIFT; - sdp->bsize = sdp->sd_sb.sb_bsize; -+ if (sdp->bsize < 512 || sdp->bsize != (sdp->bsize & -sdp->bsize)) { -+ return -1; -+ } - if (sdp->gfs1) { - sdp->sd_diptrs = (sdp->sd_sb.sb_bsize - - sizeof(struct gfs_dinode)) / -@@ -88,7 +91,7 @@ int read_sb(struct gfs2_sbd *sdp) - sdp->sd_hash_ptrs = sdp->sd_hash_bsize / sizeof(uint64_t); - sdp->sd_heightsize[0] = sdp->sd_sb.sb_bsize - sizeof(struct gfs2_dinode); - sdp->sd_heightsize[1] = sdp->sd_sb.sb_bsize * sdp->sd_diptrs; -- for (x = 2; x <= GFS2_MAX_META_HEIGHT; x++){ -+ for (x = 2; x < GFS2_MAX_META_HEIGHT; x++){ - space = sdp->sd_heightsize[x - 1] * sdp->sd_inptrs; - /* FIXME: Do we really need this first check?? */ - if (space / sdp->sd_inptrs != sdp->sd_heightsize[x - 1] || -diff --git a/tests/fsck.at b/tests/fsck.at -index 34c5bd5..d7a8357 100644 ---- a/tests/fsck.at -+++ b/tests/fsck.at -@@ -1,8 +1,10 @@ - AT_TESTED([fsck.gfs2]) - AT_BANNER([fsck.gfs2 tests]) - --AT_SETUP([Zeroed block size]) --GFS_LANG_CHECK( -- [mkfs.gfs2 -O -p lock_nolock $GFS_TGT], -- [set sb { sb_bsize: 0 }]) -+AT_SETUP([Fix invalid block sizes]) -+GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 0 }]) -+GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 1 }]) -+GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 513 }]) -+GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 4095 }]) -+GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 4097 }]) - AT_CLEANUP -diff --git a/tests/mkfs.at b/tests/mkfs.at -index aff6a0d..a3973af 100644 ---- a/tests/mkfs.at -+++ b/tests/mkfs.at -@@ -31,6 +31,13 @@ GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT]) - GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_dlm -t foo:bar $GFS_TGT]) - AT_CLEANUP - -+AT_SETUP([Valid block sizes 512-4096]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 512 $GFS_TGT]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 1024 $GFS_TGT]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 2048 $GFS_TGT]) -+GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 4096 $GFS_TGT]) -+AT_CLEANUP -+ - AT_SETUP([Max. blocks, min. block size]) - GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 512 $GFS_TGT $(gfs_max_blocks 512)]) - AT_CLEANUP diff --git a/SOURCES/bz1028388-3-gfs2l_Build_with_D_FILE_OFFSET_BITS_64.patch b/SOURCES/bz1028388-3-gfs2l_Build_with_D_FILE_OFFSET_BITS_64.patch deleted file mode 100644 index 8758ee8..0000000 --- a/SOURCES/bz1028388-3-gfs2l_Build_with_D_FILE_OFFSET_BITS_64.patch +++ /dev/null @@ -1,27 +0,0 @@ -commit 5e4fe097ac39ceb8e6768da98cd1e84ff99b8176 -Author: Andrew Price -Date: Tue Nov 12 16:38:34 2013 +0000 - - gfs2l: Build with -D_FILE_OFFSET_BITS=64 - - The latest test cases were failing on 32-bit architectures as gfs2l - wasn't being built with large file support. This adds - -D_FILE_OFFSET_BITS=64 to fix the tests. - - Resolves: bz#1028388 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/libgfs2/Makefile.am b/gfs2/libgfs2/Makefile.am -index b57f6d9..c5cb288 100644 ---- a/gfs2/libgfs2/Makefile.am -+++ b/gfs2/libgfs2/Makefile.am -@@ -22,7 +22,7 @@ libgfs2_la_CPPFLAGS = -D_FILE_OFFSET_BITS=64 \ - -I$(top_srcdir)/gfs2/include - - gfs2l_SOURCES = gfs2l.c --gfs2l_CPPFLAGS = -I$(top_srcdir)/gfs2/include -+gfs2l_CPPFLAGS = -I$(top_srcdir)/gfs2/include -D_FILE_OFFSET_BITS=64 - gfs2l_LDADD = libgfs2.la - - # Autotools can't handle header files output by flex so we have to generate it manually diff --git a/SOURCES/bz1059443-1-gfs2_edit_Convert_fssize_to_bytes_before_reporting_fs_size.patch b/SOURCES/bz1059443-1-gfs2_edit_Convert_fssize_to_bytes_before_reporting_fs_size.patch deleted file mode 100644 index 97b4b00..0000000 --- a/SOURCES/bz1059443-1-gfs2_edit_Convert_fssize_to_bytes_before_reporting_fs_size.patch +++ /dev/null @@ -1,70 +0,0 @@ -commit 979c86c6e76aa6a879c2a163f8d20653a4a759da -Author: Andrew Price -Date: Fri Jan 31 06:30:00 2014 -0600 - - gfs2_edit: Convert fssize to bytes before reporting fs size - - gfs2_edit savemeta wasn't converting sbd.fssize to bytes before converting it - to a human-friendly number. This patch adds that multiplier along with a sanity - test for savemeta/restoremeta. - - Resolves: rhbz#1059443 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/edit/savemeta.c b/gfs2/edit/savemeta.c -index 986fdbe..b4c85d6 100644 ---- a/gfs2/edit/savemeta.c -+++ b/gfs2/edit/savemeta.c -@@ -736,7 +736,7 @@ void savemeta(char *out_fn, int saveoption, int gziplevel) - gfs1_ri_update(&sbd, 0, &rgcount, 0); - else - ri_update(&sbd, 0, &rgcount, &sane); -- printf("Done. File system size: %s\n\n", anthropomorphize(sbd.fssize)); -+ printf("Done. File system size: %s\n\n", anthropomorphize(sbd.fssize * sbd.bsize)); - fflush(stdout); - - get_journal_inode_blocks(); -diff --git a/tests/Makefile.am b/tests/Makefile.am -index 616a44e..5f02d3a 100644 ---- a/tests/Makefile.am -+++ b/tests/Makefile.am -@@ -41,6 +41,7 @@ TESTSUITE_AT = \ - testsuite.at \ - mkfs.at \ - fsck.at \ -+ edit.at \ - libgfs2.at - - TESTSUITE = $(srcdir)/testsuite -diff --git a/tests/edit.at b/tests/edit.at -new file mode 100644 -index 0000000..014d118 ---- /dev/null -+++ b/tests/edit.at -@@ -0,0 +1,15 @@ -+AT_TESTED([gfs2_edit]) -+AT_BANNER([gfs2_edit tests]) -+ -+AT_SETUP([Savemeta/restoremeta, defaults]) -+GFS_TGT_REGEN -+AT_CHECK([$GFS_MKFS -p lock_nolock $GFS_TGT $(($(gfs_max_blocks 4096)/2))], 0, [ignore], [ignore]) -+AT_CHECK([gfs2_edit savemeta $GFS_TGT test.meta > savemeta.log], 0, [ignore], [ignore]) -+AT_CHECK([head -2 savemeta.log], 0, [There are 2621440 blocks of 4096 bytes in the destination device. -+Reading resource groups...Done. File system size: 4.1023G -+], [ignore]) -+GFS_TGT_REGEN -+AT_CHECK([gfs2_edit restoremeta test.meta $GFS_TGT], 0, [ignore], [ignore]) -+AT_CHECK([fsck.gfs2 -n $GFS_TGT], 0, [ignore], [ignore]) -+ -+AT_CLEANUP -diff --git a/tests/testsuite.at b/tests/testsuite.at -index fc90879..fe781a7 100644 ---- a/tests/testsuite.at -+++ b/tests/testsuite.at -@@ -22,4 +22,5 @@ AT_COLOR_TESTS - - m4_include([mkfs.at]) - m4_include([fsck.at]) -+m4_include([edit.at]) - m4_include([libgfs2.at]) diff --git a/SOURCES/bz1059443-2-mkfs_gfs2_tests_Enable_debug_output.patch b/SOURCES/bz1059443-2-mkfs_gfs2_tests_Enable_debug_output.patch deleted file mode 100644 index a0e7f5b..0000000 --- a/SOURCES/bz1059443-2-mkfs_gfs2_tests_Enable_debug_output.patch +++ /dev/null @@ -1,122 +0,0 @@ -commit 9a070d60d70937da51f1430c6626327c971dec33 -Author: Andrew Price -Date: Wed Jan 22 18:46:53 2014 +0000 - - mkfs.gfs2 tests: Enable debug output - - Enable debug output of mkfs.gfs2 tests and define the base options as a - shell variable to make them easier to maintain. - - Resolves: rhbz#1059443 - - Signed-off-by: Andrew Price - -diff --git a/tests/atlocal.in b/tests/atlocal.in -index 660c87a..b021b13 100644 ---- a/tests/atlocal.in -+++ b/tests/atlocal.in -@@ -1,5 +1,6 @@ - GFS_TGT="$abs_builddir/testvol" - GFS_TGT_SZ=10 -+GFS_MKFS="mkfs.gfs2 -O -D" - - gfs_max_blocks() - { -diff --git a/tests/mkfs.at b/tests/mkfs.at -index a3973af..2616109 100644 ---- a/tests/mkfs.at -+++ b/tests/mkfs.at -@@ -2,70 +2,70 @@ AT_TESTED([mkfs.gfs2]) - AT_BANNER([mkfs.gfs2 tests]) - - AT_SETUP([Locking protocol validation]) --AT_CHECK([mkfs.gfs2 -O -p badprotocol $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p badprotocol $GFS_TGT], 255, [ignore], [ignore]) - AT_CLEANUP - - AT_SETUP([Resource group size validation]) --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -r 31 $GFS_TGT], 255, [ignore], [ignore]) --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -r 2049 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -r 31 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -r 2049 $GFS_TGT], 255, [ignore], [ignore]) - AT_CLEANUP - - AT_SETUP([Journal size validation]) --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -J 7 $GFS_TGT], 255, [ignore], [ignore]) --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -J 1025 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -J 7 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -J 1025 $GFS_TGT], 255, [ignore], [ignore]) - AT_CLEANUP - - AT_SETUP([Block count validation]) - GFS_TGT_REGEN --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -b 512 $GFS_TGT $(($(gfs_max_blocks 512)+1))], 255, [ignore], [ignore]) --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -b 4096 $GFS_TGT $(($(gfs_max_blocks 4096)+1))], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -b 512 $GFS_TGT $(($(gfs_max_blocks 512)+1))], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -b 4096 $GFS_TGT $(($(gfs_max_blocks 4096)+1))], 255, [ignore], [ignore]) - AT_CLEANUP - - AT_SETUP([Quota change file size validation]) --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -c 0 $GFS_TGT], 255, [ignore], [ignore]) --AT_CHECK([mkfs.gfs2 -O -p lock_nolock -c 65 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -c 0 $GFS_TGT], 255, [ignore], [ignore]) -+AT_CHECK([$GFS_MKFS -p lock_nolock -c 65 $GFS_TGT], 255, [ignore], [ignore]) - AT_CLEANUP - - AT_SETUP([Locking protocols]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_dlm -t foo:bar $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_dlm -t foo:bar $GFS_TGT]) - AT_CLEANUP - - AT_SETUP([Valid block sizes 512-4096]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 512 $GFS_TGT]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 1024 $GFS_TGT]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 2048 $GFS_TGT]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 4096 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -b 512 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -b 1024 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -b 2048 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -b 4096 $GFS_TGT]) - AT_CLEANUP - - AT_SETUP([Max. blocks, min. block size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 512 $GFS_TGT $(gfs_max_blocks 512)]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -b 512 $GFS_TGT $(gfs_max_blocks 512)]) - AT_CLEANUP - - AT_SETUP([Max. blocks, max. block size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -b 4096 $GFS_TGT $(util_max_blocks 4096)]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -b 4096 $GFS_TGT $(util_max_blocks 4096)]) - AT_CLEANUP - - AT_SETUP([Max. resource group size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -r 2048 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -r 2048 $GFS_TGT]) - AT_CLEANUP - - AT_SETUP([Min. resource group size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -r 32 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -r 32 $GFS_TGT]) - AT_CLEANUP - - AT_SETUP([Max. journal size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -J 1024 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -J 1024 $GFS_TGT]) - AT_CLEANUP - - AT_SETUP([Min. journal size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -J 8 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -J 8 $GFS_TGT]) - AT_CLEANUP - - AT_SETUP([Max. quota change file size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -c 64 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -c 64 $GFS_TGT]) - AT_CLEANUP - - AT_SETUP([Min. quota change file size]) --GFS_FSCK_CHECK([mkfs.gfs2 -O -p lock_nolock -c 1 $GFS_TGT]) -+GFS_FSCK_CHECK([$GFS_MKFS -p lock_nolock -c 1 $GFS_TGT]) - AT_CLEANUP diff --git a/SOURCES/bz1063842-1-libgfs2_Superblock_building_and_writing_improvements.patch b/SOURCES/bz1063842-1-libgfs2_Superblock_building_and_writing_improvements.patch deleted file mode 100644 index a3691df..0000000 --- a/SOURCES/bz1063842-1-libgfs2_Superblock_building_and_writing_improvements.patch +++ /dev/null @@ -1,500 +0,0 @@ -commit 37cf0257bf6298df38ca74ee8577bac5a40e6598 -Author: Andrew Price -Date: Thu Feb 6 04:25:27 2014 +0000 - - libgfs2: Superblock building and writing improvements - - build_sb was creating the sb, setting its fields from an sdp and then - writing it, and also zeroing the gap before the sb on the device in a - block-by-block way using buffer_heads. - - This patch splits the build_sb function into lgfs2_sb_init and - lgfs2_sb_write which operate on gfs2_sb structures instead of gfs2_sbds. - lgfs2_sb_write now uses pwritev to zero the initial blocks and write the - sb to an fd. - - get_random_bytes has been moved into structures.c and made static as - only lgfs2_sb_init now uses it. - - Resolves: rhbz#1063842 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/convert/gfs2_convert.c b/gfs2/convert/gfs2_convert.c -index 719ba9c..ce056a7 100644 ---- a/gfs2/convert/gfs2_convert.c -+++ b/gfs2/convert/gfs2_convert.c -@@ -2374,7 +2374,8 @@ int main(int argc, char **argv) - bh = bread(&sb2, sb2.sb_addr); - sb2.sd_sb.sb_fs_format = GFS2_FORMAT_FS; - sb2.sd_sb.sb_multihost_format = GFS2_FORMAT_MULTI; -- gfs2_sb_out(&sb2.sd_sb, bh); -+ gfs2_sb_out(&sb2.sd_sb, bh->b_data); -+ bmodified(bh); - brelse(bh); - - error = fsync(sb2.device_fd); -diff --git a/gfs2/edit/hexedit.c b/gfs2/edit/hexedit.c -index f0d9789..36f6600 100644 ---- a/gfs2/edit/hexedit.c -+++ b/gfs2/edit/hexedit.c -@@ -2132,7 +2132,8 @@ static void process_field(const char *field, const char *nstr) - gfs2_sb_assigns(&lsb, field, nstr); - else - gfs2_sb_assignval(&lsb, field, newval); -- gfs2_sb_out(&lsb, rbh); -+ gfs2_sb_out(&lsb, rbh->b_data); -+ bmodified(rbh); - if (!termlines) - gfs2_sb_printval(&lsb, field); - } else { -diff --git a/gfs2/fsck/initialize.c b/gfs2/fsck/initialize.c -index 5758607..0f33aa6 100644 ---- a/gfs2/fsck/initialize.c -+++ b/gfs2/fsck/initialize.c -@@ -60,7 +60,7 @@ static int block_mounters(struct gfs2_sbd *sdp, int block_em) - } - } - -- if (write_sb(sdp)) { -+ if (lgfs2_sb_write(&sdp->sd_sb, sdp->device_fd, sdp->bsize)) { - stack; - return -1; - } -@@ -1130,7 +1130,6 @@ static int sb_repair(struct gfs2_sbd *sdp) - { - uint64_t half; - uint32_t known_bsize = 0; -- unsigned char uuid[16]; - int error = 0; - - memset(&fix_md, 0, sizeof(fix_md)); -@@ -1205,9 +1204,8 @@ static int sb_repair(struct gfs2_sbd *sdp) - } - } - /* Step 3 - Rebuild the lock protocol and file system table name */ -- strcpy(sdp->lockproto, GFS2_DEFAULT_LOCKPROTO); -- strcpy(sdp->locktable, "unknown"); - if (query(_("Okay to fix the GFS2 superblock? (y/n)"))) { -+ struct gfs2_sb sb; - log_info(_("Found system master directory at: 0x%llx\n"), - sdp->sd_sb.sb_master_dir.no_addr); - sdp->master_dir = lgfs2_inode_read(sdp, -@@ -1226,8 +1224,12 @@ static int sb_repair(struct gfs2_sbd *sdp) - log_crit(_("Error reading root inode: %s\n"), strerror(errno)); - return -1; - } -- get_random_bytes(uuid, sizeof(uuid)); -- build_sb(sdp, uuid); -+ lgfs2_sb_init(&sb, sdp->bsize); -+ strcpy(sb.sb_lockproto, GFS2_DEFAULT_LOCKPROTO); -+ strcpy(sb.sb_locktable, "unknown"); -+ sb.sb_master_dir = sdp->master_dir->i_di.di_num; -+ sb.sb_root_dir = sdp->md.rooti->i_di.di_num; -+ lgfs2_sb_write(&sb, sdp->device_fd, sdp->bsize); - inode_put(&sdp->md.rooti); - inode_put(&sdp->master_dir); - sb_fixed = 1; -diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h -index e785017..6710e72 100644 ---- a/gfs2/libgfs2/libgfs2.h -+++ b/gfs2/libgfs2/libgfs2.h -@@ -724,7 +724,6 @@ extern int mount_gfs2_meta(struct gfs2_sbd *sdp); - extern void cleanup_metafs(struct gfs2_sbd *sdp); - extern int set_sysfs(const char *fsname, const char *filename, const char *val); - extern int is_fsname(char *name); --extern void get_random_bytes(void *buf, int nbytes); - - /* recovery.c */ - extern void gfs2_replay_incr_blk(struct gfs2_inode *ip, unsigned int *blk); -@@ -758,7 +757,8 @@ static inline unsigned int rgrp_size(struct rgrp_tree *rgrp) - - /* structures.c */ - extern int build_master(struct gfs2_sbd *sdp); --extern void build_sb(struct gfs2_sbd *sdp, const unsigned char *uuid); -+extern void lgfs2_sb_init(struct gfs2_sb *sb, unsigned bsize); -+extern int lgfs2_sb_write(const struct gfs2_sb *sb, int fd, const unsigned bsize); - extern int build_journal(struct gfs2_sbd *sdp, int j, - struct gfs2_inode *jindex); - extern int build_jindex(struct gfs2_sbd *sdp); -@@ -794,14 +794,14 @@ extern void print_it(const char *label, const char *fmt, const char *fmt2, ...) - /* Translation functions */ - - extern void gfs2_inum_in(struct gfs2_inum *no, char *buf); --extern void gfs2_inum_out(struct gfs2_inum *no, char *buf); -+extern void gfs2_inum_out(const struct gfs2_inum *no, char *buf); - extern void gfs2_meta_header_in(struct gfs2_meta_header *mh, - struct gfs2_buffer_head *bh); - extern void gfs2_meta_header_out(const struct gfs2_meta_header *mh, char *buf); - extern void gfs2_meta_header_out_bh(const struct gfs2_meta_header *mh, - struct gfs2_buffer_head *bh); - extern void gfs2_sb_in(struct gfs2_sb *sb, struct gfs2_buffer_head *bh); --extern void gfs2_sb_out(struct gfs2_sb *sb, struct gfs2_buffer_head *bh); -+extern void gfs2_sb_out(const struct gfs2_sb *sb, char *buf); - extern void gfs2_rindex_in(struct gfs2_rindex *ri, char *buf); - extern void gfs2_rindex_out(struct gfs2_rindex *ri, char *buf); - extern void gfs2_rgrp_in(struct gfs2_rgrp *rg, struct gfs2_buffer_head *bh); -diff --git a/gfs2/libgfs2/misc.c b/gfs2/libgfs2/misc.c -index c4ed722..d707687 100644 ---- a/gfs2/libgfs2/misc.c -+++ b/gfs2/libgfs2/misc.c -@@ -17,7 +17,6 @@ - #include - #include - #include --#include - #include - - #include "libgfs2.h" -@@ -304,47 +303,3 @@ int set_sysfs(const char *fsname, const char *filename, const char *val) - close(fd); - return 0; - } -- --/* -- * get_random_bytes - Generate a series of random bytes using /dev/urandom. -- * -- * Modified from original code in gen_uuid.c in e2fsprogs/lib -- */ --void get_random_bytes(void *buf, int nbytes) --{ -- int i, n = nbytes, fd; -- int lose_counter = 0; -- unsigned char *cp = (unsigned char *) buf; -- struct timeval tv; -- -- gettimeofday(&tv, 0); -- fd = open("/dev/urandom", O_RDONLY | O_CLOEXEC); -- srand((getpid() << 16) ^ getuid() ^ tv.tv_sec ^ tv.tv_usec); -- /* Crank the random number generator a few times */ -- gettimeofday(&tv, 0); -- for (i = (tv.tv_sec ^ tv.tv_usec) & 0x1F; i > 0; i--) -- rand(); -- if (fd >= 0) { -- while (n > 0) { -- i = read(fd, cp, n); -- if (i <= 0) { -- if (lose_counter++ > 16) -- break; -- continue; -- } -- n -= i; -- cp += i; -- lose_counter = 0; -- } -- close(fd); -- } -- -- /* -- * We do this all the time, but this is the only source of -- * randomness if /dev/random/urandom is out to lunch. -- */ -- for (cp = buf, i = 0; i < nbytes; i++) -- *cp++ ^= (rand() >> 7) & 0xFF; -- -- return; --} -diff --git a/gfs2/libgfs2/ondisk.c b/gfs2/libgfs2/ondisk.c -index 4baacc7..43618bc 100644 ---- a/gfs2/libgfs2/ondisk.c -+++ b/gfs2/libgfs2/ondisk.c -@@ -48,7 +48,7 @@ void gfs2_inum_in(struct gfs2_inum *no, char *buf) - CPIN_64(no, str, no_addr); - } - --void gfs2_inum_out(struct gfs2_inum *no, char *buf) -+void gfs2_inum_out(const struct gfs2_inum *no, char *buf) - { - struct gfs2_inum *str = (struct gfs2_inum *)buf; - -@@ -124,11 +124,11 @@ void gfs2_sb_in(struct gfs2_sb *sb, struct gfs2_buffer_head *bh) - #endif - } - --void gfs2_sb_out(struct gfs2_sb *sb, struct gfs2_buffer_head *bh) -+void gfs2_sb_out(const struct gfs2_sb *sb, char *buf) - { -- struct gfs2_sb *str = (struct gfs2_sb *)bh->b_data; -+ struct gfs2_sb *str = (struct gfs2_sb *)buf; - -- gfs2_meta_header_out_bh(&sb->sb_header, bh); -+ gfs2_meta_header_out(&sb->sb_header, buf); - - CPOUT_32(sb, str, sb_fs_format); - CPOUT_32(sb, str, sb_multihost_format); -@@ -144,7 +144,6 @@ void gfs2_sb_out(struct gfs2_sb *sb, struct gfs2_buffer_head *bh) - #ifdef GFS2_HAS_UUID - memcpy(str->sb_uuid, sb->sb_uuid, 16); - #endif -- bmodified(bh); - } - - const char *str_uuid(const unsigned char *uuid) -diff --git a/gfs2/libgfs2/structures.c b/gfs2/libgfs2/structures.c -index e888f1e..2c1939a 100644 ---- a/gfs2/libgfs2/structures.c -+++ b/gfs2/libgfs2/structures.c -@@ -11,6 +11,7 @@ - #include - #include - #include -+#include - - #include "libgfs2.h" - -@@ -41,43 +42,102 @@ int build_master(struct gfs2_sbd *sdp) - return 0; - } - --void build_sb(struct gfs2_sbd *sdp, const unsigned char *uuid) -+#ifdef GFS2_HAS_UUID -+/** -+ * Generate a series of random bytes using /dev/urandom. -+ * Modified from original code in gen_uuid.c in e2fsprogs/lib -+ */ -+static void get_random_bytes(void *buf, int nbytes) - { -- unsigned int x; -- struct gfs2_buffer_head *bh; -- struct gfs2_sb sb; -- -- /* Zero out the beginning of the device up to the superblock */ -- for (x = 0; x < sdp->sb_addr; x++) { -- bh = bget(sdp, x); -- memset(bh->b_data, 0, sdp->bsize); -- bmodified(bh); -- brelse(bh); -+ int i, n = nbytes, fd; -+ int lose_counter = 0; -+ unsigned char *cp = (unsigned char *) buf; -+ struct timeval tv; -+ -+ gettimeofday(&tv, 0); -+ fd = open("/dev/urandom", O_RDONLY | O_CLOEXEC); -+ srand((getpid() << 16) ^ getuid() ^ tv.tv_sec ^ tv.tv_usec); -+ /* Crank the random number generator a few times */ -+ gettimeofday(&tv, 0); -+ for (i = (tv.tv_sec ^ tv.tv_usec) & 0x1F; i > 0; i--) -+ rand(); -+ if (fd >= 0) { -+ while (n > 0) { -+ i = read(fd, cp, n); -+ if (i <= 0) { -+ if (lose_counter++ > 16) -+ break; -+ continue; -+ } -+ n -= i; -+ cp += i; -+ lose_counter = 0; -+ } -+ close(fd); - } - -- memset(&sb, 0, sizeof(struct gfs2_sb)); -- sb.sb_header.mh_magic = GFS2_MAGIC; -- sb.sb_header.mh_type = GFS2_METATYPE_SB; -- sb.sb_header.mh_format = GFS2_FORMAT_SB; -- sb.sb_fs_format = GFS2_FORMAT_FS; -- sb.sb_multihost_format = GFS2_FORMAT_MULTI; -- sb.sb_bsize = sdp->bsize; -- sb.sb_bsize_shift = ffs(sdp->bsize) - 1; -- sb.sb_master_dir = sdp->master_dir->i_di.di_num; -- sb.sb_root_dir = sdp->md.rooti->i_di.di_num; -- strcpy(sb.sb_lockproto, sdp->lockproto); -- strcpy(sb.sb_locktable, sdp->locktable); -+ /* -+ * We do this all the time, but this is the only source of -+ * randomness if /dev/random/urandom is out to lunch. -+ */ -+ for (cp = buf, i = 0; i < nbytes; i++) -+ *cp++ ^= (rand() >> 7) & 0xFF; -+ -+ return; -+} -+#endif -+ -+/** -+ * Initialise a gfs2_sb structure with sensible defaults. -+ */ -+void lgfs2_sb_init(struct gfs2_sb *sb, unsigned bsize) -+{ -+ memset(sb, 0, sizeof(struct gfs2_sb)); -+ sb->sb_header.mh_magic = GFS2_MAGIC; -+ sb->sb_header.mh_type = GFS2_METATYPE_SB; -+ sb->sb_header.mh_format = GFS2_FORMAT_SB; -+ sb->sb_fs_format = GFS2_FORMAT_FS; -+ sb->sb_multihost_format = GFS2_FORMAT_MULTI; -+ sb->sb_bsize = bsize; -+ sb->sb_bsize_shift = ffs(bsize) - 1; - #ifdef GFS2_HAS_UUID -- memcpy(sb.sb_uuid, uuid, sizeof(sb.sb_uuid)); -+ get_random_bytes(&sb->sb_uuid, sizeof(sb->sb_uuid)); - #endif -- bh = bget(sdp, sdp->sb_addr); -- gfs2_sb_out(&sb, bh); -- brelse(bh); -+} - -- if (sdp->debug) { -- printf("\nSuper Block:\n"); -- gfs2_sb_print(&sb); -+int lgfs2_sb_write(const struct gfs2_sb *sb, int fd, const unsigned bsize) -+{ -+ int i, err = -1; -+ struct iovec *iov; -+ const size_t sb_addr = GFS2_SB_ADDR * GFS2_BASIC_BLOCK / bsize; -+ const size_t len = sb_addr + 1; -+ -+ /* We only need 2 blocks: one for zeroing and a second for the superblock */ -+ char *buf = calloc(2, bsize); -+ if (buf == NULL) -+ return -1; -+ -+ iov = malloc(len * sizeof(*iov)); -+ if (iov == NULL) -+ goto out_buf; -+ -+ for (i = 0; i < len; i++) { -+ iov[i].iov_base = buf; -+ iov[i].iov_len = bsize; - } -+ -+ gfs2_sb_out(sb, buf + bsize); -+ iov[sb_addr].iov_base = buf + bsize; -+ -+ if (pwritev(fd, iov, len, 0) < (len * bsize)) -+ goto out_iov; -+ -+ err = 0; -+out_iov: -+ free(iov); -+out_buf: -+ free(buf); -+ return err; - } - - int write_journal(struct gfs2_sbd *sdp, unsigned int j, unsigned int blocks) -diff --git a/gfs2/libgfs2/super.c b/gfs2/libgfs2/super.c -index d074236..b956366 100644 ---- a/gfs2/libgfs2/super.c -+++ b/gfs2/libgfs2/super.c -@@ -309,15 +309,3 @@ int gfs1_ri_update(struct gfs2_sbd *sdp, int fd, int *rgcount, int quiet) - - return __ri_update(sdp, fd, rgcount, &sane, quiet); - } -- --int write_sb(struct gfs2_sbd *sbp) --{ -- struct gfs2_buffer_head *bh; -- -- bh = bread(sbp, GFS2_SB_ADDR >> sbp->sd_fsb2bb_shift); -- gfs2_sb_out(&sbp->sd_sb, bh); -- brelse(bh); -- fsync(sbp->device_fd); /* make sure the change gets to disk ASAP */ -- return 0; --} -- -diff --git a/gfs2/mkfs/main_mkfs.c b/gfs2/mkfs/main_mkfs.c -index 0d84064..8bd396a 100644 ---- a/gfs2/mkfs/main_mkfs.c -+++ b/gfs2/mkfs/main_mkfs.c -@@ -569,8 +569,8 @@ static void print_results(struct gfs2_sbd *sdp, uint64_t real_device_size, - (unsigned long long)sdp->fssize, _("blocks")); - printf("%-27s%u\n", _("Journals:"), sdp->md.journals); - printf("%-27s%llu\n", _("Resource groups:"), (unsigned long long)sdp->rgrps); -- printf("%-27s\"%s\"\n", _("Locking protocol:"), sdp->lockproto); -- printf("%-27s\"%s\"\n", _("Lock table:"), sdp->locktable); -+ printf("%-27s\"%s\"\n", _("Locking protocol:"), opts->lockproto); -+ printf("%-27s\"%s\"\n", _("Lock table:"), opts->locktable); - /* Translators: "UUID" = universally unique identifier. */ - printf("%-27s%s\n", _("UUID:"), str_uuid(uuid)); - } -@@ -701,8 +701,6 @@ static void sbd_init(struct gfs2_sbd *sdp, struct mkfs_opts *opts, struct mkfs_d - /* TODO: Check if the fssize is too small, somehow */ - sdp->device.length = opts->fssize; - } -- strcpy(sdp->lockproto, opts->lockproto); -- strcpy(sdp->locktable, opts->locktable); - } - - static int probe_contents(struct mkfs_dev *dev) -@@ -791,11 +789,11 @@ static void open_dev(const char *path, struct mkfs_dev *dev) - void main_mkfs(int argc, char *argv[]) - { - struct gfs2_sbd sbd; -+ struct gfs2_sb sb; - struct mkfs_opts opts; - struct mkfs_dev dev; - lgfs2_rgrps_t rgs; - int error; -- unsigned char uuid[16]; - unsigned bsize; - - opts_init(&opts); -@@ -810,15 +808,16 @@ void main_mkfs(int argc, char *argv[]) - } - - sbd_init(&sbd, &opts, &dev, bsize); -+ lgfs2_sb_init(&sb, bsize); - if (opts.debug) { - printf(_("File system options:\n")); - printf(" bsize = %u\n", sbd.bsize); - printf(" qcsize = %u\n", sbd.qcsize); - printf(" jsize = %u\n", sbd.jsize); - printf(" journals = %u\n", sbd.md.journals); -- printf(" proto = %s\n", sbd.lockproto); -+ printf(" proto = %s\n", opts.lockproto); -+ printf(" table = %s\n", opts.locktable); - printf(" rgsize = %u\n", sbd.rgsize); -- printf(" table = %s\n", sbd.locktable); - printf(" fssize = %"PRIu64"\n", opts.fssize); - printf(" sunit = %lu\n", opts.sunit); - printf(" swidth = %lu\n", opts.swidth); -@@ -838,8 +837,13 @@ void main_mkfs(int argc, char *argv[]) - exit(1); - } - sbd.rgtree.osi_node = lgfs2_rgrps_root(rgs); // Temporary -+ - build_root(&sbd); -+ sb.sb_root_dir = sbd.md.rooti->i_di.di_num; -+ - build_master(&sbd); -+ sb.sb_master_dir = sbd.master_dir->i_di.di_num; -+ - error = build_jindex(&sbd); - if (error) { - fprintf(stderr, _("Error building '%s': %s\n"), "jindex", strerror(errno)); -@@ -872,8 +876,9 @@ void main_mkfs(int argc, char *argv[]) - fprintf(stderr, _("Error building '%s': %s\n"), "quota", strerror(errno)); - exit(EXIT_FAILURE); - } -- get_random_bytes(uuid, sizeof(uuid)); -- build_sb(&sbd, uuid); -+ -+ strcpy(sb.sb_lockproto, opts.lockproto); -+ strcpy(sb.sb_locktable, opts.locktable); - - do_init_inum(&sbd); - do_init_statfs(&sbd); -@@ -884,6 +889,13 @@ void main_mkfs(int argc, char *argv[]) - inode_put(&sbd.md.statfs); - - gfs2_rgrp_free(&sbd.rgtree); -+ -+ error = lgfs2_sb_write(&sb, dev.fd, sbd.bsize); -+ if (error) { -+ perror(_("Failed to write superblock\n")); -+ exit(EXIT_FAILURE); -+ } -+ - error = fsync(dev.fd); - if (error){ - perror(opts.device); -@@ -897,5 +909,5 @@ void main_mkfs(int argc, char *argv[]) - } - - if (!opts.quiet) -- print_results(&sbd, dev.size, &opts, uuid); -+ print_results(&sbd, dev.size, &opts, sb.sb_uuid); - } diff --git a/SOURCES/bz1063842-2-gfs2_utils_Ensure_sb_uuid_uses_are_guarded.patch b/SOURCES/bz1063842-2-gfs2_utils_Ensure_sb_uuid_uses_are_guarded.patch deleted file mode 100644 index 6afb997..0000000 --- a/SOURCES/bz1063842-2-gfs2_utils_Ensure_sb_uuid_uses_are_guarded.patch +++ /dev/null @@ -1,108 +0,0 @@ -commit 75a68102d55a1c361725ed01864c98fee6f77199 -Author: Andrew Price -Date: Thu Feb 6 13:16:18 2014 +0000 - - gfs2-utils: Ensure sb_uuid uses are guarded - - Guard uses of sb_uuid with #ifdef GFS2_HAS_UUID - - Tweak print_results() in mkfs.gfs2 to accept the gfs2_sb which we - conditionally print the uuid from, instead of the gfs2_sbd. - - Resolves: rhbz#1063842 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/edit/hexedit.c b/gfs2/edit/hexedit.c -index 36f6600..0708445 100644 ---- a/gfs2/edit/hexedit.c -+++ b/gfs2/edit/hexedit.c -@@ -104,10 +104,12 @@ static int gfs2_sb_printval(struct gfs2_sb *lsb, const char *strfield) - checkprints(strfield, lsb, sb_locktable); - checkprint(strfield, lsb, __pad3.no_addr); - checkprint(strfield, lsb, __pad4.no_addr); -+#ifdef GFS2_HAS_UUID - if (strcmp(strfield, "sb_uuid") == 0) { - printf("%s\n", str_uuid(lsb->sb_uuid)); - return 0; - } -+#endif - - return -1; - } -@@ -135,8 +137,9 @@ static int gfs2_sb_assigns(struct gfs2_sb *lsb, const char *strfield, - { - checkassigns(strfield, lsb, sb_lockproto, val); - checkassigns(strfield, lsb, sb_locktable, val); -+#ifdef GFS2_HAS_UUID - checkassigns(strfield, lsb, sb_uuid, val); -- -+#endif - return -1; - } - -diff --git a/gfs2/mkfs/main_mkfs.c b/gfs2/mkfs/main_mkfs.c -index 8bd396a..32da585 100644 ---- a/gfs2/mkfs/main_mkfs.c -+++ b/gfs2/mkfs/main_mkfs.c -@@ -555,24 +555,25 @@ static void opts_check(struct mkfs_opts *opts) - } - } - --static void print_results(struct gfs2_sbd *sdp, uint64_t real_device_size, -- struct mkfs_opts *opts, unsigned char uuid[16]) -+static void print_results(struct gfs2_sb *sb, struct mkfs_dev *dev, struct mkfs_opts *opts, -+ uint64_t rgrps, uint64_t fssize) - { - printf("%-27s%s\n", _("Device:"), opts->device); -- printf("%-27s%u\n", _("Block size:"), sdp->bsize); -- printf("%-27s%.2f %s (%llu %s)\n", _("Device size:"), -+ printf("%-27s%u\n", _("Block size:"), sb->sb_bsize); -+ printf("%-27s%.2f %s (%"PRIu64" %s)\n", _("Device size:"), - /* Translators: "GB" here means "gigabytes" */ -- real_device_size / ((float)(1 << 30)), _("GB"), -- (unsigned long long)real_device_size / sdp->bsize, _("blocks")); -- printf("%-27s%.2f %s (%llu %s)\n", _("Filesystem size:"), -- sdp->fssize / ((float)(1 << 30)) * sdp->bsize, _("GB"), -- (unsigned long long)sdp->fssize, _("blocks")); -- printf("%-27s%u\n", _("Journals:"), sdp->md.journals); -- printf("%-27s%llu\n", _("Resource groups:"), (unsigned long long)sdp->rgrps); -+ (dev->size / ((float)(1 << 30))), _("GB"), -+ (dev->size / sb->sb_bsize), _("blocks")); -+ printf("%-27s%.2f %s (%"PRIu64" %s)\n", _("Filesystem size:"), -+ (fssize / ((float)(1 << 30)) * sb->sb_bsize), _("GB"), fssize, _("blocks")); -+ printf("%-27s%u\n", _("Journals:"), opts->journals); -+ printf("%-27s%"PRIu64"\n", _("Resource groups:"), rgrps); - printf("%-27s\"%s\"\n", _("Locking protocol:"), opts->lockproto); - printf("%-27s\"%s\"\n", _("Lock table:"), opts->locktable); -+#ifdef GFS2_HAS_UUID - /* Translators: "UUID" = universally unique identifier. */ -- printf("%-27s%s\n", _("UUID:"), str_uuid(uuid)); -+ printf("%-27s%s\n", _("UUID:"), str_uuid(sb->sb_uuid)); -+#endif - } - - static void warn_of_destruction(const char *path) -@@ -909,5 +910,5 @@ void main_mkfs(int argc, char *argv[]) - } - - if (!opts.quiet) -- print_results(&sbd, dev.size, &opts, sb.sb_uuid); -+ print_results(&sb, &dev, &opts, sbd.rgrps, sbd.fssize); - } -diff --git a/gfs2/tune/super.c b/gfs2/tune/super.c -index cc34990..cbd0026 100644 ---- a/gfs2/tune/super.c -+++ b/gfs2/tune/super.c -@@ -124,8 +124,9 @@ static int is_gfs2(const struct tunegfs2 *tfs) - int print_super(const struct tunegfs2 *tfs) - { - printf(_("File system volume name: %s\n"), tfs->sb->sb_locktable); -- if (is_gfs2(tfs)) -- printf(_("File system UUID: %s\n"), uuid2str(tfs->sb->sb_uuid)); -+#ifdef GFS2_HAS_UUID -+ printf(_("File system UUID: %s\n"), uuid2str(tfs->sb->sb_uuid)); -+#endif - printf( _("File system magic number: 0x%X\n"), be32_to_cpu(tfs->sb->sb_header.mh_magic)); - printf(_("Block size: %d\n"), be32_to_cpu(tfs->sb->sb_bsize)); - printf(_("Block shift: %d\n"), be32_to_cpu(tfs->sb->sb_bsize_shift)); diff --git a/SOURCES/bz1063842-3-libgfs2_Add_support_for_new_leaf_hint_fields.patch b/SOURCES/bz1063842-3-libgfs2_Add_support_for_new_leaf_hint_fields.patch deleted file mode 100644 index dd1d1e3..0000000 --- a/SOURCES/bz1063842-3-libgfs2_Add_support_for_new_leaf_hint_fields.patch +++ /dev/null @@ -1,286 +0,0 @@ -commit e7b57dae8cfd096514b970d200e1e97648b495a6 -Author: Andrew Price -Date: Thu Feb 6 16:19:02 2014 +0000 - - libgfs2: Add support for new leaf hint fields - - Kernel commit 01bcb0de introduces new gfs2_leaf fields. This patch adds - support for those fields to libgfs2, conditional upon them being - discovered in the configure stage. Includes meta.c changes by Steve - Whitehouse. - - Resolves: rhbz#1063842 - - Signed-off-by: Andrew Price - -diff --git a/configure.ac b/configure.ac -index 628d85e..80310be 100644 ---- a/configure.ac -+++ b/configure.ac -@@ -116,12 +116,10 @@ AC_CHECK_HEADERS([arpa/inet.h fcntl.h inttypes.h libintl.h limits.h locale.h mnt - AC_CHECK_HEADERS([linux/dlmconstants.h linux/limits.h linux/types.h linux/netlink.h linux/fs.h],, - [AC_MSG_ERROR([Unable to find all required kernel headers.])]) - --AC_CHECK_HEADERS([linux/gfs2_ondisk.h], -- [AC_CHECK_MEMBERS([struct gfs2_sb.sb_uuid],, -- [AC_MSG_ERROR([Unable to find gfs2 uuid support in your headers. --Please update your kernel headers to a more recent version])], -- [#include ])], -- [AC_MSG_ERROR([Unable to find required kernel headers.])]) -+AC_CHECK_HEADER([linux/gfs2_ondisk.h], [], [AC_MSG_ERROR([Unable to find linux/gfs2_ondisk.h])]) -+AC_CHECK_MEMBER([struct gfs2_sb.sb_uuid], [], [], [[#include ]]) -+AC_CHECK_MEMBER([struct gfs2_leaf.lf_inode],[AC_DEFINE([GFS2_HAS_LEAF_HINTS],[],[Leaf block hints])], -+ [], [[#include ]]) - - # Checks for typedefs, structures, and compiler characteristics. - AC_C_INLINE -diff --git a/gfs2/edit/extended.c b/gfs2/edit/extended.c -index 27c32a9..328e35c 100644 ---- a/gfs2/edit/extended.c -+++ b/gfs2/edit/extended.c -@@ -296,8 +296,18 @@ static void print_inode_type(__be16 de_type) - } - } - -+#ifdef GFS2_HAS_LEAF_HINTS -+#define LEAF_HINT_FMTS "lf_inode: 0x%"PRIx64", lf_dist: %"PRIu32", " \ -+ "lf_nsec: %"PRIu32", lf_sec: %"PRIu64", " -+#define LEAF_HINT_FIELDS(lp) lp->lf_inode, lp->lf_dist, lp->lf_nsec, lp->lf_sec, -+#else -+#define LEAF_HINT_FMTS -+#define LEAF_HINT_FIELDS(lp) -+#endif -+ - static int display_leaf(struct iinfo *ind) - { -+ struct gfs2_leaf *leaf = &ind->ii[0].lf; - int start_line, total_dirents = start_row[dmode]; - int d; - -@@ -305,11 +315,13 @@ static int display_leaf(struct iinfo *ind) - if (gfs2_struct_type == GFS2_METATYPE_SB) - print_gfs2("The superblock has 2 directories"); - else -- print_gfs2("Directory block: lf_depth:%d, lf_entries:%d," -+ print_gfs2("Directory block: lf_depth:%d, lf_entries:%d, " -+ LEAF_HINT_FMTS - "fmt:%d next=0x%llx (%d dirents).", -- ind->ii[0].lf_depth, ind->ii[0].lf_entries, -- ind->ii[0].lf_dirent_format, -- ind->ii[0].lf_next, -+ leaf->lf_depth, leaf->lf_entries, -+ LEAF_HINT_FIELDS(leaf) -+ leaf->lf_dirent_format, -+ leaf->lf_next, - ind->ii[0].dirents); - - start_line = line; -diff --git a/gfs2/edit/gfs2hex.c b/gfs2/edit/gfs2hex.c -index cc0ceb6..cda4dbe 100644 ---- a/gfs2/edit/gfs2hex.c -+++ b/gfs2/edit/gfs2hex.c -@@ -341,17 +341,12 @@ uint64_t do_leaf_extended(char *dlebuf, struct iinfo *indir) - { - int x, i; - struct gfs2_dirent de; -- struct gfs2_leaf leaf; - struct gfs2_buffer_head tbh; /* kludge */ - - x = 0; - memset(indir, 0, sizeof(*indir)); - tbh.b_data = dlebuf; -- gfs2_leaf_in(&leaf, &tbh); -- indir->ii[0].lf_depth = leaf.lf_depth; -- indir->ii[0].lf_entries = leaf.lf_entries; -- indir->ii[0].lf_dirent_format = leaf.lf_dirent_format; -- indir->ii[0].lf_next = leaf.lf_next; -+ gfs2_leaf_in(&indir->ii[0].lf, &tbh); - /* Directory Entries: */ - for (i = sizeof(struct gfs2_leaf); i < sbd.bsize; - i += de.de_rec_len) { -@@ -372,7 +367,7 @@ uint64_t do_leaf_extended(char *dlebuf, struct iinfo *indir) - if (de.de_rec_len <= sizeof(struct gfs2_dirent)) - break; - } -- return leaf.lf_next; -+ return indir->ii[0].lf.lf_next; - } - - static void do_eattr_extended(struct gfs2_buffer_head *ebh) -diff --git a/gfs2/edit/hexedit.c b/gfs2/edit/hexedit.c -index 0708445..1738652 100644 ---- a/gfs2/edit/hexedit.c -+++ b/gfs2/edit/hexedit.c -@@ -219,7 +219,15 @@ static int gfs2_leaf_printval(struct gfs2_leaf *lf, const char *strfield) - checkprint(strfield, lf, lf_entries); - checkprint(strfield, lf, lf_dirent_format); - checkprint(strfield, lf, lf_next); -+#ifdef GFS2_HAS_LEAF_HINTS -+ checkprint(strfield, lf, lf_inode); -+ checkprint(strfield, lf, lf_dist); -+ checkprint(strfield, lf, lf_nsec); -+ checkprint(strfield, lf, lf_sec); -+ checkprints(strfield, lf, lf_reserved2); -+#else - checkprints(strfield, lf, lf_reserved); -+#endif - - return -1; - } -@@ -231,6 +239,12 @@ static int gfs2_leaf_assignval(struct gfs2_leaf *lf, const char *strfield, - checkassign(strfield, lf, lf_entries, value); - checkassign(strfield, lf, lf_dirent_format, value); - checkassign(strfield, lf, lf_next, value); -+#ifdef GFS2_HAS_LEAF_HINTS -+ checkassign(strfield, lf, lf_inode, value); -+ checkassign(strfield, lf, lf_dist, value); -+ checkassign(strfield, lf, lf_nsec, value); -+ checkassign(strfield, lf, lf_sec, value); -+#endif - - return -1; - } -diff --git a/gfs2/edit/hexedit.h b/gfs2/edit/hexedit.h -index 706909c..ebe3855 100644 ---- a/gfs2/edit/hexedit.h -+++ b/gfs2/edit/hexedit.h -@@ -78,10 +78,7 @@ struct indirect_info { - int height; - uint64_t block; - uint32_t dirents; -- uint16_t lf_depth; -- uint16_t lf_entries; -- uint32_t lf_dirent_format; -- uint64_t lf_next; -+ struct gfs2_leaf lf; - struct metapath mp; - struct gfs2_dirents dirent[64]; - }; -diff --git a/gfs2/fsck/metawalk.c b/gfs2/fsck/metawalk.c -index b8cef87..59fbde8 100644 ---- a/gfs2/fsck/metawalk.c -+++ b/gfs2/fsck/metawalk.c -@@ -657,7 +657,6 @@ static void dir_leaf_reada(struct gfs2_inode *ip, uint64_t *tbl, unsigned hsize) - static int check_leaf_blks(struct gfs2_inode *ip, struct metawalk_fxns *pass) - { - int error = 0; -- struct gfs2_leaf leaf; - unsigned hsize = (1 << ip->i_di.di_depth); - uint64_t leaf_no, leaf_next; - uint64_t first_ok_leaf, orig_di_blocks; -@@ -767,6 +766,7 @@ static int check_leaf_blks(struct gfs2_inode *ip, struct metawalk_fxns *pass) - - chained_leaf = 0; - do { -+ struct gfs2_leaf leaf; - if (fsck_abort) { - free(tbl); - posix_fadvise(sdp->device_fd, 0, 0, POSIX_FADV_NORMAL); -diff --git a/gfs2/libgfs2/fs_ops.c b/gfs2/libgfs2/fs_ops.c -index 4a84687..1790421 100644 ---- a/gfs2/libgfs2/fs_ops.c -+++ b/gfs2/libgfs2/fs_ops.c -@@ -1024,6 +1024,9 @@ void dir_split_leaf(struct gfs2_inode *dip, uint32_t start, uint64_t leaf_no, - oleaf->lf_depth = cpu_to_be16(oleaf->lf_depth); - nleaf->lf_depth = oleaf->lf_depth; - -+#ifdef GFS2_HAS_LEAF_HINTS -+ nleaf->lf_inode = cpu_to_be64(dip->i_di.di_num.no_addr); -+#endif - dip->i_di.di_blocks++; - bmodified(dip->i_bh); - -@@ -1206,7 +1209,9 @@ restart: - nleaf = (struct gfs2_leaf *)nbh->b_data; - nleaf->lf_depth = leaf->lf_depth; - nleaf->lf_dirent_format = cpu_to_be32(GFS2_FORMAT_DE); -- -+#ifdef GFS2_HAS_LEAF_HINTS -+ nleaf->lf_inode = cpu_to_be64(dip->i_di.di_num.no_addr); -+#endif - err = dirent_alloc(dip, nbh, len, &dent); - if (err) - return err; -@@ -1256,7 +1261,9 @@ static void dir_make_exhash(struct gfs2_inode *dip) - leaf = (struct gfs2_leaf *)bh->b_data; - leaf->lf_dirent_format = cpu_to_be32(GFS2_FORMAT_DE); - leaf->lf_entries = cpu_to_be16(dip->i_di.di_entries); -- -+#ifdef GFS2_HAS_LEAF_HINTS -+ leaf->lf_inode = cpu_to_be64(dip->i_di.di_num.no_addr); -+#endif - buffer_copy_tail(sdp, bh, sizeof(struct gfs2_leaf), - dip->i_bh, sizeof(struct gfs2_dinode)); - -diff --git a/gfs2/libgfs2/meta.c b/gfs2/libgfs2/meta.c -index 94be823..4305393 100644 ---- a/gfs2/libgfs2/meta.c -+++ b/gfs2/libgfs2/meta.c -@@ -317,7 +317,15 @@ F(lf_depth) - F(lf_entries) - F(lf_dirent_format) - F(lf_next) -+#ifdef GFS2_HAS_LEAF_HINTS -+FP(lf_inode, .points_to = (1 << LGFS2_MT_GFS2_DINODE)) -+F(lf_dist) -+F(lf_nsec, .flags = LGFS2_MFF_NSECS) -+F(lf_sec, .flags = LGFS2_MFF_SECS) -+RF(lf_reserved2) -+#else - RF(lf_reserved) -+#endif - }; - - #undef STRUCT -diff --git a/gfs2/libgfs2/ondisk.c b/gfs2/libgfs2/ondisk.c -index 43618bc..dcc537e 100644 ---- a/gfs2/libgfs2/ondisk.c -+++ b/gfs2/libgfs2/ondisk.c -@@ -433,8 +433,15 @@ void gfs2_leaf_in(struct gfs2_leaf *lf, struct gfs2_buffer_head *bh) - CPIN_16(lf, str, lf_entries); - CPIN_32(lf, str, lf_dirent_format); - CPIN_64(lf, str, lf_next); -- -+#ifdef GFS2_HAS_LEAF_HINTS -+ CPIN_64(lf, str, lf_inode); -+ CPIN_32(lf, str, lf_dist); -+ CPIN_32(lf, str, lf_nsec); -+ CPIN_64(lf, str, lf_sec); -+ CPIN_08(lf, str, lf_reserved2, 40); -+#else - CPIN_08(lf, str, lf_reserved, 32); -+#endif - } - - void gfs2_leaf_out(struct gfs2_leaf *lf, struct gfs2_buffer_head *bh) -@@ -446,8 +453,15 @@ void gfs2_leaf_out(struct gfs2_leaf *lf, struct gfs2_buffer_head *bh) - CPOUT_16(lf, str, lf_entries); - CPOUT_32(lf, str, lf_dirent_format); - CPOUT_64(lf, str, lf_next); -- -- CPOUT_08(lf, str, lf_reserved, 32); -+#ifdef GFS2_HAS_LEAF_HINTS -+ CPOUT_64(lf, str, lf_inode); -+ CPOUT_32(lf, str, lf_dist); -+ CPOUT_32(lf, str, lf_nsec); -+ CPOUT_64(lf, str, lf_sec); -+ CPOUT_08(lf, str, lf_reserved2, 40); -+#else -+ CPOUT_08(lf, str, lf_reserved, 64); -+#endif - bmodified(bh); - } - -@@ -458,6 +472,12 @@ void gfs2_leaf_print(struct gfs2_leaf *lf) - pv(lf, lf_entries, "%u", "0x%x"); - pv(lf, lf_dirent_format, "%u", "0x%x"); - pv(lf, lf_next, "%llu", "0x%llx"); -+#ifdef GFS2_HAS_LEAF_HINTS -+ pv(lf, lf_inode, "%llu", "0x%llx"); -+ pv(lf, lf_dist, "%u", "0x%x"); -+ pv(lf, lf_nsec, "%u", "0x%x"); -+ pv(lf, lf_sec, "%llu", "0x%llx"); -+#endif - } - - void gfs2_ea_header_in(struct gfs2_ea_header *ea, char *buf) diff --git a/SOURCES/bz1112342-1-gfs2_utils_tests_Build_unit_tests_with_consistent_cpp_flags.patch b/SOURCES/bz1112342-1-gfs2_utils_tests_Build_unit_tests_with_consistent_cpp_flags.patch new file mode 100644 index 0000000..c85bb70 --- /dev/null +++ b/SOURCES/bz1112342-1-gfs2_utils_tests_Build_unit_tests_with_consistent_cpp_flags.patch @@ -0,0 +1,56 @@ +commit e0e4c93b80f36fc40a5d631a14615162f27f3371 +Author: Andrew Price +Date: Mon Sep 8 12:03:40 2014 +0200 + + gfs2-utils tests: Build unit tests with consistent cpp flags + + The check_rgrp unit test was failing on ARM and s390 due to struct + gfs2_sbd having a different alignment from libgfs2. This was due to the + unit tests being built with different options to libgfs2. Fix up the + unit test CPPFLAGS to make sure the alignment is consistent. + + Also bump the test timeout for check_rgrp to make sure it completes on + slower build machines. + + Signed-off-by: Andrew Price + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 70e77ef..b912dfa 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -15,16 +15,22 @@ UNIT_CFLAGS = \ + UNIT_LDADD = \ + $(top_builddir)/gfs2/libgfs2/libgfs2.la \ + @check_LIBS@ ++UNIT_CPPFLAGS = \ ++ -D_FILE_OFFSET_BITS=64 \ ++ -D_LARGEFILE64_SOURCE \ ++ -D_GNU_SOURCE + + check_PROGRAMS = $(UNIT_TESTS) + + check_meta_SOURCES = $(UNIT_SOURCES) check_meta.c + check_meta_CFLAGS = $(UNIT_CFLAGS) + check_meta_LDADD = $(UNIT_LDADD) ++check_meta_CPPFLAGS = $(UNIT_CPPFLAGS) + + check_rgrp_SOURCES = $(UNIT_SOURCES) check_rgrp.c + check_rgrp_CFLAGS = $(UNIT_CFLAGS) + check_rgrp_LDADD = $(UNIT_LDADD) ++check_rgrp_CPPFLAGS = $(UNIT_CPPFLAGS) + endif + + # The `:;' works around a Bash 3.2 bug when the output is not writable. +diff --git a/tests/check_rgrp.c b/tests/check_rgrp.c +index d113846..e5fca8d 100644 +--- a/tests/check_rgrp.c ++++ b/tests/check_rgrp.c +@@ -125,7 +125,7 @@ static Suite * libgfs2_suite(void) + tcase_add_test(tc_rgrp, test_rbm_find_good); + tcase_add_test(tc_rgrp, test_rbm_find_bad); + tcase_add_test(tc_rgrp, test_rbm_find_lastblock); +- tcase_set_timeout(tc_rgrp, 60); ++ tcase_set_timeout(tc_rgrp, 120); + suite_add_tcase(s, tc_rgrp); + + return s; diff --git a/SOURCES/bz1112342-2-gfs2_utils_tests_Fix_unit_tests_for_RHEL7.patch b/SOURCES/bz1112342-2-gfs2_utils_tests_Fix_unit_tests_for_RHEL7.patch new file mode 100644 index 0000000..33d073c --- /dev/null +++ b/SOURCES/bz1112342-2-gfs2_utils_tests_Fix_unit_tests_for_RHEL7.patch @@ -0,0 +1,28 @@ +commit 9142cd526adfb9739b92419fc1faa0b4730e936d +Author: Andrew Price +Date: Mon Sep 8 10:18:11 2014 +0100 + + gfs2-utils tests: Fix unit tests for RHEL7 + + Older versions of check-devel do not have ck_assert_ptr_ne nor + ck_assert_uint_eq so provide macros to map them to fail_unless calls. + + Resolves: rhbz#1112342 + + Signed-off-by: Andrew Price + +diff --git a/tests/check_rgrp.c b/tests/check_rgrp.c +index e5fca8d..36dffe4 100644 +--- a/tests/check_rgrp.c ++++ b/tests/check_rgrp.c +@@ -5,6 +5,10 @@ + // TODO: Remove this when the extern is removed from libgfs2 + void print_it(const char *label, const char *fmt, const char *fmt2, ...) {} + ++/* Older check-devel doesn't have these functions */ ++#define ck_assert_ptr_ne(ptr, val) fail_unless(ptr != val) ++#define ck_assert_uint_eq(u1, u2) fail_unless(u1 == u2) ++ + static lgfs2_rgrps_t mockup_rgrp(void) + { + struct gfs2_sbd *sdp; diff --git a/SOURCES/bz1146160-fsck_gfs2_Detect_and_correct_corrupt_journals.patch b/SOURCES/bz1146160-fsck_gfs2_Detect_and_correct_corrupt_journals.patch new file mode 100644 index 0000000..80a8836 --- /dev/null +++ b/SOURCES/bz1146160-fsck_gfs2_Detect_and_correct_corrupt_journals.patch @@ -0,0 +1,161 @@ +commit 86fe75d99f1838410bebaf6f459bfee3333e5756 +Author: Bob Peterson +Date: Thu Nov 13 09:54:16 2014 -0600 + + fsck.gfs2: Detect and correct corrupt journals + + This patch changes fsck.gfs2 so that it can detect corruption in the + journal sequence numbering scheme. If the corruption is within a + certain tolerance (currently 10 sequencing errors) the journal sequence + numbers are fixed and journal is replayed as normal. If there are more + errors than can be tolerated, the problem is detected and the journal + may be cleared. + + rhbz#1146160 + +diff --git a/gfs2/fsck/fs_recovery.c b/gfs2/fsck/fs_recovery.c +index bc4210d..3d8fe98 100644 +--- a/gfs2/fsck/fs_recovery.c ++++ b/gfs2/fsck/fs_recovery.c +@@ -17,6 +17,7 @@ + #include "util.h" + + #define JOURNAL_NAME_SIZE 16 ++#define JOURNAL_SEQ_TOLERANCE 10 + + unsigned int sd_found_jblocks = 0, sd_replayed_jblocks = 0; + unsigned int sd_found_metablocks = 0, sd_replayed_metablocks = 0; +@@ -138,10 +139,15 @@ static int buf_lo_scan_elements(struct gfs2_inode *ip, unsigned int start, + check_magic = ((struct gfs2_meta_header *) + (bh_ip->b_data))->mh_magic; + check_magic = be32_to_cpu(check_magic); +- if (check_magic != GFS2_MAGIC) ++ if (check_magic != GFS2_MAGIC) { ++ log_err(_("Journal corruption detected at block #" ++ "%lld (0x%llx) for journal+0x%x.\n"), ++ (unsigned long long)blkno, (unsigned long long)blkno, ++ start); + error = -EIO; +- else ++ } else { + bmodified(bh_ip); ++ } + + brelse(bh_log); + brelse(bh_ip); +@@ -313,8 +319,11 @@ static int foreach_descriptor(struct gfs2_inode *ip, unsigned int start, + brelse(bh); + continue; + } +- if (error == 1) ++ if (error == 1) { ++ log_err(_("Journal corruption detected at " ++ "journal+0x%x.\n"), start); + error = -EIO; ++ } + bmodified(bh); + brelse(bh); + return error; +@@ -354,10 +363,13 @@ static int foreach_descriptor(struct gfs2_inode *ip, unsigned int start, + } + + /** +- * fix_journal_seq_no - Fix log header sequencing problems ++ * check_journal_seq_no - Check and Fix log header sequencing problems + * @ip: the journal incore inode ++ * @fix: if 1, fix the sequence numbers, otherwise just report the problem ++ * ++ * Returns: The number of sequencing errors (hopefully none). + */ +-static int fix_journal_seq_no(struct gfs2_inode *ip) ++static int check_journal_seq_no(struct gfs2_inode *ip, int fix) + { + int error = 0, wrapped = 0; + uint32_t jd_blocks = ip->i_di.di_size / ip->i_sbd->sd_sb.sb_bsize; +@@ -368,6 +380,7 @@ static int fix_journal_seq_no(struct gfs2_inode *ip) + uint64_t dblock; + uint32_t extlen; + struct gfs2_buffer_head *bh; ++ int seq_errors = 0; + + memset(&lh, 0, sizeof(lh)); + for (blk = 0; blk < jd_blocks; blk++) { +@@ -395,6 +408,10 @@ static int fix_journal_seq_no(struct gfs2_inode *ip) + (unsigned long long)lowest_seq, + (unsigned long long)highest_seq, + (unsigned long long)prev_seq); ++ if (!fix) { ++ seq_errors++; ++ continue; ++ } + highest_seq++; + lh.lh_sequence = highest_seq; + prev_seq = lh.lh_sequence; +@@ -404,7 +421,9 @@ static int fix_journal_seq_no(struct gfs2_inode *ip) + gfs2_log_header_out(&lh, bh); + brelse(bh); + } +- return 0; ++ if (seq_errors && fix) ++ log_err(_("%d sequence errors fixed.\n"), seq_errors); ++ return seq_errors; + } + + /** +@@ -456,6 +475,15 @@ static int gfs2_recover_journal(struct gfs2_inode *ip, int j, int preen, + + osi_list_init(&sd_revoke_list); + error = gfs2_find_jhead(ip, &head); ++ if (!error) { ++ error = check_journal_seq_no(ip, 0); ++ if (error > JOURNAL_SEQ_TOLERANCE) { ++ log_err( _("Journal #%d (\"journal%d\") has %d " ++ "sequencing errors; tolerance is %d.\n"), ++ j+1, j, error, JOURNAL_SEQ_TOLERANCE); ++ goto out; ++ } ++ } + if (error) { + if (opts.no) { + log_err( _("Journal #%d (\"journal%d\") is corrupt\n"),j+1, j); +@@ -481,7 +509,7 @@ static int gfs2_recover_journal(struct gfs2_inode *ip, int j, int preen, + goto out; + } + log_info( _("jid=%u: Repairing journal...\n"), j); +- error = fix_journal_seq_no(ip); ++ error = check_journal_seq_no(ip, 1); + if (error) { + log_err( _("jid=%u: Unable to fix the bad journal.\n"), + j); +@@ -530,8 +558,10 @@ static int gfs2_recover_journal(struct gfs2_inode *ip, int j, int preen, + for (pass = 0; pass < 2; pass++) { + error = foreach_descriptor(ip, head.lh_tail, + head.lh_blkno, pass); +- if (error) ++ if (error) { ++ log_err(_("Error found during journal replay.\n")); + goto out; ++ } + } + log_info( _("jid=%u: Found %u revoke tags\n"), j, sd_found_revokes); + gfs2_revoke_clean(sdp); +@@ -550,14 +580,16 @@ out: + log_info( _("jid=%u: Done\n"), j); + return 0; + } +- log_info( _("jid=%u: Failed\n"), j); ++ log_err( _("jid=%u: Failed\n"), j); + reinit: +- if (query( _("Do you want to clear the journal instead? (y/n)"))) ++ if (query( _("Do you want to clear the journal instead? (y/n)"))) { + error = write_journal(sdp->md.journal[j], sdp->bsize, + sdp->md.journal[j]->i_di.di_size / + sdp->sd_sb.sb_bsize); +- else ++ log_err(_("jid=%u: journal was cleared.\n"), j); ++ } else { + log_err( _("jid=%u: journal not cleared.\n"), j); ++ } + return error; + } + diff --git a/SOURCES/bz1154786-fsck_gfs2_Improve_reporting_of_pass_timings.patch b/SOURCES/bz1154786-fsck_gfs2_Improve_reporting_of_pass_timings.patch new file mode 100644 index 0000000..a630fa8 --- /dev/null +++ b/SOURCES/bz1154786-fsck_gfs2_Improve_reporting_of_pass_timings.patch @@ -0,0 +1,90 @@ +commit 34ab6e375e654b5b8b4c4c3c01e12c9f9749a928 +Author: Andrew Price +Date: Thu Nov 13 07:43:01 2014 -0500 + + fsck.gfs2: Improve reporting of pass timings + + The days value is not currently reported in the pass timings but the + hours value is still reported modulo 24. Drop the use of gmtime(3) as + it's more appropriate for calendar time operations than elapsed time, + and add a simple duration reporting function which matches the existing + output format. + + Resolves: rhbz#1154786 + + Signed-off-by: Andrew Price + +diff --git a/gfs2/fsck/main.c b/gfs2/fsck/main.c +index b25d802..a4af25d 100644 +--- a/gfs2/fsck/main.c ++++ b/gfs2/fsck/main.c +@@ -246,18 +246,46 @@ static const struct fsck_pass passes[] = { + { .name = NULL, } + }; + ++static void print_pass_duration(const char *name, struct timeval *start) ++{ ++ char duration[17] = ""; /* strlen("XXdXXhXXmXX.XXXs") + 1 */ ++ struct timeval end, diff; ++ unsigned d, h, m, s; ++ char *p = duration; ++ ++ gettimeofday(&end, NULL); ++ timersub(&end, start, &diff); ++ ++ s = diff.tv_sec % 60; ++ diff.tv_sec /= 60; ++ m = diff.tv_sec % 60; ++ diff.tv_sec /= 60; ++ h = diff.tv_sec % 24; ++ d = diff.tv_sec / 24; ++ ++ if (d) ++ p += snprintf(p, 4, "%ud", d > 99 ? 99U : d); ++ if (h) ++ p += snprintf(p, 4, "%uh", h); ++ if (m) ++ p += snprintf(p, 4, "%um", m); ++ ++ snprintf(p, 8, "%u.%03lus", s, diff.tv_usec / 1000); ++ log_notice(_("%s completed in %s\n"), name, duration); ++} ++ + static int fsck_pass(const struct fsck_pass *p, struct gfs2_sbd *sdp) + { + int ret; +- struct timeval before, after, diff; +- time_t runtime; +- struct tm *run_tm; ++ struct timeval timer; + + if (fsck_abort) + return FSCK_CANCELED; + pass = p->name; ++ + log_notice( _("Starting %s\n"), p->name); +- gettimeofday(&before, 0); ++ gettimeofday(&timer, NULL); ++ + ret = p->f(sdp); + if (ret) + exit(ret); +@@ -266,16 +294,8 @@ static int fsck_pass(const struct fsck_pass *p, struct gfs2_sbd *sdp) + log_notice( _("%s interrupted \n"), p->name); + return FSCK_CANCELED; + } +- gettimeofday(&after, 0); +- timersub(&after, &before, &diff); +- runtime = (time_t)diff.tv_sec; +- run_tm = gmtime(&runtime); +- log_notice( _("%s completed in "), p->name); +- if (run_tm->tm_hour) +- log_notice("%dh", run_tm->tm_hour); +- if (run_tm->tm_min) +- log_notice("%dm", run_tm->tm_min); +- log_notice("%d.%03lds \n", run_tm->tm_sec, diff.tv_usec / 1000); ++ ++ print_pass_duration(p->name, &timer); + return 0; + } + diff --git a/SOURCES/bz1162817-mkfs_gfs2_Revert_default_resource_group_size.patch b/SOURCES/bz1162817-mkfs_gfs2_Revert_default_resource_group_size.patch new file mode 100644 index 0000000..7bcc648 --- /dev/null +++ b/SOURCES/bz1162817-mkfs_gfs2_Revert_default_resource_group_size.patch @@ -0,0 +1,27 @@ +commit 33c48a55afa572b86de40364246d749a0e5d44e2 +Author: Andrew Price +Date: Thu Nov 13 14:09:08 2014 +0000 + + mkfs.gfs2: Revert default resource group size + + Choose a more performant resource group size than the maximum by default + until gfs2 is more tuned for the larger number of bitmap blocks required + for 2GB resource groups. + + Resolves: rhbz#1162817 + + Signed-off-by: Andrew Price + +diff --git a/gfs2/mkfs/main_mkfs.c b/gfs2/mkfs/main_mkfs.c +index e927d82..f4b8fe6 100644 +--- a/gfs2/mkfs/main_mkfs.c ++++ b/gfs2/mkfs/main_mkfs.c +@@ -159,7 +159,7 @@ static void opts_init(struct mkfs_opts *opts) + opts->bsize = GFS2_DEFAULT_BSIZE; + opts->jsize = GFS2_DEFAULT_JSIZE; + opts->qcsize = GFS2_DEFAULT_QCSIZE; +- opts->rgsize = GFS2_MAX_RGSIZE; ++ opts->rgsize = GFS2_DEFAULT_RGSIZE; + opts->lockproto = "lock_dlm"; + opts->locktable = ""; + opts->confirm = 1; diff --git a/SOURCES/bz1178604-1-fsck_gfs2_fix_broken_i_goal_values_in_inodes.patch b/SOURCES/bz1178604-1-fsck_gfs2_fix_broken_i_goal_values_in_inodes.patch new file mode 100644 index 0000000..55f6f7a --- /dev/null +++ b/SOURCES/bz1178604-1-fsck_gfs2_fix_broken_i_goal_values_in_inodes.patch @@ -0,0 +1,173 @@ +commit b09dae840a4e91e59cf73089da8e18bc0f299e80 +Author: Abhi Das +Date: Fri Dec 5 10:16:49 2014 -0600 + + fsck.gfs2: fix broken i_goal values in inodes + + This patch allows fsck.gfs2 to fix bad values for the i_goal + field in inodes that could arise from a gfs1->gfs2 conversion + or through other corruption + + Resolves: rhbz#1149516 + Signed-off-by: Abhi Das + +diff --git a/gfs2/fsck/metawalk.c b/gfs2/fsck/metawalk.c +index 329fc3b..9aa9fb8 100644 +--- a/gfs2/fsck/metawalk.c ++++ b/gfs2/fsck/metawalk.c +@@ -1395,7 +1395,8 @@ static int build_and_check_metalist(struct gfs2_inode *ip, osi_list_t *mlp, + */ + static int check_data(struct gfs2_inode *ip, struct metawalk_fxns *pass, + struct gfs2_buffer_head *bh, int head_size, +- uint64_t *blks_checked, uint64_t *error_blk) ++ uint64_t *last_block, uint64_t *blks_checked, ++ uint64_t *error_blk) + { + int error = 0, rc = 0; + uint64_t block, *ptr; +@@ -1410,7 +1411,7 @@ static int check_data(struct gfs2_inode *ip, struct metawalk_fxns *pass, + + if (skip_this_pass || fsck_abort) + return error; +- block = be64_to_cpu(*ptr); ++ *last_block = block = be64_to_cpu(*ptr); + /* It's important that we don't call valid_block() and + bypass calling check_data on invalid blocks because that + would defeat the rangecheck_block related functions in +@@ -1490,7 +1491,7 @@ int check_metatree(struct gfs2_inode *ip, struct metawalk_fxns *pass) + struct gfs2_buffer_head *bh; + uint32_t height = ip->i_di.di_height; + int i, head_size; +- uint64_t blks_checked = 0; ++ uint64_t blks_checked = 0, last_block = 0; + int error, rc; + int metadata_clean = 0; + uint64_t error_blk = 0; +@@ -1514,6 +1515,9 @@ int check_metatree(struct gfs2_inode *ip, struct metawalk_fxns *pass) + * comprise the directory hash table, so we perform the directory + * checks and exit. */ + if (is_dir(&ip->i_di, ip->i_sbd->gfs1)) { ++ last_block = ip->i_di.di_num.no_addr; ++ if (pass->check_i_goal) ++ pass->check_i_goal(ip, last_block, pass->private); + if (!(ip->i_di.di_flags & GFS2_DIF_EXHASH)) + goto out; + /* check validity of leaf blocks and leaf chains */ +@@ -1540,7 +1544,7 @@ int check_metatree(struct gfs2_inode *ip, struct metawalk_fxns *pass) + + if (pass->check_data) + error = check_data(ip, pass, bh, head_size, +- &blks_checked, &error_blk); ++ &last_block, &blks_checked, &error_blk); + if (pass->big_file_msg && ip->i_di.di_blocks > COMFORTABLE_BLKS) + pass->big_file_msg(ip, blks_checked); + } +@@ -1552,6 +1556,8 @@ int check_metatree(struct gfs2_inode *ip, struct metawalk_fxns *pass) + (unsigned long long)ip->i_di.di_num.no_addr); + fflush(stdout); + } ++ if (!error && pass->check_i_goal) ++ pass->check_i_goal(ip, last_block, pass->private); + undo_metalist: + if (!error) + goto out; +diff --git a/gfs2/fsck/metawalk.h b/gfs2/fsck/metawalk.h +index a4e0676..b3c1299 100644 +--- a/gfs2/fsck/metawalk.h ++++ b/gfs2/fsck/metawalk.h +@@ -90,6 +90,7 @@ enum meta_check_rc { + * check_dentry: + * check_eattr_entry: + * check_eattr_extentry: ++ * check_i_goal: + */ + struct metawalk_fxns { + void *private; +@@ -141,6 +142,8 @@ struct metawalk_fxns { + struct gfs2_ea_header *ea_hdr, + struct gfs2_ea_header *ea_hdr_prev, + void *private); ++ int (*check_i_goal) (struct gfs2_inode *ip, uint64_t goal_blk, ++ void *private); + int (*finish_eattr_indir) (struct gfs2_inode *ip, int leaf_pointers, + int leaf_pointer_errors, void *private); + void (*big_file_msg) (struct gfs2_inode *ip, uint64_t blks_checked); +diff --git a/gfs2/fsck/pass1.c b/gfs2/fsck/pass1.c +index 90ca357..60f0356 100644 +--- a/gfs2/fsck/pass1.c ++++ b/gfs2/fsck/pass1.c +@@ -62,6 +62,7 @@ static int check_extended_leaf_eattr(struct gfs2_inode *ip, uint64_t *data_ptr, + struct gfs2_ea_header *ea_hdr, + struct gfs2_ea_header *ea_hdr_prev, + void *private); ++static int check_i_goal(struct gfs2_inode *ip, uint64_t goal_blk, void *private); + static int finish_eattr_indir(struct gfs2_inode *ip, int leaf_pointers, + int leaf_pointer_errors, void *private); + static int invalidate_metadata(struct gfs2_inode *ip, uint64_t block, +@@ -99,6 +100,7 @@ struct metawalk_fxns pass1_fxns = { + .check_dentry = NULL, + .check_eattr_entry = check_eattr_entries, + .check_eattr_extentry = check_extended_leaf_eattr, ++ .check_i_goal = NULL, + .finish_eattr_indir = finish_eattr_indir, + .big_file_msg = big_file_comfort, + .repair_leaf = pass1_repair_leaf, +@@ -792,6 +794,48 @@ static int check_extended_leaf_eattr(struct gfs2_inode *ip, uint64_t *data_ptr, + return error; + } + ++/** ++ * check_i_goal ++ * @ip ++ * @goal_blk: What the goal block should be for this inode ++ * ++ * The goal block for a regular file is typically the last ++ * data block of the file. If we can't get the right value, ++ * the inode metadata block is the next best thing. ++ * ++ * Returns: 0 if corrected, 1 if not corrected ++ */ ++static int check_i_goal(struct gfs2_inode *ip, uint64_t goal_blk, ++ void *private) ++{ ++ struct gfs2_sbd *sdp = ip->i_sbd; ++ ++ if (fsck_system_inode(sdp, ip->i_di.di_num.no_addr)) ++ return 0; ++ if (!goal_blk) ++ goal_blk = ip->i_di.di_num.no_addr; ++ if (ip->i_di.di_goal_meta != goal_blk || ++ ip->i_di.di_goal_data != goal_blk) { ++ log_err( _("Error: inode %llu (0x%llx) has invalid " ++ "allocation goal block %llu (0x%llx). Should" ++ " be %llu (0x%llx)\n"), ++ (unsigned long long)ip->i_di.di_num.no_addr, ++ (unsigned long long)ip->i_di.di_num.no_addr, ++ (unsigned long long)ip->i_di.di_goal_meta, ++ (unsigned long long)ip->i_di.di_goal_meta, ++ (unsigned long long)goal_blk, ++ (unsigned long long)goal_blk); ++ if (query( _("Fix the invalid goal block? (y/n) "))) { ++ ip->i_di.di_goal_meta = ip->i_di.di_goal_data = goal_blk; ++ bmodified(ip->i_bh); ++ } else { ++ log_err(_("Invalid goal block not fixed.\n")); ++ return 1; ++ } ++ } ++ return 0; ++} ++ + static int check_eattr_leaf(struct gfs2_inode *ip, uint64_t block, + uint64_t parent, struct gfs2_buffer_head **bh, + void *private) +@@ -1624,6 +1668,9 @@ int pass1(struct gfs2_sbd *sdp) + /* Make sure the system inodes are okay & represented in the bitmap. */ + check_system_inodes(sdp); + ++ /* Turn the check_i_goal function ON for the non-system inodes */ ++ pass1_fxns.check_i_goal = check_i_goal; ++ + /* So, do we do a depth first search starting at the root + * inode, or use the rg bitmaps, or just read every fs block + * to find the inodes? If we use the depth first search, why diff --git a/SOURCES/bz1178604-2-gfs2_convert_use_correct_i_goal_values_instead_of_zeros_for_inodes.patch b/SOURCES/bz1178604-2-gfs2_convert_use_correct_i_goal_values_instead_of_zeros_for_inodes.patch new file mode 100644 index 0000000..1e1ad7e --- /dev/null +++ b/SOURCES/bz1178604-2-gfs2_convert_use_correct_i_goal_values_instead_of_zeros_for_inodes.patch @@ -0,0 +1,56 @@ +commit d79246d702623124595a008c732133e32cacba8e +Author: Abhi Das +Date: Mon Dec 8 18:21:47 2014 -0600 + + gfs2_convert: use correct i_goal values instead of zeros for inodes + + This patch sets the inode i_goal_data and i_goal_meta values to the + last allocated block for that inode instead of setting it to zero + as it did before. + + Resolves: rhbz#1149516 + Signed-off-by: Abhi Das + +diff --git a/gfs2/convert/gfs2_convert.c b/gfs2/convert/gfs2_convert.c +index 19a9839..0b56dd1 100644 +--- a/gfs2/convert/gfs2_convert.c ++++ b/gfs2/convert/gfs2_convert.c +@@ -618,8 +618,10 @@ static int fix_ind_reg_or_dir(struct gfs2_sbd *sbp, struct gfs2_inode *ip, uint3 + mp_gfs1_to_gfs2(sbp, di_height, gfs2_hgt, &blk->mp, &gfs2mp); + memcpy(&blk->mp, &gfs2mp, sizeof(struct metapath)); + blk->height -= di_height - gfs2_hgt; +- if (len) ++ if (len) { + fix_metatree(sbp, ip, blk, ptr1, len); ++ ip->i_di.di_goal_data = ip->i_di.di_goal_meta = be64_to_cpu(*ptr2); ++ } + + return 0; + } +@@ -903,7 +905,7 @@ static int adjust_inode(struct gfs2_sbd *sbp, struct gfs2_buffer_head *bh) + inode->i_di.di_mode |= S_IFSOCK; + break; + } +- ++ + /* ----------------------------------------------------------- */ + /* gfs2 inodes are slightly different from gfs1 inodes in that */ + /* di_goal_meta has shifted locations and di_goal_data has */ +@@ -929,7 +931,7 @@ static int adjust_inode(struct gfs2_sbd *sbp, struct gfs2_buffer_head *bh) + inode->i_di.di_goal_data = 0; /* make sure the upper 32b are 0 */ + inode->i_di.di_goal_data = gfs1_dinode_struct->di_goal_dblk; + inode->i_di.di_generation = 0; +- ++ + if (adjust_indirect_blocks(sbp, inode)) + return -1; + /* Check for cdpns */ +@@ -945,7 +947,7 @@ static int adjust_inode(struct gfs2_sbd *sbp, struct gfs2_buffer_head *bh) + return -1; + } + } +- ++ + bmodified(inode->i_bh); + inode_put(&inode); /* does gfs2_dinode_out if modified */ + sbp->md.next_inum++; /* update inode count */ diff --git a/SOURCES/bz1178604-3-tests_test_for_incorrect_inode_i_goal_values.patch b/SOURCES/bz1178604-3-tests_test_for_incorrect_inode_i_goal_values.patch new file mode 100644 index 0000000..ec90c01 --- /dev/null +++ b/SOURCES/bz1178604-3-tests_test_for_incorrect_inode_i_goal_values.patch @@ -0,0 +1,24 @@ +commit c5b09c4f957d9690807610c8b5e789a280132d2e +Author: Abhi Das +Date: Tue Dec 23 12:51:27 2014 -0600 + + tests: test for incorrect inode i_goal values + + Test corresponds to the bug 1149516 + + Resolves: rhbz#1149516 + Signed-off-by: Abhi Das + +diff --git a/tests/fsck.at b/tests/fsck.at +index d7a8357..afe26db 100644 +--- a/tests/fsck.at ++++ b/tests/fsck.at +@@ -8,3 +8,8 @@ GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 513 } + GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 4095 }]) + GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set sb { sb_bsize: 4097 }]) + AT_CLEANUP ++ ++AT_SETUP([Fix invalid goal blocks]) ++GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set '/' { di_goal_meta: 0 }]) ++GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set '/' { di_goal_data: 0 }]) ++AT_CLEANUP diff --git a/SOURCES/bz1178604-4-fsck_gfs2_Reprocess_nodes_if_anything_changed_addendum_1_of_2.patch b/SOURCES/bz1178604-4-fsck_gfs2_Reprocess_nodes_if_anything_changed_addendum_1_of_2.patch new file mode 100644 index 0000000..969787d --- /dev/null +++ b/SOURCES/bz1178604-4-fsck_gfs2_Reprocess_nodes_if_anything_changed_addendum_1_of_2.patch @@ -0,0 +1,314 @@ +commit 5eccbb33c28604436d38f4148fbb651151af1aef +Author: Bob Peterson +Date: Wed Jan 14 10:54:28 2015 -0600 + + fsck.gfs2: Reprocess nodes if anything changed - addendum 1 of 2 + + Before this patch, fsck.gfs2 called "reprocess_inode" in several + places, especially when the number of blocks had changed from the + original. That works in almost all cases. However, there's a corner + case where a block may be deleted, due to errors (for example, a + bad directory leaf), and another block takes its place. In that + case the count of the number of blocks is still the same, but the + inode should be reprocessed anyway, because the deleted blocks + and replacement blocks may be at different locations or maybe of + different types. A hash table block may be "data" when it's freed, + but if the block is reused, it may be repurposed as a "leaf" block. + That may confuse subsequent processing. Another reason to call + reprocess_inode is when the goal block changes to a value outside + the resource group, due to block allocations for repairs. + + This patch is part 1 of 2 addendum fixes to make fsck fix i_goal + values correctly. The original three patches to fix this problem were + checked in against a wrong bz 1149516 (which is the rhel6 version + of the bug). The complete fix contains those three patches (b09dae8, + d79246d, c5b09c4) and this two-patch addendum for a total of 5 + patches. + + Resolves: rhbz#1178604 + Signed-off-by: Bob Peterson + +diff --git a/gfs2/fsck/lost_n_found.c b/gfs2/fsck/lost_n_found.c +index 9672c7a..b2e35e2 100644 +--- a/gfs2/fsck/lost_n_found.c ++++ b/gfs2/fsck/lost_n_found.c +@@ -174,7 +174,6 @@ void make_sure_lf_exists(struct gfs2_inode *ip) + int add_inode_to_lf(struct gfs2_inode *ip){ + char tmp_name[256]; + __be32 inode_type; +- uint64_t lf_blocks; + struct gfs2_sbd *sdp = ip->i_sbd; + int err = 0; + uint32_t mode; +@@ -184,7 +183,6 @@ int add_inode_to_lf(struct gfs2_inode *ip){ + log_err( _("Trying to add lost+found to itself...skipping")); + return 0; + } +- lf_blocks = lf_dip->i_di.di_blocks; + + if (sdp->gfs1) + mode = gfs_to_gfs2_mode(ip); +@@ -242,10 +240,6 @@ int add_inode_to_lf(struct gfs2_inode *ip){ + tmp_name, strerror(errno)); + exit(FSCK_ERROR); + } +- /* If the lf directory had new blocks added we have to mark them +- properly in the bitmap so they're not freed. */ +- if (lf_dip->i_di.di_blocks != lf_blocks) +- reprocess_inode(lf_dip, "lost+found"); + + /* This inode is linked from lost+found */ + incr_link_count(ip->i_di.di_num, lf_dip, _("from lost+found")); +diff --git a/gfs2/fsck/metawalk.c b/gfs2/fsck/metawalk.c +index 9aa9fb8..82abb40 100644 +--- a/gfs2/fsck/metawalk.c ++++ b/gfs2/fsck/metawalk.c +@@ -1639,11 +1639,11 @@ int check_dir(struct gfs2_sbd *sdp, uint64_t block, struct metawalk_fxns *pass) + { + struct gfs2_inode *ip; + int error = 0; +- uint64_t cur_blks; ++ struct alloc_state as; + + ip = fsck_load_inode(sdp, block); + +- cur_blks = ip->i_di.di_blocks; ++ astate_save(ip, &as); + + if (ip->i_di.di_flags & GFS2_DIF_EXHASH) + error = check_leaf_blks(ip, pass); +@@ -1653,7 +1653,7 @@ int check_dir(struct gfs2_sbd *sdp, uint64_t block, struct metawalk_fxns *pass) + if (error < 0) + stack; + +- if (ip->i_di.di_blocks != cur_blks) ++ if (astate_changed(ip, &as)) + reprocess_inode(ip, _("Current")); + + fsck_inode_put(&ip); /* does a brelse */ +diff --git a/gfs2/fsck/pass2.c b/gfs2/fsck/pass2.c +index 2971b8c..40c80b9 100644 +--- a/gfs2/fsck/pass2.c ++++ b/gfs2/fsck/pass2.c +@@ -1712,7 +1712,8 @@ build_it: + static int check_system_dir(struct gfs2_inode *sysinode, const char *dirname, + int builder(struct gfs2_sbd *sdp)) + { +- uint64_t iblock = 0, cur_blks; ++ uint64_t iblock = 0; ++ struct alloc_state as; + struct dir_status ds = {0}; + int error = 0; + +@@ -1729,14 +1730,14 @@ static int check_system_dir(struct gfs2_inode *sysinode, const char *dirname, + + pass2_fxns.private = (void *) &ds; + if (ds.q == gfs2_bad_block) { +- cur_blks = sysinode->i_di.di_blocks; ++ astate_save(sysinode, &as); + /* First check that the directory's metatree is valid */ + error = check_metatree(sysinode, &pass2_fxns); + if (error < 0) { + stack; + return error; + } +- if (sysinode->i_di.di_blocks != cur_blks) ++ if (astate_changed(sysinode, &as)) + reprocess_inode(sysinode, _("System inode")); + } + error = check_dir(sysinode->i_sbd, iblock, &pass2_fxns); +@@ -1757,7 +1758,7 @@ static int check_system_dir(struct gfs2_inode *sysinode, const char *dirname, + if (!ds.dotdir) { + log_err( _("No '.' entry found for %s directory.\n"), dirname); + if (query( _("Is it okay to add '.' entry? (y/n) "))) { +- cur_blks = sysinode->i_di.di_blocks; ++ astate_save(sysinode, &as); + log_warn( _("Adding '.' entry\n")); + error = dir_add(sysinode, ".", 1, &(sysinode->i_di.di_num), + (sysinode->i_sbd->gfs1 ? GFS_FILE_DIR : DT_DIR)); +@@ -1766,7 +1767,7 @@ static int check_system_dir(struct gfs2_inode *sysinode, const char *dirname, + strerror(errno)); + return -errno; + } +- if (cur_blks != sysinode->i_di.di_blocks) ++ if (astate_changed(sysinode, &as)) + reprocess_inode(sysinode, dirname); + /* This system inode is linked to itself via '.' */ + incr_link_count(sysinode->i_di.di_num, sysinode, +@@ -1848,7 +1849,8 @@ static inline int is_system_dir(struct gfs2_sbd *sdp, uint64_t block) + */ + int pass2(struct gfs2_sbd *sdp) + { +- uint64_t dirblk, cur_blks; ++ uint64_t dirblk; ++ struct alloc_state as; + uint8_t q; + struct dir_status ds = {0}; + struct gfs2_inode *ip; +@@ -1915,14 +1917,14 @@ int pass2(struct gfs2_sbd *sdp) + /* First check that the directory's metatree + * is valid */ + ip = fsck_load_inode(sdp, dirblk); +- cur_blks = ip->i_di.di_blocks; ++ astate_save(ip, &as); + error = check_metatree(ip, &pass2_fxns); + fsck_inode_put(&ip); + if (error < 0) { + stack; + return error; + } +- if (ip->i_di.di_blocks != cur_blks) ++ if (astate_changed(ip, &as)) + reprocess_inode(ip, "current"); + } + error = check_dir(sdp, dirblk, &pass2_fxns); +@@ -1982,7 +1984,7 @@ int pass2(struct gfs2_sbd *sdp) + (unsigned long long)dirblk); + + if (query( _("Is it okay to add '.' entry? (y/n) "))) { +- cur_blks = ip->i_di.di_blocks; ++ astate_save(ip, &as); + error = dir_add(ip, ".", 1, &(ip->i_di.di_num), + (sdp->gfs1 ? GFS_FILE_DIR : DT_DIR)); + if (error) { +@@ -1990,7 +1992,7 @@ int pass2(struct gfs2_sbd *sdp) + strerror(errno)); + return -errno; + } +- if (cur_blks != ip->i_di.di_blocks) { ++ if (astate_changed(ip, &as)) { + char dirname[80]; + + sprintf(dirname, _("Directory at %lld " +diff --git a/gfs2/fsck/pass3.c b/gfs2/fsck/pass3.c +index 9582b5b..167dac0 100644 +--- a/gfs2/fsck/pass3.c ++++ b/gfs2/fsck/pass3.c +@@ -24,7 +24,7 @@ static int attach_dotdot_to(struct gfs2_sbd *sdp, uint64_t newdotdot, + int filename_len = 2; + int err; + struct gfs2_inode *ip, *pip; +- uint64_t cur_blks; ++ struct alloc_state as; + + ip = fsck_load_inode(sdp, block); + pip = fsck_load_inode(sdp, newdotdot); +@@ -39,7 +39,7 @@ static int attach_dotdot_to(struct gfs2_sbd *sdp, uint64_t newdotdot, + log_warn( _("Unable to remove \"..\" directory entry.\n")); + else + decr_link_count(olddotdot, block, _("old \"..\"")); +- cur_blks = ip->i_di.di_blocks; ++ astate_save(ip, &as); + err = dir_add(ip, filename, filename_len, &pip->i_di.di_num, + (sdp->gfs1 ? GFS_FILE_DIR : DT_DIR)); + if (err) { +@@ -47,7 +47,7 @@ static int attach_dotdot_to(struct gfs2_sbd *sdp, uint64_t newdotdot, + filename, strerror(errno)); + exit(FSCK_ERROR); + } +- if (cur_blks != ip->i_di.di_blocks) { ++ if (astate_changed(ip, &as)) { + char dirname[80]; + + sprintf(dirname, _("Directory at %lld (0x%llx)"), +@@ -179,6 +179,7 @@ int pass3(struct gfs2_sbd *sdp) + struct dir_info *di, *tdi; + struct gfs2_inode *ip; + uint8_t q; ++ struct alloc_state lf_as = {.as_blocks = 0, .as_meta_goal = 0}; + + di = dirtree_find(sdp->md.rooti->i_di.di_num.no_addr); + if (di) { +@@ -225,6 +226,8 @@ int pass3(struct gfs2_sbd *sdp) + */ + log_info( _("Checking directory linkage.\n")); + for (tmp = osi_first(&dirtree); tmp; tmp = next) { ++ if (lf_dip && lf_as.as_blocks == 0) ++ astate_save(lf_dip, &lf_as); + next = osi_next(tmp); + di = (struct dir_info *)tmp; + while (!di->checked) { +@@ -327,8 +330,14 @@ int pass3(struct gfs2_sbd *sdp) + break; + } + } +- if (lf_dip) ++ if (lf_dip) { ++ /* If the lf directory had new blocks added we have to mark ++ them properly in the blockmap so they're not freed. */ ++ if (astate_changed(lf_dip, &lf_as)) ++ reprocess_inode(lf_dip, "lost+found"); ++ + log_debug( _("At end of pass3, lost+found entries is %u\n"), + lf_dip->i_di.di_entries); ++ } + return FSCK_OK; + } +diff --git a/gfs2/fsck/pass4.c b/gfs2/fsck/pass4.c +index 7b3cb87..f0c13fc 100644 +--- a/gfs2/fsck/pass4.c ++++ b/gfs2/fsck/pass4.c +@@ -48,12 +48,15 @@ static int scan_inode_list(struct gfs2_sbd *sdp) { + struct gfs2_inode *ip; + int lf_addition = 0; + uint8_t q; ++ struct alloc_state lf_as = {.as_blocks = 0, .as_meta_goal = 0}; + + /* FIXME: should probably factor this out into a generic + * scanning fxn */ + for (tmp = osi_first(&inodetree); tmp; tmp = next) { + if (skip_this_pass || fsck_abort) /* if asked to skip the rest */ + return 0; ++ if (lf_dip && lf_as.as_blocks == 0) ++ astate_save(lf_dip, &lf_as); + next = osi_next(tmp); + if (!(ii = (struct inode_info *)tmp)) { + log_crit( _("osi_tree broken in scan_info_list!!\n")); +@@ -182,6 +185,9 @@ static int scan_inode_list(struct gfs2_sbd *sdp) { + (unsigned long long)ii->di_num.no_addr, ii->di_nlink); + } /* osi_list_foreach(tmp, list) */ + ++ if (lf_dip && astate_changed(lf_dip, &lf_as)) ++ reprocess_inode(lf_dip, "lost+found"); ++ + if (lf_addition) { + if (!(ii = inodetree_find(lf_dip->i_di.di_num.no_addr))) { + log_crit( _("Unable to find lost+found inode in inode_hash!!\n")); +diff --git a/gfs2/fsck/util.h b/gfs2/fsck/util.h +index 276c726..66b9c7a 100644 +--- a/gfs2/fsck/util.h ++++ b/gfs2/fsck/util.h +@@ -12,6 +12,11 @@ + #define INODE_VALID 1 + #define INODE_INVALID 0 + ++struct alloc_state { ++ uint64_t as_blocks; ++ uint64_t as_meta_goal; ++}; ++ + struct di_info *search_list(osi_list_t *list, uint64_t addr); + void big_file_comfort(struct gfs2_inode *ip, uint64_t blks_checked); + void warm_fuzzy_stuff(uint64_t block); +@@ -27,6 +32,21 @@ extern const char *reftypes[ref_types + 1]; + #define BLOCKMAP_BYTE_OFFSET4(x) (((x) & 0x0000000000000001) << 2) + #define BLOCKMAP_MASK4 (0xf) + ++static inline void astate_save(struct gfs2_inode *ip, struct alloc_state *as) ++{ ++ as->as_blocks = ip->i_di.di_blocks; ++ as->as_meta_goal = ip->i_di.di_goal_meta; ++} ++ ++static inline int astate_changed(struct gfs2_inode *ip, struct alloc_state *as) ++{ ++ if (as->as_blocks != ip->i_di.di_blocks) ++ return 1; ++ if (as->as_meta_goal != ip->i_di.di_goal_meta) ++ return 1; ++ return 0; ++} ++ + static inline uint8_t block_type(uint64_t bblock) + { + static unsigned char *byte; diff --git a/SOURCES/bz1178604-5-fsck_gfs2_addendum_to_fix_broken_i_goal_values_in_inodes_addendum_2_of_2.patch b/SOURCES/bz1178604-5-fsck_gfs2_addendum_to_fix_broken_i_goal_values_in_inodes_addendum_2_of_2.patch new file mode 100644 index 0000000..eb58328 --- /dev/null +++ b/SOURCES/bz1178604-5-fsck_gfs2_addendum_to_fix_broken_i_goal_values_in_inodes_addendum_2_of_2.patch @@ -0,0 +1,258 @@ +commit 6d89e9dfe83f68ebb05bfb2ef4715cc5fb1aa630 +Author: Abhi Das +Date: Thu Jan 15 12:49:48 2015 -0600 + + fsck.gfs2: addendum to fix broken i_goal values in inodes - addendum 2 of 2 + + This patch moves some code around and fixes some corner cases that + the previous patches did not address. + This patch also fixes some trailing whitespace and removes a test + that is no longer valid from test/fsck.at + + This patch is part 2 of 2 addendum fixes to make fsck fix i_goal + values correctly. The original three patches to fix this problem were + checked in against a wrong bz 1149516 (which is the rhel6 version + of the bug). The complete fix contains those three patches (b09dae8, + d79246d, c5b09c4) and this two-patch addendum for a total of 5 + patches. + + Resolves: rhbz#1178604 + Signed-off-by: Abhi Das + +diff --git a/gfs2/fsck/metawalk.c b/gfs2/fsck/metawalk.c +index 82abb40..3460141 100644 +--- a/gfs2/fsck/metawalk.c ++++ b/gfs2/fsck/metawalk.c +@@ -1497,6 +1497,9 @@ int check_metatree(struct gfs2_inode *ip, struct metawalk_fxns *pass) + uint64_t error_blk = 0; + int hit_error_blk = 0; + ++ if (!height && pass->check_i_goal) ++ pass->check_i_goal(ip, ip->i_di.di_num.no_addr, ++ pass->private); + if (!height && !is_dir(&ip->i_di, ip->i_sbd->gfs1)) + return 0; + +@@ -1891,6 +1894,72 @@ static int alloc_leaf(struct gfs2_inode *ip, uint64_t block, void *private) + return 0; + } + ++/** ++ * rgrp_contains_block - Check if the rgrp provided contains the ++ * given block. Taken directly from the gfs2 kernel code ++ * @rgd: The rgrp to search within ++ * @block: The block to search for ++ * ++ * Returns: 1 if present, 0 if not. ++ */ ++static inline int rgrp_contains_block(struct rgrp_tree *rgd, uint64_t block) ++{ ++ uint64_t first = rgd->ri.ri_data0; ++ uint64_t last = first + rgd->ri.ri_data; ++ return first <= block && block < last; ++} ++ ++/** ++ * check_i_goal ++ * @ip ++ * @goal_blk: What the goal block should be for this inode ++ * ++ * The goal block for a regular file is typically the last ++ * data block of the file. If we can't get the right value, ++ * the inode metadata block is the next best thing. ++ * ++ * Returns: 0 if corrected, 1 if not corrected ++ */ ++int check_i_goal(struct gfs2_inode *ip, uint64_t goal_blk, ++ void *private) ++{ ++ struct gfs2_sbd *sdp = ip->i_sbd; ++ uint64_t i_block = ip->i_di.di_num.no_addr; ++ ++ /* Don't fix gfs1 inodes, system inodes or inodes whose goal blocks are ++ * set to the inode blocks themselves. */ ++ if (sdp->gfs1 || ip->i_di.di_flags & GFS2_DIF_SYSTEM || ++ ip->i_di.di_goal_meta == i_block) ++ return 0; ++ /* We default to the inode block */ ++ if (!goal_blk) ++ goal_blk = i_block; ++ ++ if (ip->i_di.di_goal_meta != goal_blk) { ++ /* If the existing goal block is in the same rgrp as the inode, ++ * we give the benefit of doubt and assume the value is correct */ ++ if (ip->i_rgd && ++ rgrp_contains_block(ip->i_rgd, ip->i_di.di_goal_meta)) ++ goto skip; ++ log_err( _("Error: inode %llu (0x%llx) has invalid " ++ "allocation goal block %llu (0x%llx). Should" ++ " be %llu (0x%llx)\n"), ++ (unsigned long long)i_block, (unsigned long long)i_block, ++ (unsigned long long)ip->i_di.di_goal_meta, ++ (unsigned long long)ip->i_di.di_goal_meta, ++ (unsigned long long)goal_blk, (unsigned long long)goal_blk); ++ if (query( _("Fix the invalid goal block? (y/n) "))) { ++ ip->i_di.di_goal_meta = ip->i_di.di_goal_data = goal_blk; ++ bmodified(ip->i_bh); ++ } else { ++ log_err(_("Invalid goal block not fixed.\n")); ++ return 1; ++ } ++ } ++skip: ++ return 0; ++} ++ + struct metawalk_fxns alloc_fxns = { + .private = NULL, + .check_leaf = alloc_leaf, +@@ -1901,6 +1970,7 @@ struct metawalk_fxns alloc_fxns = { + .check_dentry = NULL, + .check_eattr_entry = NULL, + .check_eattr_extentry = NULL, ++ .check_i_goal = check_i_goal, + .finish_eattr_indir = NULL, + }; + +diff --git a/gfs2/fsck/metawalk.h b/gfs2/fsck/metawalk.h +index b3c1299..482016a 100644 +--- a/gfs2/fsck/metawalk.h ++++ b/gfs2/fsck/metawalk.h +@@ -51,6 +51,8 @@ extern int _fsck_blockmap_set(struct gfs2_inode *ip, uint64_t bblock, + extern int check_n_fix_bitmap(struct gfs2_sbd *sdp, uint64_t blk, + int error_on_dinode, + enum gfs2_mark_block new_blockmap_state); ++extern int check_i_goal(struct gfs2_inode *ip, uint64_t goal_blk, ++ void *private); + extern void reprocess_inode(struct gfs2_inode *ip, const char *desc); + extern struct duptree *dupfind(uint64_t block); + extern struct gfs2_inode *fsck_system_inode(struct gfs2_sbd *sdp, +diff --git a/gfs2/fsck/pass1.c b/gfs2/fsck/pass1.c +index 60f0356..dbe60bd 100644 +--- a/gfs2/fsck/pass1.c ++++ b/gfs2/fsck/pass1.c +@@ -62,7 +62,6 @@ static int check_extended_leaf_eattr(struct gfs2_inode *ip, uint64_t *data_ptr, + struct gfs2_ea_header *ea_hdr, + struct gfs2_ea_header *ea_hdr_prev, + void *private); +-static int check_i_goal(struct gfs2_inode *ip, uint64_t goal_blk, void *private); + static int finish_eattr_indir(struct gfs2_inode *ip, int leaf_pointers, + int leaf_pointer_errors, void *private); + static int invalidate_metadata(struct gfs2_inode *ip, uint64_t block, +@@ -100,7 +99,7 @@ struct metawalk_fxns pass1_fxns = { + .check_dentry = NULL, + .check_eattr_entry = check_eattr_entries, + .check_eattr_extentry = check_extended_leaf_eattr, +- .check_i_goal = NULL, ++ .check_i_goal = check_i_goal, + .finish_eattr_indir = finish_eattr_indir, + .big_file_msg = big_file_comfort, + .repair_leaf = pass1_repair_leaf, +@@ -794,48 +793,6 @@ static int check_extended_leaf_eattr(struct gfs2_inode *ip, uint64_t *data_ptr, + return error; + } + +-/** +- * check_i_goal +- * @ip +- * @goal_blk: What the goal block should be for this inode +- * +- * The goal block for a regular file is typically the last +- * data block of the file. If we can't get the right value, +- * the inode metadata block is the next best thing. +- * +- * Returns: 0 if corrected, 1 if not corrected +- */ +-static int check_i_goal(struct gfs2_inode *ip, uint64_t goal_blk, +- void *private) +-{ +- struct gfs2_sbd *sdp = ip->i_sbd; +- +- if (fsck_system_inode(sdp, ip->i_di.di_num.no_addr)) +- return 0; +- if (!goal_blk) +- goal_blk = ip->i_di.di_num.no_addr; +- if (ip->i_di.di_goal_meta != goal_blk || +- ip->i_di.di_goal_data != goal_blk) { +- log_err( _("Error: inode %llu (0x%llx) has invalid " +- "allocation goal block %llu (0x%llx). Should" +- " be %llu (0x%llx)\n"), +- (unsigned long long)ip->i_di.di_num.no_addr, +- (unsigned long long)ip->i_di.di_num.no_addr, +- (unsigned long long)ip->i_di.di_goal_meta, +- (unsigned long long)ip->i_di.di_goal_meta, +- (unsigned long long)goal_blk, +- (unsigned long long)goal_blk); +- if (query( _("Fix the invalid goal block? (y/n) "))) { +- ip->i_di.di_goal_meta = ip->i_di.di_goal_data = goal_blk; +- bmodified(ip->i_bh); +- } else { +- log_err(_("Invalid goal block not fixed.\n")); +- return 1; +- } +- } +- return 0; +-} +- + static int check_eattr_leaf(struct gfs2_inode *ip, uint64_t block, + uint64_t parent, struct gfs2_buffer_head **bh, + void *private) +@@ -1217,7 +1174,8 @@ bad_dinode: + * handle_di - This is now a wrapper function that takes a gfs2_buffer_head + * and calls handle_ip, which takes an in-code dinode structure. + */ +-static int handle_di(struct gfs2_sbd *sdp, struct gfs2_buffer_head *bh) ++static int handle_di(struct gfs2_sbd *sdp, struct gfs2_buffer_head *bh, ++ struct rgrp_tree *rgd) + { + int error = 0; + uint64_t block = bh->b_blocknr; +@@ -1259,6 +1217,7 @@ static int handle_di(struct gfs2_sbd *sdp, struct gfs2_buffer_head *bh) + (unsigned long long)block, + (unsigned long long)block); + } ++ ip->i_rgd = rgd; + error = handle_ip(sdp, ip); + fsck_inode_put(&ip); + return error; +@@ -1585,7 +1544,7 @@ static int pass1_process_bitmap(struct gfs2_sbd *sdp, struct rgrp_tree *rgd, uin + (unsigned long long)block, + (unsigned long long)block); + check_n_fix_bitmap(sdp, block, 0, gfs2_block_free); +- } else if (handle_di(sdp, bh) < 0) { ++ } else if (handle_di(sdp, bh, rgd) < 0) { + stack; + brelse(bh); + gfs2_special_free(&gfs1_rindex_blks); +@@ -1668,9 +1627,6 @@ int pass1(struct gfs2_sbd *sdp) + /* Make sure the system inodes are okay & represented in the bitmap. */ + check_system_inodes(sdp); + +- /* Turn the check_i_goal function ON for the non-system inodes */ +- pass1_fxns.check_i_goal = check_i_goal; +- + /* So, do we do a depth first search starting at the root + * inode, or use the rg bitmaps, or just read every fs block + * to find the inodes? If we use the depth first search, why +diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h +index 10df2d4..d024e56 100644 +--- a/gfs2/libgfs2/libgfs2.h ++++ b/gfs2/libgfs2/libgfs2.h +@@ -233,6 +233,7 @@ struct gfs2_inode { + struct gfs2_dinode i_di; + struct gfs2_buffer_head *i_bh; + struct gfs2_sbd *i_sbd; ++ struct rgrp_tree *i_rgd; /* The rgrp this inode is in */ + }; + + /* FIXME not sure that i want to keep a record of the inodes or the +diff --git a/tests/fsck.at b/tests/fsck.at +index afe26db..e3b82bd 100644 +--- a/tests/fsck.at ++++ b/tests/fsck.at +@@ -11,5 +11,4 @@ AT_CLEANUP + + AT_SETUP([Fix invalid goal blocks]) + GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set '/' { di_goal_meta: 0 }]) +-GFS_LANG_CHECK([mkfs.gfs2 -O -p lock_nolock $GFS_TGT], [set '/' { di_goal_data: 0 }]) + AT_CLEANUP diff --git a/SOURCES/bz990683-fsck_gfs2_Add_ability_to_detect_journal_inode_indirect_block_corruption.patch b/SOURCES/bz990683-fsck_gfs2_Add_ability_to_detect_journal_inode_indirect_block_corruption.patch deleted file mode 100644 index f73d832..0000000 --- a/SOURCES/bz990683-fsck_gfs2_Add_ability_to_detect_journal_inode_indirect_block_corruption.patch +++ /dev/null @@ -1,193 +0,0 @@ -commit 83f0041621aa8abf112ae5c89d0f129cf00d8905 -Author: Bob Peterson -Date: Tue Jul 30 14:01:40 2013 -0500 - - fsck.gfs2: Add ability to detect journal inode indirect block corruption - - This patch gives the journal replay portion of fsck.gfs2 the ability to - do basic sanity checks on the indirect blocks associated with journals. - If corrupt indirect blocks are found, the journal is considered damaged, - and should be rebuilt by pass1. - - rhbz#990683 - -diff --git a/gfs2/fsck/fs_recovery.c b/gfs2/fsck/fs_recovery.c -index 71d9909..41d575a 100644 ---- a/gfs2/fsck/fs_recovery.c -+++ b/gfs2/fsck/fs_recovery.c -@@ -12,6 +12,7 @@ - #include "fsck.h" - #include "fs_recovery.h" - #include "libgfs2.h" -+#include "metawalk.h" - #include "util.h" - - #define JOURNAL_NAME_SIZE 16 -@@ -559,6 +560,63 @@ reinit: - return error; - } - -+/* We can't use the rangecheck function from pass1 because we haven't gone -+ * through initialization properly yet. */ -+static int rangecheck_jblock(struct gfs2_inode *ip, uint64_t block) -+{ -+ if((block > ip->i_sbd->fssize) || (block <= ip->i_sbd->sb_addr)) { -+ log_info( _("Bad block pointer (out of range) found in " -+ "journal inode %lld (0x%llx).\n"), -+ (unsigned long long)ip->i_di.di_num.no_addr, -+ (unsigned long long)ip->i_di.di_num.no_addr); -+ return meta_error; /* Exits check_metatree quicker */ -+ } -+ return meta_is_good; -+} -+ -+static int rangecheck_jmeta(struct gfs2_inode *ip, uint64_t block, -+ struct gfs2_buffer_head **bh, int h, -+ int *is_valid, int *was_duplicate, -+ void *private) -+{ -+ int rc; -+ -+ *bh = NULL; -+ *was_duplicate = 0; -+ *is_valid = 0; -+ rc = rangecheck_jblock(ip, block); -+ if (rc == meta_is_good) { -+ *bh = bread(ip->i_sbd, block); -+ *is_valid = (gfs2_check_meta(*bh, GFS2_METATYPE_IN) == 0); -+ if (!(*is_valid)) { -+ log_err( _("Journal at block %lld (0x%llx) has a bad " -+ "indirect block pointer %lld (0x%llx) " -+ "(points to something that is not an " -+ "indirect block).\n"), -+ (unsigned long long)ip->i_di.di_num.no_addr, -+ (unsigned long long)ip->i_di.di_num.no_addr, -+ (unsigned long long)block, -+ (unsigned long long)block); -+ brelse(*bh); -+ return meta_skip_further; -+ } -+ } -+ return rc; -+} -+ -+static int rangecheck_jdata(struct gfs2_inode *ip, uint64_t metablock, -+ uint64_t block, void *private) -+{ -+ return rangecheck_jblock(ip, block); -+} -+ -+struct metawalk_fxns rangecheck_journal = { -+ .private = NULL, -+ .invalid_meta_is_fatal = 1, -+ .check_metalist = rangecheck_jmeta, -+ .check_data = rangecheck_jdata, -+}; -+ - /* - * replay_journals - replay the journals - * sdp: the super block -@@ -583,9 +641,39 @@ int replay_journals(struct gfs2_sbd *sdp, int preen, int force_check, - sdp->jsize = GFS2_DEFAULT_JSIZE; - - for(i = 0; i < sdp->md.journals; i++) { -+ if (sdp->md.journal[i]) { -+ struct rgrp_tree rgd; -+ struct gfs2_bitmap bits; -+ -+ /* The real rgrp tree hasn't been built at this point, -+ * so we need to dummy one up that covers the whole -+ * file system so basic functions in check_metatree -+ * don't segfault. */ -+ rgd.start = sdp->sb_addr + 1; -+ rgd.length = 1; -+ rgd.bh = NULL; -+ bits.bi_start = 0; -+ bits.bi_len = sdp->fssize / GFS2_NBBY; -+ rgd.bits = &bits; -+ rgd.ri.ri_addr = sdp->sb_addr + 1; -+ rgd.ri.ri_length = 1; -+ rgd.ri.ri_data0 = sdp->sb_addr + 2; -+ rgd.ri.ri_data = sdp->fssize - (sdp->sb_addr + 2); -+ -+ sdp->rgtree.osi_node = (struct osi_node *)&rgd; -+ error = check_metatree(sdp->md.journal[i], -+ &rangecheck_journal); -+ sdp->rgtree.osi_node = NULL; -+ if (error) -+ /* Don't use fsck_inode_put here because it's a -+ system file and we need to dismantle it. */ -+ inode_put(&sdp->md.journal[i]); -+ error = 0; /* bad journal is non-fatal */ -+ } - if (!sdp->md.journal[i]) { - log_err(_("File system journal \"journal%d\" is " -- "missing: pass1 will try to recreate it.\n"), -+ "missing or corrupt: pass1 will try to " -+ "recreate it.\n"), - i); - continue; - } -diff --git a/gfs2/fsck/metawalk.c b/gfs2/fsck/metawalk.c -index 22f3334..b8cef87 100644 ---- a/gfs2/fsck/metawalk.c -+++ b/gfs2/fsck/metawalk.c -@@ -1238,9 +1238,12 @@ static int build_and_check_metalist(struct gfs2_inode *ip, osi_list_t *mlp, - for (tmp = prev_list->next; tmp != prev_list; tmp = tmp->next){ - bh = osi_list_entry(tmp, struct gfs2_buffer_head, - b_altlist); -+ if (gfs2_check_meta(bh, iblk_type)) { -+ if (pass->invalid_meta_is_fatal) -+ return meta_error; - -- if (gfs2_check_meta(bh, iblk_type)) - continue; -+ } - - /* Now check the metadata itself */ - for (ptr = (uint64_t *)(bh->b_data + head_size); -@@ -1286,6 +1289,9 @@ static int build_and_check_metalist(struct gfs2_inode *ip, osi_list_t *mlp, - "%llu (0x%llx)\n"), - (unsigned long long)block, - (unsigned long long)block); -+ if (pass->invalid_meta_is_fatal) -+ return meta_error; -+ - continue; - } - if (was_duplicate) { -@@ -1300,6 +1306,9 @@ static int build_and_check_metalist(struct gfs2_inode *ip, osi_list_t *mlp, - "%lld (0x%llx)\n"), - (unsigned long long)block, - (unsigned long long)block); -+ if (pass->invalid_meta_is_fatal) -+ return meta_error; -+ - continue; - } - if (!nbh) -diff --git a/gfs2/fsck/metawalk.h b/gfs2/fsck/metawalk.h -index a5a51c2..5e30bfe 100644 ---- a/gfs2/fsck/metawalk.h -+++ b/gfs2/fsck/metawalk.h -@@ -93,6 +93,7 @@ enum meta_check_rc { - */ - struct metawalk_fxns { - void *private; -+ int invalid_meta_is_fatal; - int (*check_leaf_depth) (struct gfs2_inode *ip, uint64_t leaf_no, - int ref_count, struct gfs2_buffer_head *lbh); - int (*check_leaf) (struct gfs2_inode *ip, uint64_t block, -diff --git a/gfs2/fsck/util.c b/gfs2/fsck/util.c -index a701d82..408d89a 100644 ---- a/gfs2/fsck/util.c -+++ b/gfs2/fsck/util.c -@@ -579,6 +579,8 @@ int gfs2_blockmap_set(struct gfs2_bmap *bmap, uint64_t bblock, - static unsigned char *byte; - static uint64_t b; - -+ if (!bmap) -+ return 0; - if (bblock > bmap->size) - return -1; - diff --git a/SOURCES/bz991204-1-gfs2_grow_Don_t_try_to_open_an_empty_string.patch b/SOURCES/bz991204-1-gfs2_grow_Don_t_try_to_open_an_empty_string.patch deleted file mode 100644 index dc5e4de..0000000 --- a/SOURCES/bz991204-1-gfs2_grow_Don_t_try_to_open_an_empty_string.patch +++ /dev/null @@ -1,185 +0,0 @@ -commit 43da4b0b6a55cfad8f78a703fb3359cac0c4968a -Author: Andrew Price -Date: Thu Aug 8 17:50:47 2013 +0100 - - gfs2_grow: Don't try to open an empty string - - sdp->device_name wasn't getting set in gfs2_grow so is_gfs2() (called - via check_for_gfs2()) fails to open "" and so we get an ENOENT. - - This fixes the open("") by setting sdp->device_name before passing it to - is_pathname_mounted(), which has been updated to make it more clear - which args will be modified by it. - - is_gfs2() and check_for_gfs2() have also been removed from libgfs2 as - these were the only places they were being called and they aren't - needed: superblock checking is done further along via other functions - calling check_sb(). - - Resolves: rhbz#991204 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/fsck/initialize.c b/gfs2/fsck/initialize.c -index b45ae08..6612fe7 100644 ---- a/gfs2/fsck/initialize.c -+++ b/gfs2/fsck/initialize.c -@@ -1491,7 +1491,7 @@ int initialize(struct gfs2_sbd *sdp, int force_check, int preen, - strncpy(sdp->device_name, opts.device, - sizeof(sdp->device_name)); - sdp->path_name = sdp->device_name; /* This gets overwritten */ -- is_mounted = is_pathname_mounted(sdp, &ro); -+ is_mounted = is_pathname_mounted(sdp->path_name, sdp->device_name, &ro); - /* If the device is busy, but not because it's mounted, fail. - This protects against cases where the file system is LVM - and perhaps mounted on a different node. */ -diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h -index fe7129a..e994d3b 100644 ---- a/gfs2/libgfs2/libgfs2.h -+++ b/gfs2/libgfs2/libgfs2.h -@@ -716,11 +716,9 @@ extern void decrease_verbosity(void); - extern int compute_heightsize(struct gfs2_sbd *sdp, uint64_t *heightsize, - uint32_t *maxheight, uint32_t bsize1, int diptrs, int inptrs); - extern int compute_constants(struct gfs2_sbd *sdp); --extern int is_pathname_mounted(struct gfs2_sbd *sdp, int *ro_mount); --extern int is_gfs2(struct gfs2_sbd *sdp); -+extern int is_pathname_mounted(char *path_name, char *device_name, int *ro_mount); - extern int find_gfs2_meta(struct gfs2_sbd *sdp); - extern int dir_exists(const char *dir); --extern int check_for_gfs2(struct gfs2_sbd *sdp); - extern int mount_gfs2_meta(struct gfs2_sbd *sdp); - extern void cleanup_metafs(struct gfs2_sbd *sdp); - extern int set_sysfs(const char *fsname, const char *filename, const char *val); -diff --git a/gfs2/libgfs2/misc.c b/gfs2/libgfs2/misc.c -index c05a770..6f2dbdb 100644 ---- a/gfs2/libgfs2/misc.c -+++ b/gfs2/libgfs2/misc.c -@@ -99,7 +99,7 @@ int compute_constants(struct gfs2_sbd *sdp) - return 0; - } - --int is_pathname_mounted(struct gfs2_sbd *sdp, int *ro_mount) -+int is_pathname_mounted(char *path_name, char *device_name, int *ro_mount) - { - FILE *fp; - struct mntent *mnt; -@@ -112,7 +112,7 @@ int is_pathname_mounted(struct gfs2_sbd *sdp, int *ro_mount) - perror("open: /proc/mounts"); - return 0; - } -- if (stat(sdp->path_name, &st_buf) == 0) { -+ if (stat(path_name, &st_buf) == 0) { - if (S_ISBLK(st_buf.st_mode)) { - #ifndef __GNU__ /* The GNU hurd is broken with respect to stat devices */ - file_rdev = st_buf.st_rdev; -@@ -124,12 +124,12 @@ int is_pathname_mounted(struct gfs2_sbd *sdp, int *ro_mount) - } - while ((mnt = getmntent (fp)) != NULL) { - /* Check if they specified the device instead of mnt point */ -- if (strcmp(sdp->device_name, mnt->mnt_fsname) == 0) { -- strcpy(sdp->path_name, mnt->mnt_dir); /* fix it */ -+ if (strcmp(device_name, mnt->mnt_fsname) == 0) { -+ strcpy(path_name, mnt->mnt_dir); /* fix it */ - break; - } -- if (strcmp(sdp->path_name, mnt->mnt_dir) == 0) { -- strcpy(sdp->device_name, mnt->mnt_fsname); /* fix it */ -+ if (strcmp(path_name, mnt->mnt_dir) == 0) { -+ strcpy(device_name, mnt->mnt_fsname); /* fix it */ - break; - } - if (stat(mnt->mnt_fsname, &st_buf) == 0) { -@@ -160,36 +160,6 @@ int is_pathname_mounted(struct gfs2_sbd *sdp, int *ro_mount) - return 1; /* mounted */ - } - --int is_gfs2(struct gfs2_sbd *sdp) --{ -- int fd, rc; -- struct gfs2_sb sb; -- -- fd = open(sdp->device_name, O_RDWR); -- if (fd < 0) -- return 0; -- -- rc = 0; -- if (lseek(fd, GFS2_SB_ADDR * GFS2_BASIC_BLOCK, SEEK_SET) >= 0 && -- read(fd, &sb, sizeof(sb)) == sizeof(sb) && -- be32_to_cpu(sb.sb_header.mh_magic) == GFS2_MAGIC && -- be32_to_cpu(sb.sb_header.mh_type) == GFS2_METATYPE_SB) -- rc = 1; -- close(fd); -- return rc; --} -- --int check_for_gfs2(struct gfs2_sbd *sdp) --{ -- int ro; -- -- if (!is_pathname_mounted(sdp, &ro)) -- return -1; -- if (!is_gfs2(sdp)) -- return -1; -- return 0; --} -- - static int lock_for_admin(struct gfs2_sbd *sdp) - { - int error; -diff --git a/gfs2/mkfs/main_grow.c b/gfs2/mkfs/main_grow.c -index 73c7f84..d324af9 100644 ---- a/gfs2/mkfs/main_grow.c -+++ b/gfs2/mkfs/main_grow.c -@@ -323,6 +323,7 @@ main_grow(int argc, char *argv[]) - int rgcount, rindex_fd; - char rindex_name[PATH_MAX]; - int error = EXIT_SUCCESS; -+ int ro_mnt = 0; - - memset(sdp, 0, sizeof(struct gfs2_sbd)); - sdp->bsize = GFS2_DEFAULT_BSIZE; -@@ -336,17 +337,20 @@ main_grow(int argc, char *argv[]) - int sane; - struct rgrp_tree *last_rgrp; - -+ strncpy(sdp->device_name, argv[optind], PATH_MAX - 1); - sdp->path_name = argv[optind++]; -- sdp->path_fd = open(sdp->path_name, O_RDONLY | O_CLOEXEC); -- if (sdp->path_fd < 0){ -+ -+ if ((!is_pathname_mounted(sdp->path_name, sdp->device_name, &ro_mnt))) { - perror(sdp->path_name); - exit(EXIT_FAILURE); - } - -- if (check_for_gfs2(sdp)) { -+ sdp->path_fd = open(sdp->path_name, O_RDONLY | O_CLOEXEC); -+ if (sdp->path_fd < 0){ - perror(sdp->path_name); - exit(EXIT_FAILURE); - } -+ - sdp->device_fd = open(sdp->device_name, - (test ? O_RDONLY : O_RDWR) | O_CLOEXEC); - if (sdp->device_fd < 0){ -diff --git a/gfs2/mkfs/main_jadd.c b/gfs2/mkfs/main_jadd.c -index 58fb046..2646829 100644 ---- a/gfs2/mkfs/main_jadd.c -+++ b/gfs2/mkfs/main_jadd.c -@@ -491,6 +491,7 @@ void main_jadd(int argc, char *argv[]) - { - struct gfs2_sbd sbd, *sdp = &sbd; - unsigned int total; -+ int ro_mnt = 0; - - memset(sdp, 0, sizeof(struct gfs2_sbd)); - sdp->jsize = GFS2_DEFAULT_JSIZE; -@@ -506,7 +507,7 @@ void main_jadd(int argc, char *argv[]) - exit(EXIT_FAILURE); - } - -- if (check_for_gfs2(sdp)) { -+ if (!is_pathname_mounted(sdp->path_name, sdp->device_name, &ro_mnt)) { - perror(sdp->path_name); - exit(EXIT_FAILURE); - } diff --git a/SOURCES/bz991204-2-libgfs2_Add_lgfs2_open_mnt_functions.patch b/SOURCES/bz991204-2-libgfs2_Add_lgfs2_open_mnt_functions.patch deleted file mode 100644 index eff8974..0000000 --- a/SOURCES/bz991204-2-libgfs2_Add_lgfs2_open_mnt_functions.patch +++ /dev/null @@ -1,143 +0,0 @@ -commit 3c8db52fe77267109a6f01c178370747a23e64fd -Author: Andrew Price -Date: Sat Nov 16 02:10:52 2013 -0600 - - libgfs2: Add lgfs2_open_mnt* functions - - lgfs2_open_mnt is a replacement for is_pathname_mounted which tries to reduce - races by opening paths speculatively and passing back the open fds once they're - known to be correct. lgfs2_open_mnt_{dev,dir} build on this to provide a - convenient way to open just the device or mount directory relating to a path - which could be either. - - Resolves: bz#991204 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h -index f864a08..3e5d09c 100644 ---- a/gfs2/libgfs2/libgfs2.h -+++ b/gfs2/libgfs2/libgfs2.h -@@ -12,6 +12,7 @@ - #include - #include - #include -+#include - - #include - #include "osi_list.h" -@@ -715,6 +716,9 @@ extern int compute_heightsize(struct gfs2_sbd *sdp, uint64_t *heightsize, - uint32_t *maxheight, uint32_t bsize1, int diptrs, int inptrs); - extern int compute_constants(struct gfs2_sbd *sdp); - extern int is_pathname_mounted(char *path_name, char *device_name, int *ro_mount); -+extern int lgfs2_open_mnt(const char *path, int dirflags, int *dirfd, int devflags, int *devfd, struct mntent **mnt); -+extern int lgfs2_open_mnt_dev(const char *path, int flags, struct mntent **mnt); -+extern int lgfs2_open_mnt_dir(const char *path, int flags, struct mntent **mnt); - extern int find_gfs2_meta(struct gfs2_sbd *sdp); - extern int dir_exists(const char *dir); - extern int mount_gfs2_meta(struct gfs2_sbd *sdp); -diff --git a/gfs2/libgfs2/misc.c b/gfs2/libgfs2/misc.c -index 7f500e6..195b983 100644 ---- a/gfs2/libgfs2/misc.c -+++ b/gfs2/libgfs2/misc.c -@@ -163,6 +163,100 @@ int is_pathname_mounted(char *path_name, char *device_name, int *ro_mount) - return 1; /* mounted */ - } - -+/* Returns 0 if fd1 and fd2 refer to the same device/file, 1 otherwise, or -1 on error */ -+static int fdcmp(int fd1, int fd2) -+{ -+ struct stat st1, st2; -+ if ((fstat(fd1, &st1) != 0) || (fstat(fd2, &st2) != 0)) -+ return -1; -+ if (S_ISBLK(st1.st_mode) && S_ISBLK(st2.st_mode)) { -+ if (st1.st_rdev == st2.st_rdev) { -+ return 0; -+ } -+ } else if ((st1.st_dev == st2.st_dev) && (st1.st_ino == st2.st_ino)) { -+ return 0; -+ } -+ return 1; -+} -+ -+int lgfs2_open_mnt(const char *path, int dirflags, int *dirfd, int devflags, int *devfd, struct mntent **mnt) -+{ -+ FILE *fp = setmntent("/proc/mounts", "r"); -+ if (fp == NULL) { -+ perror("open: /proc/mounts"); -+ return 1; -+ } -+ /* Assume path is mount point until we know better. */ -+ *dirfd = open(path, dirflags); -+ if (*dirfd < 0) -+ return 1; -+ -+ while ((*mnt = getmntent(fp)) != NULL) { -+ int fd; -+ if (strcmp((*mnt)->mnt_type, "gfs2") != 0) -+ continue; -+ *devfd = open((*mnt)->mnt_fsname, devflags); -+ /* Defer checking *devfd until later: whether it's ok to ignore -+ * the error depends on whether we find the mount point. */ -+ -+ if (strcmp(path, (*mnt)->mnt_dir) == 0) -+ break; -+ if (strcmp(path, (*mnt)->mnt_fsname) == 0 || fdcmp(*dirfd, *devfd) == 0) { -+ /* We have a match but our above assumption was -+ incorrect and *dirfd is actually the device. */ -+ close(*dirfd); -+ *dirfd = open((*mnt)->mnt_dir, dirflags); -+ break; -+ } -+ -+ fd = open((*mnt)->mnt_dir, dirflags); -+ if (fd >= 0) { -+ int diff = fdcmp(*dirfd, fd); -+ close(fd); -+ if (diff == 0) -+ break; -+ } -+ if (*devfd >= 0) -+ close(*devfd); -+ } -+ endmntent(fp); -+ if (*mnt == NULL) { -+ close(*dirfd); -+ return 0; /* Success. Answer is no. Both fds closed. */ -+ } -+ if (*dirfd < 0) { -+ close(*devfd); -+ return 1; -+ } -+ if (*devfd < 0) { -+ close(*dirfd); -+ return 1; -+ } -+ return 0; /* Success. Answer is yes. Both fds open. */ -+} -+ -+int lgfs2_open_mnt_dev(const char *path, int flags, struct mntent **mnt) -+{ -+ int dirfd = -1; -+ int devfd = -1; -+ if (lgfs2_open_mnt(path, O_RDONLY, &dirfd, flags, &devfd, mnt) != 0) -+ return -1; -+ if (*mnt != NULL) -+ close(dirfd); -+ return devfd; -+} -+ -+int lgfs2_open_mnt_dir(const char *path, int flags, struct mntent **mnt) -+{ -+ int dirfd = -1; -+ int devfd = -1; -+ if (lgfs2_open_mnt(path, flags, &dirfd, O_RDONLY, &devfd, mnt) != 0) -+ return -1; -+ if (*mnt != NULL) -+ close(devfd); -+ return dirfd; -+} -+ - static int lock_for_admin(struct gfs2_sbd *sdp) - { - int error; diff --git a/SOURCES/bz991204-3-Switch_is_pathname_mounted_callers_to_lgfs2_open_mnt.patch b/SOURCES/bz991204-3-Switch_is_pathname_mounted_callers_to_lgfs2_open_mnt.patch deleted file mode 100644 index 27209d1..0000000 --- a/SOURCES/bz991204-3-Switch_is_pathname_mounted_callers_to_lgfs2_open_mnt.patch +++ /dev/null @@ -1,170 +0,0 @@ -commit 63bd2eff2043c2d14399d5511e116ae0cdd8bba3 -Author: Andrew Price -Date: Sat Nov 16 02:19:07 2013 -0600 - - Switch is_pathname_mounted callers to lgfs2_open_mnt* - - Use the new lgfs2_open_mnt* functions in fsck.gfs2, gfs2_grow, and gfs2_jadd. - - Resolves: bz#991204 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/fsck/initialize.c b/gfs2/fsck/initialize.c -index 6612fe7..5758607 100644 ---- a/gfs2/fsck/initialize.c -+++ b/gfs2/fsck/initialize.c -@@ -1475,8 +1475,7 @@ int initialize(struct gfs2_sbd *sdp, int force_check, int preen, - - sdp->device_fd = open(opts.device, open_flag); - if (sdp->device_fd < 0) { -- int is_mounted, ro; -- -+ struct mntent *mnt; - if (open_flag == O_RDONLY || errno != EBUSY) { - log_crit( _("Unable to open device: %s\n"), - opts.device); -@@ -1485,30 +1484,23 @@ int initialize(struct gfs2_sbd *sdp, int force_check, int preen, - /* We can't open it EXCL. It may be already open rw (in which - case we want to deny them access) or it may be mounted as - the root file system at boot time (in which case we need to -- allow it.) We use is_pathname_mounted here even though -- we're specifying a device name, not a path name. The -- function checks for device as well. */ -- strncpy(sdp->device_name, opts.device, -- sizeof(sdp->device_name)); -- sdp->path_name = sdp->device_name; /* This gets overwritten */ -- is_mounted = is_pathname_mounted(sdp->path_name, sdp->device_name, &ro); -- /* If the device is busy, but not because it's mounted, fail. -+ allow it.) -+ If the device is busy, but not because it's mounted, fail. - This protects against cases where the file system is LVM -- and perhaps mounted on a different node. */ -- if (!is_mounted) -+ and perhaps mounted on a different node. -+ Try opening without O_EXCL. */ -+ sdp->device_fd = lgfs2_open_mnt_dev(opts.device, O_RDWR, &mnt); -+ if (sdp->device_fd < 0) - goto mount_fail; - /* If the device is mounted, but not mounted RO, fail. This - protects them against cases where the file system is - mounted RW, but still allows us to check our own root - file system. */ -- if (!ro) -- goto mount_fail; -+ if (!hasmntopt(mnt, MNTOPT_RO)) -+ goto close_fail; - /* The device is mounted RO, so it's likely our own root - file system. We can only do so much to protect the users -- from themselves. Try opening without O_EXCL. */ -- if ((sdp->device_fd = open(opts.device, O_RDWR)) < 0) -- goto mount_fail; -- -+ from themselves. */ - was_mounted_ro = 1; - } - -@@ -1591,6 +1583,8 @@ int initialize(struct gfs2_sbd *sdp, int force_check, int preen, - - return FSCK_OK; - -+close_fail: -+ close(sdp->device_fd); - mount_fail: - log_crit( _("Device %s is busy.\n"), opts.device); - return FSCK_USAGE; -diff --git a/gfs2/mkfs/main_grow.c b/gfs2/mkfs/main_grow.c -index 5db91d9..541b0f2 100644 ---- a/gfs2/mkfs/main_grow.c -+++ b/gfs2/mkfs/main_grow.c -@@ -323,7 +323,7 @@ main_grow(int argc, char *argv[]) - int rgcount, rindex_fd; - char rindex_name[PATH_MAX]; - int error = EXIT_SUCCESS; -- int ro_mnt = 0; -+ int devflags = (test ? O_RDONLY : O_RDWR) | O_CLOEXEC; - - memset(sdp, 0, sizeof(struct gfs2_sbd)); - sdp->bsize = GFS2_DEFAULT_BSIZE; -@@ -333,30 +333,23 @@ main_grow(int argc, char *argv[]) - sdp->md.journals = 1; - decode_arguments(argc, argv, sdp); - -- while ((argc - optind) > 0) { -+ for(; (argc - optind) > 0; optind++) { - int sane; -+ struct mntent *mnt; - struct rgrp_tree *last_rgrp; - -- strncpy(sdp->device_name, argv[optind], PATH_MAX - 1); -- sdp->path_name = argv[optind++]; -- -- if ((!is_pathname_mounted(sdp->path_name, sdp->device_name, &ro_mnt))) { -- perror(sdp->path_name); -- exit(EXIT_FAILURE); -- } -- -- sdp->path_fd = open(sdp->path_name, O_RDONLY | O_CLOEXEC); -- if (sdp->path_fd < 0){ -- perror(sdp->path_name); -+ error = lgfs2_open_mnt(argv[optind], O_RDONLY|O_CLOEXEC, &sdp->path_fd, -+ devflags, &sdp->device_fd, &mnt); -+ if (error != 0) { -+ fprintf(stderr, _("Error looking up mount '%s': %s\n"), argv[optind], strerror(errno)); - exit(EXIT_FAILURE); - } -- -- sdp->device_fd = open(sdp->device_name, -- (test ? O_RDONLY : O_RDWR) | O_CLOEXEC); -- if (sdp->device_fd < 0){ -- perror(sdp->device_name); -- exit(EXIT_FAILURE); -+ if (mnt == NULL) { -+ fprintf(stderr, _("%s: not a mounted gfs2 file system\n"), argv[optind]); -+ continue; - } -+ sdp->path_name = mnt->mnt_dir; -+ strncpy(sdp->device_name, mnt->mnt_fsname, PATH_MAX - 1); - - if (lgfs2_get_dev_info(sdp->device_fd, &sdp->dinfo) < 0) { - perror(sdp->device_name); -diff --git a/gfs2/mkfs/main_jadd.c b/gfs2/mkfs/main_jadd.c -index b6cd8e4..815dd52 100644 ---- a/gfs2/mkfs/main_jadd.c -+++ b/gfs2/mkfs/main_jadd.c -@@ -490,8 +490,8 @@ add_j(struct gfs2_sbd *sdp) - void main_jadd(int argc, char *argv[]) - { - struct gfs2_sbd sbd, *sdp = &sbd; -+ struct mntent *mnt; - unsigned int total; -- int ro_mnt = 0; - - memset(sdp, 0, sizeof(struct gfs2_sbd)); - sdp->jsize = GFS2_DEFAULT_JSIZE; -@@ -500,17 +500,18 @@ void main_jadd(int argc, char *argv[]) - - decode_arguments(argc, argv, sdp); - verify_arguments(sdp); -- -- sdp->path_fd = open(sdp->path_name, O_RDONLY | O_CLOEXEC); -- if (sdp->path_fd < 0){ -- perror(sdp->path_name); -+ -+ sbd.path_fd = lgfs2_open_mnt_dir(sbd.path_name, O_RDONLY|O_CLOEXEC, &mnt); -+ if (sbd.path_fd < 0) { -+ fprintf(stderr, _("Error looking up mount '%s': %s\n"), sbd.path_name, strerror(errno)); - exit(EXIT_FAILURE); - } -- -- if (!is_pathname_mounted(sdp->path_name, sdp->device_name, &ro_mnt)) { -- perror(sdp->path_name); -+ if (mnt == NULL) { -+ fprintf(stderr, _("%s: not a mounted gfs2 file system\n"), sbd.path_name); - exit(EXIT_FAILURE); - } -+ sbd.path_name = mnt->mnt_dir; -+ strncpy(sbd.device_name, mnt->mnt_fsname, PATH_MAX - 1); - - gather_info(sdp); - diff --git a/SOURCES/bz991204-4-libgfs2_Remove_is_pathname_mounted.patch b/SOURCES/bz991204-4-libgfs2_Remove_is_pathname_mounted.patch deleted file mode 100644 index e703721..0000000 --- a/SOURCES/bz991204-4-libgfs2_Remove_is_pathname_mounted.patch +++ /dev/null @@ -1,96 +0,0 @@ -commit 0d5b21adc867da3c738474ec2bcd1cfa625f8bb6 -Author: Andrew Price -Date: Sat Nov 16 02:21:36 2013 -0600 - - libgfs2: Remove is_pathname_mounted - - All callers are now using lgfs2_open_mnt* instead. - - Resolves: bz#991204 - - Signed-off-by: Andrew Price - -diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h -index 3e5d09c..e785017 100644 ---- a/gfs2/libgfs2/libgfs2.h -+++ b/gfs2/libgfs2/libgfs2.h -@@ -715,7 +715,6 @@ extern int metafs_interrupted; - extern int compute_heightsize(struct gfs2_sbd *sdp, uint64_t *heightsize, - uint32_t *maxheight, uint32_t bsize1, int diptrs, int inptrs); - extern int compute_constants(struct gfs2_sbd *sdp); --extern int is_pathname_mounted(char *path_name, char *device_name, int *ro_mount); - extern int lgfs2_open_mnt(const char *path, int dirflags, int *dirfd, int devflags, int *devfd, struct mntent **mnt); - extern int lgfs2_open_mnt_dev(const char *path, int flags, struct mntent **mnt); - extern int lgfs2_open_mnt_dir(const char *path, int flags, struct mntent **mnt); -diff --git a/gfs2/libgfs2/misc.c b/gfs2/libgfs2/misc.c -index 195b983..c4ed722 100644 ---- a/gfs2/libgfs2/misc.c -+++ b/gfs2/libgfs2/misc.c -@@ -102,67 +102,6 @@ int compute_constants(struct gfs2_sbd *sdp) - return 0; - } - --int is_pathname_mounted(char *path_name, char *device_name, int *ro_mount) --{ -- FILE *fp; -- struct mntent *mnt; -- dev_t file_dev=0, file_rdev=0; -- ino_t file_ino=0; -- struct stat st_buf; -- -- *ro_mount = 0; -- if ((fp = setmntent("/proc/mounts", "r")) == NULL) { -- perror("open: /proc/mounts"); -- return 0; -- } -- if (stat(path_name, &st_buf) == 0) { -- if (S_ISBLK(st_buf.st_mode)) { --#ifndef __GNU__ /* The GNU hurd is broken with respect to stat devices */ -- file_rdev = st_buf.st_rdev; --#endif /* __GNU__ */ -- } else { -- file_dev = st_buf.st_dev; -- file_ino = st_buf.st_ino; -- } -- } -- while ((mnt = getmntent (fp)) != NULL) { -- /* Check if they specified the device instead of mnt point */ -- if (strcmp(device_name, mnt->mnt_fsname) == 0) { -- strcpy(path_name, mnt->mnt_dir); /* fix it */ -- break; -- } -- if (strcmp(path_name, mnt->mnt_dir) == 0) { -- strcpy(device_name, mnt->mnt_fsname); /* fix it */ -- break; -- } -- if (stat(mnt->mnt_fsname, &st_buf) == 0) { -- if (S_ISBLK(st_buf.st_mode)) { --#ifndef __GNU__ -- if (file_rdev && (file_rdev == st_buf.st_rdev)) -- break; --#endif /* __GNU__ */ -- } else { -- if (file_dev && ((file_dev == st_buf.st_dev) && -- (file_ino == st_buf.st_ino))) -- break; -- } -- } -- } -- endmntent (fp); -- if (mnt == NULL) -- return 0; -- if (stat(mnt->mnt_dir, &st_buf) < 0) { -- if (errno == ENOENT) -- return 0; -- } -- /* Can't trust fstype because / has "rootfs". */ -- if (file_rdev && (st_buf.st_dev != file_rdev)) -- return 0; -- if (hasmntopt(mnt, MNTOPT_RO)) -- *ro_mount = 1; -- return 1; /* mounted */ --} -- - /* Returns 0 if fd1 and fd2 refer to the same device/file, 1 otherwise, or -1 on error */ - static int fdcmp(int fd1, int fd2) - { diff --git a/SOURCES/bz996236-gfs2_tool_catch_interrupts_while_the_metafs_is_mounted.patch b/SOURCES/bz996236-gfs2_tool_catch_interrupts_while_the_metafs_is_mounted.patch deleted file mode 100644 index f1163f1..0000000 --- a/SOURCES/bz996236-gfs2_tool_catch_interrupts_while_the_metafs_is_mounted.patch +++ /dev/null @@ -1,184 +0,0 @@ -commit 12604ad33b41eca2b7c6511da8d519a299787ef5 -Author: Bob Peterson -Date: Mon Aug 12 15:08:55 2013 -0500 - - gfs2_tool: catch interrupts while the metafs is mounted - - This patch catches interrupt signals while the metafs is mounted, - and if interrupted, sets a flag. Later, if the caller sees the flag, - they will unmount the metafs. That way, the metafs is never left - mounted by accident if a gfs2_grow or gfs2_jadd is interrupted or - killed. - -diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h -index e994d3b..dd7420b 100644 ---- a/gfs2/libgfs2/libgfs2.h -+++ b/gfs2/libgfs2/libgfs2.h -@@ -713,6 +713,8 @@ extern void increase_verbosity(void); - extern void decrease_verbosity(void); - /* misc.c */ - -+extern int metafs_interrupted; -+ - extern int compute_heightsize(struct gfs2_sbd *sdp, uint64_t *heightsize, - uint32_t *maxheight, uint32_t bsize1, int diptrs, int inptrs); - extern int compute_constants(struct gfs2_sbd *sdp); -diff --git a/gfs2/libgfs2/misc.c b/gfs2/libgfs2/misc.c -index 6f2dbdb..7f500e6 100644 ---- a/gfs2/libgfs2/misc.c -+++ b/gfs2/libgfs2/misc.c -@@ -18,6 +18,7 @@ - #include - #include - #include -+#include - - #include "libgfs2.h" - -@@ -25,6 +26,8 @@ - #define SYS_BASE "/sys/fs/gfs2" /* FIXME: Look in /proc/mounts to find this */ - #define DIV_RU(x, y) (((x) + (y) - 1) / (y)) - -+int metafs_interrupted = 0; -+ - int compute_heightsize(struct gfs2_sbd *sdp, uint64_t *heightsize, - uint32_t *maxheight, uint32_t bsize1, int diptrs, int inptrs) - { -@@ -179,10 +182,15 @@ static int lock_for_admin(struct gfs2_sbd *sdp) - return 0; - } - -+static void sighandler(int error) -+{ -+ metafs_interrupted = 1; -+} - - int mount_gfs2_meta(struct gfs2_sbd *sdp) - { - int ret; -+ struct sigaction sa = { .sa_handler = &sighandler }; - - memset(sdp->metafs_path, 0, PATH_MAX); - snprintf(sdp->metafs_path, PATH_MAX - 1, "/tmp/.gfs2meta.XXXXXX"); -@@ -190,6 +198,15 @@ int mount_gfs2_meta(struct gfs2_sbd *sdp) - if(!mkdtemp(sdp->metafs_path)) - return -1; - -+ sigaction(SIGINT, &sa, NULL); -+ sigaction(SIGILL, &sa, NULL); -+ sigaction(SIGTERM, &sa, NULL); -+ sigaction(SIGHUP, &sa, NULL); -+ sigaction(SIGABRT, &sa, NULL); -+ sigaction(SIGSEGV, &sa, NULL); -+ sigaction(SIGCONT, &sa, NULL); -+ sigaction(SIGUSR1, &sa, NULL); -+ sigaction(SIGUSR2, &sa, NULL); - ret = mount(sdp->path_name, sdp->metafs_path, "gfs2meta", 0, NULL); - if (ret) { - rmdir(sdp->metafs_path); -@@ -203,6 +220,7 @@ int mount_gfs2_meta(struct gfs2_sbd *sdp) - void cleanup_metafs(struct gfs2_sbd *sdp) - { - int ret; -+ struct sigaction sa = { .sa_handler = SIG_DFL }; - - if (sdp->metafs_fd <= 0) - return; -@@ -215,6 +233,16 @@ void cleanup_metafs(struct gfs2_sbd *sdp) - sdp->metafs_path, strerror(errno)); - else - rmdir(sdp->metafs_path); -+ sigaction(SIGINT, &sa, NULL); -+ sigaction(SIGILL, &sa, NULL); -+ sigaction(SIGTERM, &sa, NULL); -+ sigaction(SIGHUP, &sa, NULL); -+ sigaction(SIGABRT, &sa, NULL); -+ sigaction(SIGSEGV, &sa, NULL); -+ sigaction(SIGCONT, &sa, NULL); -+ sigaction(SIGUSR1, &sa, NULL); -+ sigaction(SIGUSR2, &sa, NULL); -+ metafs_interrupted = 0; - } - - int set_sysfs(const char *fsname, const char *filename, const char *val) -diff --git a/gfs2/mkfs/main_grow.c b/gfs2/mkfs/main_grow.c -index d324af9..5db91d9 100644 ---- a/gfs2/mkfs/main_grow.c -+++ b/gfs2/mkfs/main_grow.c -@@ -372,10 +372,13 @@ main_grow(int argc, char *argv[]) - perror(_("Bad constants (1)")); - exit(EXIT_FAILURE); - } -- if (read_sb(sdp) < 0) -- die( _("Error reading superblock.\n")); -+ if (read_sb(sdp) < 0) { -+ fprintf(stderr, _("Error reading superblock.\n")); -+ exit(EXIT_FAILURE); -+ } - if (sdp->gfs1) { -- die( _("cannot grow gfs1 filesystem\n")); -+ fprintf(stderr, _("cannot grow gfs1 filesystem\n")); -+ exit(EXIT_FAILURE); - } - fix_device_geometry(sdp); - if (mount_gfs2_meta(sdp)) { -@@ -387,7 +390,8 @@ main_grow(int argc, char *argv[]) - rindex_fd = open(rindex_name, (test ? O_RDONLY : O_RDWR) | O_CLOEXEC); - if (rindex_fd < 0) { - cleanup_metafs(sdp); -- die( _("GFS2 rindex not found. Please run fsck.gfs2.\n")); -+ perror(_("GFS2 rindex not found. Please run fsck.gfs2.\n")); -+ exit(EXIT_FAILURE); - } - /* Get master dinode */ - sdp->master_dir = lgfs2_inode_read(sdp, sdp->sd_sb.sb_master_dir.no_addr); -@@ -402,6 +406,8 @@ main_grow(int argc, char *argv[]) - /* we're only going to write out new RG information after */ - /* the existing RGs, and only write to the index at EOF. */ - ri_update(sdp, rindex_fd, &rgcount, &sane); -+ if (metafs_interrupted) -+ goto out; - fssize = filesystem_size(sdp); - if (!sdp->rgtree.osi_node) { - log_err(_("Error: No resource groups found.\n")); -@@ -424,10 +430,16 @@ main_grow(int argc, char *argv[]) - } else { - int old_rg_count; - -+ if (metafs_interrupted) -+ goto out; - compute_rgrp_layout(sdp, &sdp->rgtree, TRUE); -+ if (metafs_interrupted) -+ goto out; - debug_print_rgrps(sdp, &sdp->rgtree); - print_info(sdp); - initialize_new_portion(sdp, &old_rg_count); -+ if (metafs_interrupted) -+ goto out; - fix_rindex(sdp, rindex_fd, old_rg_count); - } - out: -@@ -439,6 +451,7 @@ main_grow(int argc, char *argv[]) - } - close(sdp->path_fd); - sync(); -- log_notice( _("gfs2_grow complete.\n")); -+ if (!metafs_interrupted) -+ log_notice( _("gfs2_grow complete.\n")); - exit(error); - } -diff --git a/gfs2/mkfs/main_jadd.c b/gfs2/mkfs/main_jadd.c -index 2646829..b6cd8e4 100644 ---- a/gfs2/mkfs/main_jadd.c -+++ b/gfs2/mkfs/main_jadd.c -@@ -529,6 +529,10 @@ void main_jadd(int argc, char *argv[]) - for (sdp->md.journals = sdp->orig_journals; - sdp->md.journals < total; - sdp->md.journals++) { -+ if (metafs_interrupted) { -+ cleanup_metafs(&sbd); -+ exit(130); -+ } - add_ir(sdp); - add_sc(sdp); - add_qc(sdp); diff --git a/SPECS/gfs2-utils.spec b/SPECS/gfs2-utils.spec index 94fe6ee..564f879 100644 --- a/SPECS/gfs2-utils.spec +++ b/SPECS/gfs2-utils.spec @@ -11,8 +11,8 @@ ############################################################################### Name: gfs2-utils -Version: 3.1.6 -Release: 13%{?dist} +Version: 3.1.7 +Release: 6%{?dist} License: GPLv2+ and LGPLv2+ Group: System Environment/Kernel Summary: Utilities for managing the global file system (GFS2) @@ -31,6 +31,10 @@ BuildRequires: libblkid-devel BuildRequires: check-devel URL: https://fedorahosted.org/cluster/wiki/HomePage +%if 0%{?rhel} > 0 +ExclusiveArch: x86_64 s390x +%endif + # The source for this package was pulled from the upstream git tree. # Use the following commands to generate the tarball: # git clone git://git.fedorahosted.org/gfs2-utils.git @@ -38,47 +42,31 @@ URL: https://fedorahosted.org/cluster/wiki/HomePage # ./make-tarball.sh # Source0: https://fedorahosted.org/released/gfs2-utils/gfs2-utils-%{version}.tar.gz -Patch0: bz990683-fsck_gfs2_Add_ability_to_detect_journal_inode_indirect_block_corruption.patch -Patch1: bz991204-1-gfs2_grow_Don_t_try_to_open_an_empty_string.patch -Patch2: bz1000066-gfs2_utils_tests_Switch_to_autotest.patch -Patch3: bz1001583-1-fsck_gfs2_Allocate_enough_space_for_the_block_map.patch -Patch4: bz1001583-2-libgfs2_Move_the_BLOCKMAP_macros_into_fsck_gfs2.patch -Patch5: bz996236-gfs2_tool_catch_interrupts_while_the_metafs_is_mounted.patch -Patch6: bz1003059-fsck_gfs2_Check_and_repair_per_node_contents_such_as_quota_changeX.patch -Patch7: bz1028388-1-libgfs2_Add_sd_heightsize_bounds_checking_in_read_sb.patch -Patch8: bz1028388-2-fsck_gfs2_Fix_block_size_validation.patch -Patch9: bz1028388-3-gfs2l_Build_with_D_FILE_OFFSET_BITS_64.patch -Patch10: bz991204-2-libgfs2_Add_lgfs2_open_mnt_functions.patch -Patch11: bz991204-3-Switch_is_pathname_mounted_callers_to_lgfs2_open_mnt.patch -Patch12: bz991204-4-libgfs2_Remove_is_pathname_mounted.patch -Patch13: bz1059443-1-gfs2_edit_Convert_fssize_to_bytes_before_reporting_fs_size.patch -Patch14: bz1059443-2-mkfs_gfs2_tests_Enable_debug_output.patch -Patch15: bz1063842-1-libgfs2_Superblock_building_and_writing_improvements.patch -Patch16: bz1063842-2-gfs2_utils_Ensure_sb_uuid_uses_are_guarded.patch -Patch17: bz1063842-3-libgfs2_Add_support_for_new_leaf_hint_fields.patch +Patch0: bz1112342-1-gfs2_utils_tests_Build_unit_tests_with_consistent_cpp_flags.patch +Patch1: bz1112342-2-gfs2_utils_tests_Fix_unit_tests_for_RHEL7.patch +Patch2: bz1154786-fsck_gfs2_Improve_reporting_of_pass_timings.patch +Patch3: bz1146160-fsck_gfs2_Detect_and_correct_corrupt_journals.patch +Patch4: bz1162817-mkfs_gfs2_Revert_default_resource_group_size.patch +Patch5: bz1178604-1-fsck_gfs2_fix_broken_i_goal_values_in_inodes.patch +Patch6: bz1178604-2-gfs2_convert_use_correct_i_goal_values_instead_of_zeros_for_inodes.patch +Patch7: bz1178604-3-tests_test_for_incorrect_inode_i_goal_values.patch +Patch8: bz1178604-4-fsck_gfs2_Reprocess_nodes_if_anything_changed_addendum_1_of_2.patch +Patch9: bz1178604-5-fsck_gfs2_addendum_to_fix_broken_i_goal_values_in_inodes_addendum_2_of_2.patch BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n) %prep -%setup -q -n gfs2-utils -%patch0 -p1 -b .bz990683-fsck_gfs2_Add_ability_to_detect_journal_inode_indirect_block_corruption -%patch1 -p1 -b .bz991204-1-gfs2_grow_Don_t_try_to_open_an_empty_string -%patch2 -p1 -b .bz1000066-gfs2_utils_tests_Switch_to_autotest.patch -%patch3 -p1 -b .bz1001583-1-fsck_gfs2_Allocate_enough_space_for_the_block_map.patch -%patch4 -p1 -b .bz1001583-2-libgfs2_Move_the_BLOCKMAP_macros_into_fsck_gfs2.patch -%patch5 -p1 -b .bz996236-gfs2_tool_catch_interrupts_while_the_metafs_is_mounted -%patch6 -p1 -b .bz1003059-fsck_gfs2_Check_and_repair_per_node_contents_such_as_quota_changeX -%patch7 -p1 -b .bz1028388-1-libgfs2_Add_sd_heightsize_bounds_checking_in_read_sb -%patch8 -p1 -b .bz1028388-2-fsck_gfs2_Fix_block_size_validation -%patch9 -p1 -b .bz1028388-3-gfs2l_Build_with_D_FILE_OFFSET_BITS_64 -%patch10 -p1 -b .bz991204-2-libgfs2_Add_lgfs2_open_mnt_functions -%patch11 -p1 -b .bz991204-3-Switch_is_pathname_mounted_callers_to_lgfs2_open_mnt -%patch12 -p1 -b .bz991204-4-libgfs2_Remove_is_pathname_mounted -%patch13 -p1 -b .bz1059443-1-gfs2_edit_Convert_fssize_to_bytes_before_reporting_fs_size -%patch14 -p1 -b .bz1059443-2-mkfs_gfs2_tests_Enable_debug_output -%patch15 -p1 -b .bz1063842-1-libgfs2_Superblock_building_and_writing_improvements -%patch16 -p1 -b .bz1063842-2-gfs2_utils_Ensure_sb_uuid_uses_are_guarded -%patch17 -p1 -b .bz1063842-3-libgfs2_Add_support_for_new_leaf_hint_fields +%setup -q -n gfs2-utils-%{version} +%patch0 -p1 -b .bz1112342-1-gfs2_utils_tests_Build_unit_tests_with_consistent_cpp_flags +%patch1 -p1 -b .bz1112342-2-gfs2_utils_tests_Fix_unit_tests_for_RHEL7 +%patch2 -p1 -b .bz1154786-fsck_gfs2_Improve_reporting_of_pass_timings +%patch3 -p1 -b .bz1146160-fsck_gfs2_Detect_and_correct_corrupt_journals +%patch4 -p1 -b .bz1162817-mkfs_gfs2_Revert_default_resource_group_size +%patch5 -p1 -b .bz1178604-1-fsck_gfs2_fix_broken_i_goal_values_in_inodes +%patch6 -p1 -b .bz1178604-2-gfs2_convert_use_correct_i_goal_values_instead_of_zeros_for_inodes +%patch7 -p1 -b .bz1178604-3-tests_test_for_incorrect_inode_i_goal_values +%patch8 -p1 -b .bz1178604-4-fsck_gfs2_Reprocess_nodes_if_anything_changed_addendum_1_of_2 +%patch9 -p1 -b .bz1178604-5-fsck_gfs2_addendum_to_fix_broken_i_goal_values_in_inodes_addendum_2_of_2 %build ./autogen.sh @@ -125,6 +113,42 @@ file systems. %{_mandir}/man5/* %changelog +* Thu Jan 15 2015 Andrew Price - 3.1.7-6 +- fsck.gfs2: fix broken i_goal values in inodes +- gfs2_convert: use correct i_goal values instead of zeros for inodes +- tests: test for incorrect inode i_goal values +- fsck.gfs2: Reprocess nodes if anything changed - addendum 1 of 2 +- fsck.gfs2: addendum to fix broken i_goal values in inodes - addendum 2 of 2 + Resolves: rhbz#1178604 + +* Thu Nov 20 2014 Andrew Price - 3.1.7-5 +- Update ExclusiveArch + Resolves: rhbz#1161936 + +* Tue Nov 18 2014 Andrew Price - 3.1.7-4 +- mkfs.gfs2: Revert default resource group size + Resolves: rhbz#1162817 +- Add ExclusiveArch + Resolves: rhbz#1161936 + +* Tue Nov 18 2014 Andrew Price - 3.1.7-3 +- fsck.gfs2: Detect and correct corrupt journals + Resolves: rhbz#1146160 + +* Mon Nov 17 2014 Andrew Price - 3.1.7-2 +- fsck.gfs2: Improve reporting of pass timings + Resolves: rhbz#1154786 + +* Mon Sep 08 2014 Andrew Price - 3.1.7-1 +- Rebase to new upstream version 3.1.7 +- gfs2-utils tests: Fix unit tests for RHEL7 +- gfs2-utils tests: Build unit tests with consistent cpp flags + Resolves: rhbz#1112342 + Resolves: rhbz#1017381 + Resolves: rhbz#1075135 + Resolves: rhbz#1079507 + Resolves: rhbz#1107238 + * Fri Mar 07 2014 Andrew Price - 3.1.6-13 - gfs2_edit: Convert fssize to bytes before reporting fs size - mkfs.gfs2 tests: Enable debug output