Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 11 Aug 2008 09:24:14 GMT
From:      Nick Barkas <snb@FreeBSD.org>
To:        Perforce Change Reviews <perforce@FreeBSD.org>
Subject:   PERFORCE change 147142 for review
Message-ID:  <200808110924.m7B9OEBL081618@repoman.freebsd.org>

next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=147142

Change 147142 by snb@snb_toro on 2008/08/11 09:23:37

	* Replace DH_RECLAIMAGE with a writeable sysctl
	         (vfs.ufs.dirhash_reclaimage)
	       * Fix bug where ufsdirhash_lowmem() tries to delete old locked hashes
	         instead of skipping them, and doesn't delete the unlocked ones.
	       * ufsdirhash_lowmem() now is more aggressive and deletes at a minimum 
	         enough dirhashes to free 10% of ufs_dirhashmem per invocation, and 
	         always deletes hashes it can older than ufs_dirhashreclaimage, as 
	         suggested by Alan Cox.

Affected files ...

.. //depot/projects/soc2008/snb-dirhash/sys-ufs-ufs/dirhash.h#3 edit
.. //depot/projects/soc2008/snb-dirhash/sys-ufs-ufs/ufs_dirhash.c#8 edit

Differences ...

==== //depot/projects/soc2008/snb-dirhash/sys-ufs-ufs/dirhash.h#3 (text+ko) ====

@@ -68,12 +68,6 @@
 #define DH_SCOREINIT	8	/* initial dh_score when dirhash built */
 #define DH_SCOREMAX	64	/* max dh_score value */
 
-/* 
- * If a vm_lowmem signal is received, we will try to free memory by 
- * deleting all hashes older than DH_RECLAIMAGE seconds. 
- */
-#define DH_RECLAIMAGE	5
-
 /*
  * The main hash table has 2 levels. It is an array of pointers to
  * blocks of DH_NBLKOFF offsets.

==== //depot/projects/soc2008/snb-dirhash/sys-ufs-ufs/ufs_dirhash.c#8 (text+ko) ====

@@ -85,6 +85,10 @@
 static int ufs_dirhashlowmemcount = 0;
 SYSCTL_INT(_vfs_ufs, OID_AUTO, dirhash_lowmemcount, CTLFLAG_RD, 
     &ufs_dirhashlowmemcount, 0, "number of times low memory hook called");
+static int ufs_dirhashreclaimage = 5;
+SYSCTL_INT(_vfs_ufs, OID_AUTO, dirhash_reclaimage, CTLFLAG_RW, 
+    &ufs_dirhashreclaimage, 0, 
+    "max time in seconds of hash inactivity before deletion in low VM events");
 
 
 static int ufsdirhash_hash(struct dirhash *dh, char *name, int namelen);
@@ -1173,39 +1177,34 @@
 {
 	struct dirhash *dh;
 	int memfreed = 0;
+	/* XXX: this 10% may need to be adjusted */
 	int memwanted = ufs_dirhashmem / 10;
 
 	ufs_dirhashlowmemcount++;
 
 	DIRHASHLIST_LOCK();
 	/* 
-	 * Delete dirhashes not used for more than DH_RECLAIMAGE seconds. 
-	 * If we can't get a lock on the dirhash, it will be skipped. Quit 
-	 * when we have freed up 10% or more of the memory currently used by 
-	 * dirhashes. 
-	 * XXX 10% may need to be adjusted?
+	 * Delete dirhashes not used for more than ufs_dirhashreclaimage 
+	 * seconds. If we can't get a lock on the dirhash, it will be skipped.
 	 */
 	for (dh = TAILQ_FIRST(&ufsdirhash_list); dh != NULL; dh = 
 	     TAILQ_NEXT(dh, dh_list)) {
-		if (time_second - dh->dh_lastused > DH_RECLAIMAGE && 
-		    lockmgr(&dh->dh_lock, LK_EXCLUSIVE | LK_NOWAIT, NULL))
+		if (lockmgr(&dh->dh_lock, LK_EXCLUSIVE | LK_NOWAIT, NULL))
+			continue;
+		if (time_second - dh->dh_lastused > ufs_dirhashreclaimage)
 			memfreed += ufsdirhash_destroy(dh);
-		if (memfreed >= memwanted)
-			break;
 	}
 	
 	/* 
-	 * If no hashes were old enough, instead try deleting a single dirhash 
-	 * from the end of the list.
+	 * If not enough memory was freed, keep deleting hashes from the head 
+	 * of the dirhash list. The ones closest to the head should be the 
+	 * oldest. 
 	 */
-	dh = TAILQ_FIRST(&ufsdirhash_list);
-	while (memfreed == 0 && dh != NULL) {
-		if (lockmgr(&dh->dh_lock, LK_EXCLUSIVE | LK_NOWAIT, NULL)) {
-			dh = TAILQ_NEXT(dh, dh_list);
+	for (dh = TAILQ_FIRST(&ufsdirhash_list); memfreed < memwanted &&
+	     dh !=NULL; dh = TAILQ_NEXT(dh, dh_list)) {
+		if (lockmgr(&dh->dh_lock, LK_EXCLUSIVE | LK_NOWAIT, NULL))
 			continue;
-		}
 		memfreed += ufsdirhash_destroy(dh);
-		break;
 	}
 	DIRHASHLIST_UNLOCK();
 }



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200808110924.m7B9OEBL081618>