Skip to contentSkip to conversation

fix ext3 i_blocks accounting

PATCH New Andrew Morton 1 participant 1 message Apr 2, 2002

lore
Share & tools
lore
#0 lore raw

PATCH 1/1 fix ext3 i_blocks accounting

This fixes the "i_blocks went wrong when the disk filled up" problem.

In ext3_new_block() we increment i_blocks early, so the quota operation can be performed outside lock_super(). But if the block allocation ends up failing, we forget to undo the allocation.

This is not a serious bug, and probably does not warrant an upgrade for production machines. Its effects are:

1) errors are generated from e2fsck and

2) users could appear to be over quota when they really aren't.

The patch undoes the accounting operation if the allocation ends up failing.

fs/ext3/balloc.c renamed from fs/ext3/balloc.c~ext3-i_blocks +8 -2
@@ -542,6 +542,7 @@ int ext3_new_block (handle_t *handle, st
 	int i, j, k, tmp, alloctmp;
 	int bitmap_nr;
 	int fatal = 0, err;
+	int performed_allocation = 0;
 	struct super_block * sb;
 	struct ext3_group_desc * gdp;
 	struct ext3_super_block * es;
@@ -644,8 +645,7 @@ int ext3_new_block (handle_t *handle, st
 	}
 
 	/* No space left on the device */
-	unlock_super (sb);
-	return 0;
+	goto out;
 
 search_back:
 	/* 
@@ -694,6 +694,7 @@ got_block:
 	J_ASSERT_BH(bh, !ext3_test_bit(j, bh->b_data));
 	BUFFER_TRACE(bh, "setting bitmap bit");
 	ext3_set_bit(j, bh->b_data);
+	performed_allocation = 1;
 
 #ifdef CONFIG_JBD_DEBUG
 	{
@@ -815,6 +816,11 @@ out:
 		ext3_std_error(sb, fatal);
 	}
 	unlock_super (sb);
+	/*
+	 * Undo the block allocation
+	 */
+	if (!performed_allocation)
+		DQUOT_FREE_BLOCK(inode, 1);
 	return 0;
 	
 }

-