Below is an updated diff addressing the following concerns:
On Fri, Mar 17, 2023 at 03:45:59PM +0100, Alexander Bluhm wrote:
> The FreeBSD Code puts the check_nifree label before the if
> (fs->fs_cs(fs, cg).cs_nifree == 0) check. Could you move this chunk
> a little up to keep us in sync?
On Fri, Mar 17, 2023 at 03:57:39PM +0100, Mark Kettenis wrote:
> Don't hide a global variable like that!
There are also some concerns on the string "indallck",
to my understanding the first 7 characters show up as wchan in ps
and should be easy to grep for.
Any better names?
"ffs-node-lock"
"ffsndlock"
Index: ffs_alloc.c
===================================================================
RCS file: /cvs/src/sys/ufs/ffs/ffs_alloc.c,v
retrieving revision 1.114
diff -u -p -r1.114 ffs_alloc.c
--- ffs_alloc.c 11 Mar 2021 13:31:35 -0000 1.114
+++ ffs_alloc.c 17 Mar 2023 19:28:11 -0000
@@ -46,6 +46,7 @@
#include <sys/buf.h>
#include <sys/vnode.h>
#include <sys/mount.h>
+#include <sys/rwlock.h>
#include <sys/syslog.h>
#include <sys/stdint.h>
#include <sys/time.h>
@@ -75,6 +76,7 @@ daddr_t ffs_mapsearch(struct fs *, stru
static const struct timeval fserr_interval = { 2, 0 };
+struct rwlock ffs_node_lock = RWLOCK_INITIALIZER("indallck");
/*
* Allocate a block in the file system.
@@ -1108,6 +1110,9 @@ ffs_nodealloccg(struct inode *ip, u_int
* and in the cylinder group itself.
*/
fs = ip->i_fs;
+#ifdef FFS2
+ check_nifree:
+#endif
if (fs->fs_cs(fs, cg).cs_nifree == 0)
return (0);
@@ -1201,9 +1206,12 @@ gotit:
/* Has any inode not been used at least once? */
cgp->cg_initediblk < cgp->cg_ffs2_niblk) {
+ if (rw_enter(&ffs_node_lock, RW_WRITE | RW_SLEEPFAIL))
+ goto check_nifree;
ibp = getblk(ip->i_devvp, fsbtodb(fs,
ino_to_fsba(fs, cg * fs->fs_ipg + cgp->cg_initediblk)),
(int)fs->fs_bsize, 0, INFSLP);
+ rw_exit(&ffs_node_lock);
memset(ibp->b_data, 0, fs->fs_bsize);
dp2 = (struct ufs2_dinode *)(ibp->b_data);