summaryrefslogtreecommitdiffstats
path: root/sys/kern
diff options
context:
space:
mode:
authorgreen <green@FreeBSD.org>2004-08-02 00:18:36 +0000
committergreen <green@FreeBSD.org>2004-08-02 00:18:36 +0000
commit9532ab7116a36e60ae15ec463c757a7d2e7f9b39 (patch)
treeff53102435294d83e0ddcbd011824aa65f84e3c8 /sys/kern
parent14a50c4ac0247a8950847156b4fc16cf935c14ca (diff)
downloadFreeBSD-src-9532ab7116a36e60ae15ec463c757a7d2e7f9b39.zip
FreeBSD-src-9532ab7116a36e60ae15ec463c757a7d2e7f9b39.tar.gz
* Add a "how" argument to uma_zone constructors and initialization functions
so that they know whether the allocation is supposed to be able to sleep or not. * Allow uma_zone constructors and initialation functions to return either success or error. Almost all of the ones in the tree currently return success unconditionally, but mbuf is a notable exception: the packet zone constructor wants to be able to fail if it cannot suballocate an mbuf cluster, and the mbuf allocators want to be able to fail in general in a MAC kernel if the MAC mbuf initializer fails. This fixes the panics people are seeing when they run out of memory for mbuf clusters. * Allow debug.nosleepwithlocks on WITNESS to be disabled, without changing the default. Both bmilekic and jeff have reviewed the changes made to make failable zone allocations work.
Diffstat (limited to 'sys/kern')
-rw-r--r--sys/kern/kern_mbuf.c67
-rw-r--r--sys/kern/kern_proc.c14
-rw-r--r--sys/kern/kern_thread.c20
-rw-r--r--sys/kern/sys_pipe.c14
4 files changed, 60 insertions, 55 deletions
diff --git a/sys/kern/kern_mbuf.c b/sys/kern/kern_mbuf.c
index f2badd6..c2b749f 100644
--- a/sys/kern/kern_mbuf.c
+++ b/sys/kern/kern_mbuf.c
@@ -111,13 +111,13 @@ uma_zone_t zone_pack;
/*
* Local prototypes.
*/
-static void mb_ctor_mbuf(void *, int, void *);
-static void mb_ctor_clust(void *, int, void *);
-static void mb_ctor_pack(void *, int, void *);
+static int mb_ctor_mbuf(void *, int, void *, int);
+static int mb_ctor_clust(void *, int, void *, int);
+static int mb_ctor_pack(void *, int, void *, int);
static void mb_dtor_mbuf(void *, int, void *);
static void mb_dtor_clust(void *, int, void *); /* XXX */
static void mb_dtor_pack(void *, int, void *); /* XXX */
-static void mb_init_pack(void *, int);
+static int mb_init_pack(void *, int, int);
static void mb_fini_pack(void *, int);
static void mb_reclaim(void *);
@@ -180,19 +180,20 @@ mbuf_init(void *dummy)
* contains call-specific information required to support the
* mbuf allocation API.
*/
-static void
-mb_ctor_mbuf(void *mem, int size, void *arg)
+static int
+mb_ctor_mbuf(void *mem, int size, void *arg, int how)
{
struct mbuf *m;
struct mb_args *args;
+#ifdef MAC
+ int error;
+#endif
int flags;
- int how;
short type;
m = (struct mbuf *)mem;
args = (struct mb_args *)arg;
flags = args->flags;
- how = args->how;
type = args->type;
m->m_type = type;
@@ -206,17 +207,14 @@ mb_ctor_mbuf(void *mem, int size, void *arg)
SLIST_INIT(&m->m_pkthdr.tags);
#ifdef MAC
/* If the label init fails, fail the alloc */
- if (mac_init_mbuf(m, how) != 0) {
- m_free(m);
-/* XXX*/ panic("mb_ctor_mbuf(): can't deal with failure!");
-/* return 0; */
- }
+ error = mac_init_mbuf(m, how);
+ if (error)
+ return (error);
#endif
} else
m->m_data = m->m_dat;
mbstat.m_mbufs += 1; /* XXX */
-/* return 1;
-*/
+ return (0);
}
/*
@@ -252,8 +250,8 @@ mb_dtor_pack(void *mem, int size, void *arg)
* Here the 'arg' pointer points to the Mbuf which we
* are configuring cluster storage for.
*/
-static void
-mb_ctor_clust(void *mem, int size, void *arg)
+static int
+mb_ctor_clust(void *mem, int size, void *arg, int how)
{
struct mbuf *m;
@@ -269,8 +267,7 @@ mb_ctor_clust(void *mem, int size, void *arg)
m->m_ext.ext_buf);
*(m->m_ext.ref_cnt) = 1;
mbstat.m_mclusts += 1; /* XXX */
-/* return 1;
-*/
+ return (0);
}
/* XXX */
@@ -284,17 +281,18 @@ mb_dtor_clust(void *mem, int size, void *arg)
* The Packet secondary zone's init routine, executed on the
* object's transition from keg slab to zone cache.
*/
-static void
-mb_init_pack(void *mem, int size)
+static int
+mb_init_pack(void *mem, int size, int how)
{
struct mbuf *m;
m = (struct mbuf *)mem;
m->m_ext.ext_buf = NULL;
- uma_zalloc_arg(zone_clust, m, M_NOWAIT);
- if (m->m_ext.ext_buf == NULL) /* XXX */
- panic("mb_init_pack(): Can't deal with failure yet.");
+ uma_zalloc_arg(zone_clust, m, how);
+ if (m->m_ext.ext_buf == NULL)
+ return (ENOMEM);
mbstat.m_mclusts -= 1; /* XXX */
+ return (0);
}
/*
@@ -315,19 +313,21 @@ mb_fini_pack(void *mem, int size)
/*
* The "packet" keg constructor.
*/
-static void
-mb_ctor_pack(void *mem, int size, void *arg)
+static int
+mb_ctor_pack(void *mem, int size, void *arg, int how)
{
struct mbuf *m;
struct mb_args *args;
- int flags, how;
+#ifdef MAC
+ int error;
+#endif
+ int flags;
short type;
m = (struct mbuf *)mem;
args = (struct mb_args *)arg;
flags = args->flags;
type = args->type;
- how = args->how;
m->m_type = type;
m->m_next = NULL;
@@ -346,17 +346,14 @@ mb_ctor_pack(void *mem, int size, void *arg)
SLIST_INIT(&m->m_pkthdr.tags);
#ifdef MAC
/* If the label init fails, fail the alloc */
- if (mac_init_mbuf(m, how) != 0) {
- m_free(m);
-/* XXX*/ panic("mb_ctor_pack(): can't deal with failure!");
-/* return 0; */
- }
+ error = mac_init_mbuf(m, how);
+ if (error)
+ return (error);
#endif
}
mbstat.m_mbufs += 1; /* XXX */
mbstat.m_mclusts += 1; /* XXX */
-/* return 1;
-*/
+ return (0);
}
/*
diff --git a/sys/kern/kern_proc.c b/sys/kern/kern_proc.c
index a83b9e1..a104ae4 100644
--- a/sys/kern/kern_proc.c
+++ b/sys/kern/kern_proc.c
@@ -74,9 +74,9 @@ static void doenterpgrp(struct proc *, struct pgrp *);
static void orphanpg(struct pgrp *pg);
static void pgadjustjobc(struct pgrp *pgrp, int entering);
static void pgdelete(struct pgrp *);
-static void proc_ctor(void *mem, int size, void *arg);
+static int proc_ctor(void *mem, int size, void *arg, int flags);
static void proc_dtor(void *mem, int size, void *arg);
-static void proc_init(void *mem, int size);
+static int proc_init(void *mem, int size, int flags);
static void proc_fini(void *mem, int size);
/*
@@ -128,12 +128,13 @@ procinit()
/*
* Prepare a proc for use.
*/
-static void
-proc_ctor(void *mem, int size, void *arg)
+static int
+proc_ctor(void *mem, int size, void *arg, int flags)
{
struct proc *p;
p = (struct proc *)mem;
+ return (0);
}
/*
@@ -178,8 +179,8 @@ proc_dtor(void *mem, int size, void *arg)
/*
* Initialize type-stable parts of a proc (when newly created).
*/
-static void
-proc_init(void *mem, int size)
+static int
+proc_init(void *mem, int size, int flags)
{
struct proc *p;
struct thread *td;
@@ -195,6 +196,7 @@ proc_init(void *mem, int size)
proc_linkup(p, kg, ke, td);
bzero(&p->p_mtx, sizeof(struct mtx));
mtx_init(&p->p_mtx, "process lock", NULL, MTX_DEF | MTX_DUPOK);
+ return (0);
}
/*
diff --git a/sys/kern/kern_thread.c b/sys/kern/kern_thread.c
index c5e9504..7f6ef95 100644
--- a/sys/kern/kern_thread.c
+++ b/sys/kern/kern_thread.c
@@ -143,8 +143,8 @@ MTX_SYSINIT(tid_lock, &tid_lock, "TID lock", MTX_DEF);
/*
* Prepare a thread for use.
*/
-static void
-thread_ctor(void *mem, int size, void *arg)
+static int
+thread_ctor(void *mem, int size, void *arg, int flags)
{
struct thread *td;
@@ -165,6 +165,7 @@ thread_ctor(void *mem, int size, void *arg)
* next thread.
*/
td->td_critnest = 1;
+ return (0);
}
/*
@@ -202,8 +203,8 @@ thread_dtor(void *mem, int size, void *arg)
/*
* Initialize type-stable parts of a thread (when newly created).
*/
-static void
-thread_init(void *mem, int size)
+static int
+thread_init(void *mem, int size, int flags)
{
struct thread *td;
struct tid_bitmap_part *bmp, *new;
@@ -251,6 +252,7 @@ thread_init(void *mem, int size)
td->td_sleepqueue = sleepq_alloc();
td->td_turnstile = turnstile_alloc();
td->td_sched = (struct td_sched *)&td[1];
+ return (0);
}
/*
@@ -287,25 +289,27 @@ thread_fini(void *mem, int size)
/*
* Initialize type-stable parts of a kse (when newly created).
*/
-static void
-kse_init(void *mem, int size)
+static int
+kse_init(void *mem, int size, int flags)
{
struct kse *ke;
ke = (struct kse *)mem;
ke->ke_sched = (struct ke_sched *)&ke[1];
+ return (0);
}
/*
* Initialize type-stable parts of a ksegrp (when newly created).
*/
-static void
-ksegrp_init(void *mem, int size)
+static int
+ksegrp_init(void *mem, int size, int flags)
{
struct ksegrp *kg;
kg = (struct ksegrp *)mem;
kg->kg_sched = (struct kg_sched *)&kg[1];
+ return (0);
}
/*
diff --git a/sys/kern/sys_pipe.c b/sys/kern/sys_pipe.c
index 03f88e1..9efdc54 100644
--- a/sys/kern/sys_pipe.c
+++ b/sys/kern/sys_pipe.c
@@ -182,9 +182,9 @@ static void pipe_clone_write_buffer(struct pipe *wpipe);
static int pipespace(struct pipe *cpipe, int size);
static int pipespace_new(struct pipe *cpipe, int size);
-static void pipe_zone_ctor(void *mem, int size, void *arg);
+static int pipe_zone_ctor(void *mem, int size, void *arg, int flags);
static void pipe_zone_dtor(void *mem, int size, void *arg);
-static void pipe_zone_init(void *mem, int size);
+static int pipe_zone_init(void *mem, int size, int flags);
static void pipe_zone_fini(void *mem, int size);
static uma_zone_t pipe_zone;
@@ -201,8 +201,8 @@ pipeinit(void *dummy __unused)
KASSERT(pipe_zone != NULL, ("pipe_zone not initialized"));
}
-static void
-pipe_zone_ctor(void *mem, int size, void *arg)
+static int
+pipe_zone_ctor(void *mem, int size, void *arg, int flags)
{
struct pipepair *pp;
struct pipe *rpipe, *wpipe;
@@ -247,6 +247,7 @@ pipe_zone_ctor(void *mem, int size, void *arg)
pp->pp_label = NULL;
atomic_add_int(&amountpipes, 2);
+ return (0);
}
static void
@@ -261,8 +262,8 @@ pipe_zone_dtor(void *mem, int size, void *arg)
atomic_subtract_int(&amountpipes, 2);
}
-static void
-pipe_zone_init(void *mem, int size)
+static int
+pipe_zone_init(void *mem, int size, int flags)
{
struct pipepair *pp;
@@ -271,6 +272,7 @@ pipe_zone_init(void *mem, int size)
pp = (struct pipepair *)mem;
mtx_init(&pp->pp_mtx, "pipe mutex", NULL, MTX_DEF | MTX_RECURSE);
+ return (0);
}
static void
OpenPOWER on IntegriCloud