Source-Changes-HG archive

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

[src/trunk]: src/sys/ufs/ffs Patch from Kirk McKusick to fix an ordering prob...



details:   https://anonhg.NetBSD.org/src/rev/8b05913de1ca
branches:  trunk
changeset: 500547:8b05913de1ca
user:      mycroft <mycroft%NetBSD.org@localhost>
date:      Wed Dec 13 20:07:32 2000 +0000

description:
Patch from Kirk McKusick to fix an ordering problem in softdep_setup_freeblks()
that could cause an inode to be reused prematurely (possibly resulting in the
file containing garbage blocks).

diffstat:

 sys/ufs/ffs/ffs_softdep.c |  37 ++++++++++++++++++++-----------------
 1 files changed, 20 insertions(+), 17 deletions(-)

diffs (75 lines):

diff -r 1af767565068 -r 8b05913de1ca sys/ufs/ffs/ffs_softdep.c
--- a/sys/ufs/ffs/ffs_softdep.c Wed Dec 13 18:15:56 2000 +0000
+++ b/sys/ufs/ffs/ffs_softdep.c Wed Dec 13 20:07:32 2000 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: ffs_softdep.c,v 1.11 2000/12/13 15:32:31 chs Exp $     */
+/*     $NetBSD: ffs_softdep.c,v 1.12 2000/12/13 20:07:32 mycroft Exp $ */
 
 /*
  * Copyright 1998 Marshall Kirk McKusick. All Rights Reserved.
@@ -1620,7 +1620,7 @@
        struct buf *bp;
        struct bufq_head fbqh;
        struct fs *fs = ip->i_fs;
-       int i, error;
+       int i, error, delay;
 #ifdef FFS_EI
        const int needswap = UFS_FSNEEDSWAP(fs);
 #endif
@@ -1673,6 +1673,16 @@
        if ((inodedep->id_state & IOSTARTED) != 0)
                panic("softdep_setup_freeblocks: inode busy");
        /*
+        * Add the freeblks structure to the list of operations that
+        * must await the zero'ed inode being written to disk. If we
+        * still have a bitmap dependency (delay == 0), then the inode
+        * has never been written to disk, so we can process the
+        * freeblks below once we have deleted the dependencies.
+        */
+       delay = (inodedep->id_state & DEPCOMPLETE);
+       if (delay)
+               WORKLIST_INSERT(&inodedep->id_bufwait, &freeblks->fb_list);
+       /*
         * Because the file length has been truncated to zero, any
         * pending block allocation dependency structures associated
         * with this inode are obsolete and can simply be de-allocated.
@@ -1708,23 +1718,16 @@
                ACQUIRE_LOCK(&lk);
        }
        softdep_free_pagecache(&fbqh);
+       if (inodedep_lookup(fs, ip->i_number, 0, &inodedep) != 0)
+               (void) free_inodedep(inodedep);
+       FREE_LOCK(&lk);
        /*
-        * Add the freeblks structure to the list of operations that
-        * must await the zero'ed inode being written to disk. If we
-        * still have a bitmap dependency, then the inode has never been
-        * written to disk, so we can process the freeblks immediately.
-        * If the inodedep does not exist, then the zero'ed inode has
-        * been written and we can also proceed.
+        * If the inode has never been written to disk (delay == 0),
+        * then we can process the freeblks now that we have deleted
+        * the dependencies.
         */
-       if (inodedep_lookup(fs, ip->i_number, 0, &inodedep) == 0 ||
-           free_inodedep(inodedep) ||
-           (inodedep->id_state & DEPCOMPLETE) == 0) {
-               FREE_LOCK(&lk);
+       if (!delay)
                handle_workitem_freeblocks(freeblks);
-       } else {
-               WORKLIST_INSERT(&inodedep->id_bufwait, &freeblks->fb_list);
-               FREE_LOCK(&lk);
-       }
 }
 
 /*
@@ -2042,7 +2045,7 @@
 
 #ifdef DIAGNOSTIC
        if (freeblks->fb_chkcnt != blocksreleased)
-               panic("handle_workitem_freeblocks: block count");
+               printf("handle_workitem_freeblocks: block count");
        if (allerror)
                softdep_error("handle_workitem_freeblks", allerror);
 #endif /* DIAGNOSTIC */



Home | Main Index | Thread Index | Old Index