Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/fs/puffs Add a PUFFS_UNMOUNT server->kernel request, whi...



details:   https://anonhg.NetBSD.org/src/rev/a367d61b1228
branches:  trunk
changeset: 750598:a367d61b1228
user:      pooka <pooka%NetBSD.org@localhost>
date:      Thu Jan 07 22:45:31 2010 +0000

description:
Add a PUFFS_UNMOUNT server->kernel request, which causes the kernel
to initiate self destruct, i.e. unmount(MNT_FORCE).  This, however,
is a semi-controlled self-destruct, since all caches are flushed
before the (possibly) violent unmount takes place.

diffstat:

 sys/fs/puffs/puffs_msgif.c |  53 +++++++++++++++++++++++++++++++++++++++++----
 sys/fs/puffs/puffs_msgif.h |   3 +-
 sys/fs/puffs/puffs_sys.h   |   3 +-
 3 files changed, 52 insertions(+), 7 deletions(-)

diffs (147 lines):

diff -r 27aac389037c -r a367d61b1228 sys/fs/puffs/puffs_msgif.c
--- a/sys/fs/puffs/puffs_msgif.c        Thu Jan 07 22:43:00 2010 +0000
+++ b/sys/fs/puffs/puffs_msgif.c        Thu Jan 07 22:45:31 2010 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: puffs_msgif.c,v 1.76 2009/12/07 20:57:55 pooka Exp $   */
+/*     $NetBSD: puffs_msgif.c,v 1.77 2010/01/07 22:45:31 pooka Exp $   */
 
 /*
  * Copyright (c) 2005, 2006, 2007  Antti Kantee.  All Rights Reserved.
@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: puffs_msgif.c,v 1.76 2009/12/07 20:57:55 pooka Exp $");
+__KERNEL_RCSID(0, "$NetBSD: puffs_msgif.c,v 1.77 2010/01/07 22:45:31 pooka Exp $");
 
 #include <sys/param.h>
 #include <sys/atomic.h>
@@ -855,6 +855,7 @@
                DPRINTF(("dispatch: vn/vfs message 0x%x\n", preq->preq_optype));
                puffsop_msg(pmp, preq);
                break;
+
        case PUFFSOP_FLUSH: /* process in sop thread */
        {
                struct puffs_flush *pf;
@@ -877,6 +878,23 @@
                mutex_exit(&pmp->pmp_sopmtx);
                break;
        }
+
+       case PUFFSOP_UNMOUNT: /* process in sop thread */
+       {
+
+               DPRINTF(("dispatch: unmount 0x%x\n", preq->preq_optype));
+
+               psopr = kmem_alloc(sizeof(*psopr), KM_SLEEP);
+               psopr->psopr_preq = *preq;
+               psopr->psopr_sopreq = PUFFS_SOPREQ_UNMOUNT;
+
+               mutex_enter(&pmp->pmp_sopmtx);
+               TAILQ_INSERT_TAIL(&pmp->pmp_sopreqs, psopr, psopr_entries);
+               cv_signal(&pmp->pmp_sopcv);
+               mutex_exit(&pmp->pmp_sopmtx);
+               break;
+       }
+
        default:
                DPRINTF(("dispatch: invalid class 0x%x\n", preq->preq_opclass));
                puffs_msg_sendresp(pmp, preq, EOPNOTSUPP);
@@ -897,8 +915,10 @@
 puffs_sop_thread(void *arg)
 {
        struct puffs_mount *pmp = arg;
+       struct mount *mp = PMPTOMP(pmp);
        struct puffs_sopreq *psopr;
        bool keeprunning;
+       bool unmountme = false;
 
        mutex_enter(&pmp->pmp_sopmtx);
        for (keeprunning = true; keeprunning; ) {
@@ -914,6 +934,18 @@
                case PUFFS_SOPREQ_FLUSH:
                        puffsop_flush(pmp, &psopr->psopr_pf);
                        break;
+               case PUFFS_SOPREQ_UNMOUNT:
+                       puffs_msg_sendresp(pmp, &sopreq->psopr_preq, 0);
+
+                       unmountme = true;
+                       keeprunning = false;
+
+                       /*
+                        * We know the mountpoint is still alive because
+                        * the thread that is us (poetic?) is still alive.
+                        */
+                       atomic_inc_uint((unsigned int*)&mp->mnt_refcnt);
+                       break;
                }
 
                kmem_free(psopr, sizeof(*psopr));
@@ -921,8 +953,7 @@
        }
 
        /*
-        * Purge remaining ops.  could send error, but that is highly
-        * unlikely to reach the caller.
+        * Purge remaining ops.  could send error, but ...
         */
        while ((psopr = TAILQ_FIRST(&pmp->pmp_sopreqs)) != NULL) {
                TAILQ_REMOVE(&pmp->pmp_sopreqs, psopr, psopr_entries);
@@ -932,9 +963,21 @@
        }
 
        pmp->pmp_sopthrcount--;
-       cv_signal(&pmp->pmp_sopcv);
+       cv_broadcast(&pmp->pmp_sopcv);
        mutex_exit(&pmp->pmp_sopmtx); /* not allowed to access fs after this */
 
+       /*
+        * If unmount was requested, we can now safely do it here, since
+        * our context is dead from the point-of-view of puffs_unmount()
+        * and we are just another thread.  dounmount() makes internally
+        * sure that VFS_UNMOUNT() isn't called reentrantly and that it
+        * is eventually completed.
+        */
+       if (unmountme) {
+               (void)dounmount(mp, MNT_FORCE, curlwp);
+               vfs_destroy(mp);
+       }
+
        kthread_exit(0);
 }
 
diff -r 27aac389037c -r a367d61b1228 sys/fs/puffs/puffs_msgif.h
--- a/sys/fs/puffs/puffs_msgif.h        Thu Jan 07 22:43:00 2010 +0000
+++ b/sys/fs/puffs/puffs_msgif.h        Thu Jan 07 22:45:31 2010 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: puffs_msgif.h,v 1.68 2009/10/17 23:22:04 pooka Exp $   */
+/*     $NetBSD: puffs_msgif.h,v 1.69 2010/01/07 22:45:31 pooka Exp $   */
 
 /*
  * Copyright (c) 2005, 2006, 2007  Antti Kantee.  All Rights Reserved.
@@ -52,6 +52,7 @@
 #define PUFFSOP_ERROR          0x04    /* only kernel-> */
 #define PUFFSOP_FLUSH          0x05    /* ->kernel */
 #define PUFFSOP_SUSPEND                0x06    /* ->kernel */
+#define PUFFSOP_UNMOUNT                0x07    /* ->kernel */
 
 #define PUFFSOPFLAG_FAF                0x10    /* fire-and-forget */
 #define PUFFSOPFLAG_ISRESPONSE 0x20    /* req is actually a resp */
diff -r 27aac389037c -r a367d61b1228 sys/fs/puffs/puffs_sys.h
--- a/sys/fs/puffs/puffs_sys.h  Thu Jan 07 22:43:00 2010 +0000
+++ b/sys/fs/puffs/puffs_sys.h  Thu Jan 07 22:45:31 2010 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: puffs_sys.h,v 1.73 2009/12/07 20:57:55 pooka Exp $     */
+/*     $NetBSD: puffs_sys.h,v 1.74 2010/01/07 22:45:31 pooka Exp $     */
 
 /*
  * Copyright (c) 2005, 2006  Antti Kantee.  All Rights Reserved.
@@ -101,6 +101,7 @@
 enum puffs_sopreqtype {
        PUFFS_SOPREQ_EXIT,
        PUFFS_SOPREQ_FLUSH,
+       PUFFS_SOPREQ_UNMOUNT,
 };
 
 struct puffs_sopreq {



Home | Main Index | Thread Index | Old Index