M_NOWAIT failure handling -- not so very rosy picture
Robert Watson
rwatson at FreeBSD.org
Wed Mar 26 19:48:40 PST 2003
I'm running a diskless system with the attached patch; the results have
not been so very pleasing. I'm collecting a set of panics and traces to
mail out to relevant developers, but it does give one pause. A related
patch for the mbuf allocator would probably also give some interesting
results. The patch is far from perfect, but has been enough to result in
some interesting scenarios.
# sysctl debug.malloc_failure_rate=10 # Fail one in ten
Some things to try that I've bumped into so far:
# sysctl -a > /dev/null
# mdconfig -a -s 5m -t malloc
# dd if=/dev/zero of=/dev/md0
# newfs /dev/md0
Both of these seem to be storage-related and I've e-mailed phk about them,
but I suspect there are a lot of others hanging around.
Robert N M Watson FreeBSD Core Team, TrustedBSD Projects
robert at fledge.watson.org Network Associates Laboratories
Index: kern_malloc.c
===================================================================
RCS file: /home/ncvs/src/sys/kern/kern_malloc.c,v
retrieving revision 1.119
diff -u -r1.119 kern_malloc.c
--- kern_malloc.c 10 Mar 2003 20:24:54 -0000 1.119
+++ kern_malloc.c 26 Mar 2003 19:27:28 -0000
@@ -138,6 +138,20 @@
/* time_uptime of last malloc(9) failure */
static time_t t_malloc_fail;
+#ifdef MALLOC_MAKE_FAILURES
+/*
+ * Cause malloc failures ever (n) mallocs with M_NOWAIT. If set to 0,
+ * don't cause failures.
+ */
+static int malloc_failure_rate;
+static int malloc_nowait_count;
+static int malloc_failure_count;
+SYSCTL_INT(_debug, OID_AUTO, malloc_failure_rate, CTLFLAG_RW,
+ &malloc_failure_rate, 0, "Every (n) mallocs with M_NOWAIT will fail");
+SYSCTL_INT(_debug, OID_AUTO, malloc_failure_count, CTLFLAG_RD,
+ &malloc_failure_count, 0, "Number of imposed malloc failures");
+#endif
+
int
malloc_last_fail(void)
{
@@ -187,6 +201,15 @@
#if 0
if (size == 0)
Debugger("zero size malloc");
+#endif
+#ifdef MALLOC_MAKE_FAILURES
+ if ((flags & M_NOWAIT) && (malloc_failure_rate != 0)) {
+ atomic_add_int(&malloc_nowait_count, 1);
+ if ((malloc_nowait_count % malloc_failure_rate) == 0) {
+ atomic_add_int(&malloc_failure_count, 1);
+ return (NULL);
+ }
+ }
#endif
if (flags & M_WAITOK)
KASSERT(curthread->td_intr_nesting_level == 0,
More information about the freebsd-arch
mailing list