]> git.hungrycats.org Git - linux/commitdiff
[PATCH] ext2 block allocation race fix
authorAndrew Morton <akpm@osdl.org>
Sun, 9 Nov 2003 23:18:01 +0000 (15:18 -0800)
committerLinus Torvalds <torvalds@home.osdl.org>
Sun, 9 Nov 2003 23:18:01 +0000 (15:18 -0800)
If this CPU decides that an ext2 block group has a free block it will then go
in and try to acquire it.  No locks are held, so another CPU can come in and
steal the last block.

In this case we will bogusly report a corrupted filessytem.

Fix it by just restarting the scan - this will choose a different blockgroup
or will generate -ENOSPC.

fs/ext2/balloc.c

index b63ebc25a245e6f767d964d71ad35ea905ba676a..a0aa0386f21faff42ae4de029a06ce6d726b338e 100644 (file)
@@ -402,6 +402,7 @@ int ext2_new_block(struct inode *inode, unsigned long goal,
         * Now search the rest of the groups.  We assume that 
         * i and desc correctly point to the last group visited.
         */
+retry:
        for (bit = 0; !group_alloc &&
                        bit < sbi->s_groups_count; bit++) {
                group_no++;
@@ -425,11 +426,12 @@ int ext2_new_block(struct inode *inode, unsigned long goal,
        ret_block = grab_block(sb_bgl_lock(sbi, group_no), bitmap_bh->b_data,
                                group_size, 0);
        if (ret_block < 0) {
-               ext2_error (sb, "ext2_new_block",
-                       "Free blocks count corrupted for block group %d",
-                               group_no);
+               /*
+                * Someone else grabbed the last free block in this blockgroup
+                * before us.  Retry the scan.
+                */
                group_alloc = 0;
-               goto io_error;
+               goto retry;
        }
 
 got_block: