patch-2.3.11 linux/fs/proc/root.c

Next file: linux/include/asm-alpha/core_pyxis.h
Previous file: linux/fs/proc/fd.c
Back to the patch index
Back to the overall index

diff -u --recursive --new-file v2.3.10/linux/fs/proc/root.c linux/fs/proc/root.c
@@ -849,14 +849,29 @@
 	int len;
 
 	if (dir->i_ino == PROC_ROOT_INO) { /* check for safety... */
-		dir->i_nlink = proc_root.nlink;
+		extern unsigned long total_forks;
+		static int last_timestamp = 0;
 
-		read_lock(&tasklist_lock);
-		for_each_task(p) {
-			if (p->pid)
-				dir->i_nlink++;
+		/*
+		 * this one can be a serious 'ps' performance problem if
+		 * there are many threads running - thus we do 'lazy'
+		 * link-recalculation - we change it only if the number
+		 * of threads has increased.
+		 */
+		if (total_forks != last_timestamp) {
+			int nlink = proc_root.nlink;
+
+			read_lock(&tasklist_lock);
+			last_timestamp = total_forks;
+			for_each_task(p)
+				nlink++;
+			read_unlock(&tasklist_lock);
+			/*
+			 * subtract the # of idle threads which
+			 * do not show up in /proc:
+			 */
+			dir->i_nlink = nlink - smp_num_cpus;
 		}
-		read_unlock(&tasklist_lock);
 	}
 
 	if (!proc_lookup(dir, dentry))

FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)