summaryrefslogtreecommitdiffstats
path: root/sys/kern/kern_jail.c
diff options
context:
space:
mode:
Diffstat (limited to 'sys/kern/kern_jail.c')
-rw-r--r--sys/kern/kern_jail.c31
1 files changed, 5 insertions, 26 deletions
diff --git a/sys/kern/kern_jail.c b/sys/kern/kern_jail.c
index 050563b..8ce8327 100644
--- a/sys/kern/kern_jail.c
+++ b/sys/kern/kern_jail.c
@@ -2470,32 +2470,11 @@ prison_deref(struct prison *pr, int flags)
if (!(flags & PD_LOCKED))
mtx_lock(&pr->pr_mtx);
- /* Decrement the user references in a separate loop. */
- if (flags & PD_DEUREF) {
- for (tpr = pr;; tpr = tpr->pr_parent) {
- if (tpr != pr)
- mtx_lock(&tpr->pr_mtx);
- if (--tpr->pr_uref > 0)
- break;
- KASSERT(tpr != &prison0, ("prison0 pr_uref=0"));
- mtx_unlock(&tpr->pr_mtx);
- }
- /* Done if there were only user references to remove. */
- if (!(flags & PD_DEREF)) {
- mtx_unlock(&tpr->pr_mtx);
- if (flags & PD_LIST_SLOCKED)
- sx_sunlock(&allprison_lock);
- else if (flags & PD_LIST_XLOCKED)
- sx_xunlock(&allprison_lock);
- return;
- }
- if (tpr != pr) {
- mtx_unlock(&tpr->pr_mtx);
- mtx_lock(&pr->pr_mtx);
- }
- }
-
for (;;) {
+ if (flags & PD_DEUREF) {
+ pr->pr_uref--;
+ KASSERT(prison0.pr_uref != 0, ("prison0 pr_uref=0"));
+ }
if (flags & PD_DEREF)
pr->pr_ref--;
/* If the prison still has references, nothing else to do. */
@@ -2551,7 +2530,7 @@ prison_deref(struct prison *pr, int flags)
/* Removing a prison frees a reference on its parent. */
pr = ppr;
mtx_lock(&pr->pr_mtx);
- flags = PD_DEREF;
+ flags = PD_DEREF | PD_DEUREF;
}
}
OpenPOWER on IntegriCloud