From d9593868cd58a5c843d871fe728deef166e91eee Mon Sep 17 00:00:00 2001 From: Andrew Price Date: Wed, 4 Nov 2020 16:29:15 +0000 Subject: [PATCH 1/7] Documentation: Update filesystems/gfs2.rst Remove an obsolete URL and generally bring the doc up-to-date Signed-off-by: Andrew Price Signed-off-by: Andreas Gruenbacher --- Documentation/filesystems/gfs2.rst | 37 +++++++++++++++--------------- 1 file changed, 18 insertions(+), 19 deletions(-) diff --git a/Documentation/filesystems/gfs2.rst b/Documentation/filesystems/gfs2.rst index 8d1ab589ce18..1bc48a13430c 100644 --- a/Documentation/filesystems/gfs2.rst +++ b/Documentation/filesystems/gfs2.rst @@ -1,53 +1,52 @@ .. SPDX-License-Identifier: GPL-2.0 -================== -Global File System -================== +==================== +Global File System 2 +==================== -https://fedorahosted.org/cluster/wiki/HomePage - -GFS is a cluster file system. It allows a cluster of computers to +GFS2 is a cluster file system. It allows a cluster of computers to simultaneously use a block device that is shared between them (with FC, -iSCSI, NBD, etc). GFS reads and writes to the block device like a local +iSCSI, NBD, etc). GFS2 reads and writes to the block device like a local file system, but also uses a lock module to allow the computers coordinate their I/O so file system consistency is maintained. One of the nifty -features of GFS is perfect consistency -- changes made to the file system +features of GFS2 is perfect consistency -- changes made to the file system on one machine show up immediately on all other machines in the cluster. -GFS uses interchangeable inter-node locking mechanisms, the currently +GFS2 uses interchangeable inter-node locking mechanisms, the currently supported mechanisms are: lock_nolock - - allows gfs to be used as a local file system + - allows GFS2 to be used as a local file system lock_dlm - - uses a distributed lock manager (dlm) for inter-node locking. + - uses the distributed lock manager (dlm) for inter-node locking. The dlm is found at linux/fs/dlm/ -Lock_dlm depends on user space cluster management systems found +lock_dlm depends on user space cluster management systems found at the URL above. -To use gfs as a local file system, no external clustering systems are +To use GFS2 as a local file system, no external clustering systems are needed, simply:: $ mkfs -t gfs2 -p lock_nolock -j 1 /dev/block_device $ mount -t gfs2 /dev/block_device /dir -If you are using Fedora, you need to install the gfs2-utils package -and, for lock_dlm, you will also need to install the cman package -and write a cluster.conf as per the documentation. For F17 and above -cman has been replaced by the dlm package. +The gfs2-utils package is required on all cluster nodes and, for lock_dlm, you +will also need the dlm and corosync user space utilities configured as per the +documentation. + +gfs2-utils can be found at https://pagure.io/gfs2-utils GFS2 is not on-disk compatible with previous versions of GFS, but it is pretty close. -The following man pages can be found at the URL above: +The following man pages are available from gfs2-utils: ============ ============================================= fsck.gfs2 to repair a filesystem gfs2_grow to expand a filesystem online gfs2_jadd to add journals to a filesystem online tunegfs2 to manipulate, examine and tune a filesystem - gfs2_convert to convert a gfs filesystem to gfs2 in-place + gfs2_convert to convert a gfs filesystem to GFS2 in-place mkfs.gfs2 to make a filesystem ============ ============================================= From 257f160a0e548639251a35ee8d55c94d9607bb12 Mon Sep 17 00:00:00 2001 From: Andrew Price Date: Wed, 18 Nov 2020 15:31:20 +0000 Subject: [PATCH 2/7] MAINTAINERS: Add gfs2 bug tracker link And remove the obsolete website URL. Signed-off-by: Andrew Price Signed-off-by: Andreas Gruenbacher --- MAINTAINERS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MAINTAINERS b/MAINTAINERS index a008b70f3c16..4cbfef8e1245 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -7422,7 +7422,7 @@ M: Bob Peterson M: Andreas Gruenbacher L: cluster-devel@redhat.com S: Supported -W: http://sources.redhat.com/cluster/ +B: https://bugzilla.kernel.org/enter_bug.cgi?product=File%20System&component=gfs2 T: git git://git.kernel.org/pub/scm/linux/kernel/git/gfs2/linux-gfs2.git F: Documentation/filesystems/gfs2* F: fs/gfs2/ From e3a77eebfa256c2f8871b8771f217b1afda4525e Mon Sep 17 00:00:00 2001 From: Andreas Gruenbacher Date: Wed, 25 Nov 2020 21:14:15 +0100 Subject: [PATCH 3/7] gfs2: Make inode operations static The inode operations are not used outside inode.c. Signed-off-by: Andreas Gruenbacher --- fs/gfs2/inode.c | 10 +++++++--- fs/gfs2/inode.h | 3 --- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/fs/gfs2/inode.c b/fs/gfs2/inode.c index 65ae4fc28ede..3d77f2970349 100644 --- a/fs/gfs2/inode.c +++ b/fs/gfs2/inode.c @@ -36,6 +36,10 @@ #include "super.h" #include "glops.h" +static const struct inode_operations gfs2_file_iops; +static const struct inode_operations gfs2_dir_iops; +static const struct inode_operations gfs2_symlink_iops; + static int iget_test(struct inode *inode, void *opaque) { u64 no_addr = *(u64 *)opaque; @@ -2136,7 +2140,7 @@ static int gfs2_update_time(struct inode *inode, struct timespec64 *time, return generic_update_time(inode, time, flags); } -const struct inode_operations gfs2_file_iops = { +static const struct inode_operations gfs2_file_iops = { .permission = gfs2_permission, .setattr = gfs2_setattr, .getattr = gfs2_getattr, @@ -2147,7 +2151,7 @@ const struct inode_operations gfs2_file_iops = { .update_time = gfs2_update_time, }; -const struct inode_operations gfs2_dir_iops = { +static const struct inode_operations gfs2_dir_iops = { .create = gfs2_create, .lookup = gfs2_lookup, .link = gfs2_link, @@ -2168,7 +2172,7 @@ const struct inode_operations gfs2_dir_iops = { .atomic_open = gfs2_atomic_open, }; -const struct inode_operations gfs2_symlink_iops = { +static const struct inode_operations gfs2_symlink_iops = { .get_link = gfs2_get_link, .permission = gfs2_permission, .setattr = gfs2_setattr, diff --git a/fs/gfs2/inode.h b/fs/gfs2/inode.h index b52ecf4ffe63..8073b8d2c7fa 100644 --- a/fs/gfs2/inode.h +++ b/fs/gfs2/inode.h @@ -107,9 +107,6 @@ extern int gfs2_open_common(struct inode *inode, struct file *file); extern loff_t gfs2_seek_data(struct file *file, loff_t offset); extern loff_t gfs2_seek_hole(struct file *file, loff_t offset); -extern const struct inode_operations gfs2_file_iops; -extern const struct inode_operations gfs2_dir_iops; -extern const struct inode_operations gfs2_symlink_iops; extern const struct file_operations gfs2_file_fops_nolock; extern const struct file_operations gfs2_dir_fops_nolock; From a55a47a3bc82cb53509ed2501697f9b385036195 Mon Sep 17 00:00:00 2001 From: Andreas Gruenbacher Date: Fri, 27 Nov 2020 14:23:04 +0100 Subject: [PATCH 4/7] Revert "GFS2: Prevent delete work from occurring on glocks used for create" Since commit a0e3cc65fa29 ("gfs2: Turn gl_delete into a delayed work"), we're cancelling any pending delete work of an iopen glock before attaching a new inode to that glock in gfs2_create_inode. This means that delete_work_func can no longer be queued or running when attaching the iopen glock to the new inode, and we can revert commit a4923865ea07 ("GFS2: Prevent delete work from occurring on glocks used for create"), which tried to achieve the same but in a racy way. Signed-off-by: Andreas Gruenbacher --- fs/gfs2/glock.c | 8 -------- fs/gfs2/incore.h | 1 - fs/gfs2/inode.c | 6 +----- 3 files changed, 1 insertion(+), 14 deletions(-) diff --git a/fs/gfs2/glock.c b/fs/gfs2/glock.c index 35a6fd103761..d87a5bc3607b 100644 --- a/fs/gfs2/glock.c +++ b/fs/gfs2/glock.c @@ -857,12 +857,6 @@ static void delete_work_func(struct work_struct *work) clear_bit(GLF_PENDING_DELETE, &gl->gl_flags); spin_unlock(&gl->gl_lockref.lock); - /* If someone's using this glock to create a new dinode, the block must - have been freed by another node, then re-used, in which case our - iopen callback is too late after the fact. Ignore it. */ - if (test_bit(GLF_INODE_CREATING, &gl->gl_flags)) - goto out; - if (test_bit(GLF_DEMOTE, &gl->gl_flags)) { /* * If we can evict the inode, give the remote node trying to @@ -2112,8 +2106,6 @@ static const char *gflags2str(char *buf, const struct gfs2_glock *gl) *p++ = 'o'; if (test_bit(GLF_BLOCKING, gflags)) *p++ = 'b'; - if (test_bit(GLF_INODE_CREATING, gflags)) - *p++ = 'c'; if (test_bit(GLF_PENDING_DELETE, gflags)) *p++ = 'P'; if (test_bit(GLF_FREEING, gflags)) diff --git a/fs/gfs2/incore.h b/fs/gfs2/incore.h index f8858d995b24..8e1ab8ed4abc 100644 --- a/fs/gfs2/incore.h +++ b/fs/gfs2/incore.h @@ -348,7 +348,6 @@ enum { GLF_LRU = 13, GLF_OBJECT = 14, /* Used only for tracing */ GLF_BLOCKING = 15, - GLF_INODE_CREATING = 16, /* Inode creation occurring */ GLF_PENDING_DELETE = 17, GLF_FREEING = 18, /* Wait for glock to be freed */ }; diff --git a/fs/gfs2/inode.c b/fs/gfs2/inode.c index 3d77f2970349..c1b77e8d6b1c 100644 --- a/fs/gfs2/inode.c +++ b/fs/gfs2/inode.c @@ -609,7 +609,7 @@ static int gfs2_create_inode(struct inode *dir, struct dentry *dentry, struct inode *inode = NULL; struct gfs2_inode *dip = GFS2_I(dir), *ip; struct gfs2_sbd *sdp = GFS2_SB(&dip->i_inode); - struct gfs2_glock *io_gl = NULL; + struct gfs2_glock *io_gl; int error, free_vfs_inode = 1; u32 aflags = 0; unsigned blocks = 1; @@ -750,8 +750,6 @@ static int gfs2_create_inode(struct inode *dir, struct dentry *dentry, init_dinode(dip, ip, symname); gfs2_trans_end(sdp); - BUG_ON(test_and_set_bit(GLF_INODE_CREATING, &io_gl->gl_flags)); - error = gfs2_glock_nq_init(io_gl, LM_ST_SHARED, GL_EXACT, &ip->i_iopen_gh); if (error) goto fail_gunlock2; @@ -797,7 +795,6 @@ static int gfs2_create_inode(struct inode *dir, struct dentry *dentry, gfs2_glock_dq_uninit(ghs); gfs2_qa_put(ip); gfs2_glock_dq_uninit(ghs + 1); - clear_bit(GLF_INODE_CREATING, &io_gl->gl_flags); gfs2_glock_put(io_gl); gfs2_qa_put(dip); return error; @@ -806,7 +803,6 @@ fail_gunlock3: glock_clear_object(io_gl, ip); gfs2_glock_dq_uninit(&ip->i_iopen_gh); fail_gunlock2: - clear_bit(GLF_INODE_CREATING, &io_gl->gl_flags); glock_clear_object(io_gl, ip); gfs2_glock_put(io_gl); fail_free_inode: From 28c332b941a7850d3854a00353c83965f3670791 Mon Sep 17 00:00:00 2001 From: Tom Rix Date: Fri, 27 Nov 2020 11:12:09 -0800 Subject: [PATCH 5/7] gfs2: remove trailing semicolons from macro definitions The macro use will already have a semicolon. Signed-off-by: Tom Rix Signed-off-by: Andreas Gruenbacher --- fs/gfs2/util.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/fs/gfs2/util.h b/fs/gfs2/util.h index d7562981b3a0..a4443dd8a94b 100644 --- a/fs/gfs2/util.h +++ b/fs/gfs2/util.h @@ -151,7 +151,7 @@ extern int check_journal_clean(struct gfs2_sbd *sdp, struct gfs2_jdesc *jd, bool verbose); #define gfs2_io_error(sdp) \ -gfs2_io_error_i((sdp), __func__, __FILE__, __LINE__); +gfs2_io_error_i((sdp), __func__, __FILE__, __LINE__) void gfs2_io_error_bh_i(struct gfs2_sbd *sdp, struct buffer_head *bh, @@ -159,10 +159,10 @@ void gfs2_io_error_bh_i(struct gfs2_sbd *sdp, struct buffer_head *bh, bool withdraw); #define gfs2_io_error_bh_wd(sdp, bh) \ -gfs2_io_error_bh_i((sdp), (bh), __func__, __FILE__, __LINE__, true); +gfs2_io_error_bh_i((sdp), (bh), __func__, __FILE__, __LINE__, true) #define gfs2_io_error_bh(sdp, bh) \ -gfs2_io_error_bh_i((sdp), (bh), __func__, __FILE__, __LINE__, false); +gfs2_io_error_bh_i((sdp), (bh), __func__, __FILE__, __LINE__, false) extern struct kmem_cache *gfs2_glock_cachep; From dd64fe8167ba4cbda343f0a40c5a7c2143d48866 Mon Sep 17 00:00:00 2001 From: Bob Peterson Date: Thu, 3 Dec 2020 08:49:55 -0500 Subject: [PATCH 6/7] gfs2: Remove sb_start_write from gfs2_statfs_sync Before this patch, function gfs2_statfs_sync called sb_start_write and sb_end_write. This is completely unnecessary because, aside from grabbing glocks, gfs2_statfs_sync does all its updates to statfs with a transaction: gfs2_trans_begin and _end. And transactions always do sb_start_intwrite in gfs2_trans_begin and sb_end_intwrite in gfs2_trans_end. This patch simply removes the call to sb_start_write. Signed-off-by: Bob Peterson Signed-off-by: Andreas Gruenbacher --- fs/gfs2/super.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/fs/gfs2/super.c b/fs/gfs2/super.c index b3d951ab8068..2f56acc41c04 100644 --- a/fs/gfs2/super.c +++ b/fs/gfs2/super.c @@ -353,7 +353,6 @@ int gfs2_statfs_sync(struct super_block *sb, int type) struct buffer_head *m_bh, *l_bh; int error; - sb_start_write(sb); error = gfs2_glock_nq_init(m_ip->i_gl, LM_ST_EXCLUSIVE, GL_NOCACHE, &gh); if (error) @@ -392,7 +391,6 @@ out_bh: out_unlock: gfs2_glock_dq_uninit(&gh); out: - sb_end_write(sb); return error; } From 6e5c4ea37a99e5b97aba227fc43f3682d4bc0496 Mon Sep 17 00:00:00 2001 From: Bob Peterson Date: Thu, 3 Dec 2020 08:51:41 -0500 Subject: [PATCH 7/7] gfs2: in signal_our_withdraw wait for unfreeze of _this_ fs only Function signal_our_withdraw needs to work on file systems that have been partially frozen. To do this, it called flush_workqueue(gfs2_freeze_wq). This this wrong because it waits for *ALL* file systems to be unfrozen, not just the one we're withdrawing from. It should only wait for the targetted file system to be unfrozen. Otherwise it would wait until ALL file systems are thawed before signaling the withdraw. This patch changes signal_our_withdraw so it calls flush_work() for the target file system's freeze work (only) to be completed. Signed-off-by: Bob Peterson Signed-off-by: Andreas Gruenbacher --- fs/gfs2/util.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/gfs2/util.c b/fs/gfs2/util.c index 0fba3bf64189..a374397f4273 100644 --- a/fs/gfs2/util.c +++ b/fs/gfs2/util.c @@ -137,7 +137,7 @@ static void signal_our_withdraw(struct gfs2_sbd *sdp) gfs2_glock_dq(&sdp->sd_jinode_gh); if (test_bit(SDF_FS_FROZEN, &sdp->sd_flags)) { /* Make sure gfs2_unfreeze works if partially-frozen */ - flush_workqueue(gfs2_freeze_wq); + flush_work(&sdp->sd_freeze_work); atomic_set(&sdp->sd_freeze_state, SFS_FROZEN); thaw_super(sdp->sd_vfs); } else {