Whamcloud - gitweb
Add bad blocks allocation fix from extN (only used when on-disk data is bad).
authoradilger <adilger>
Mon, 7 Apr 2003 21:13:32 +0000 (21:13 +0000)
committeradilger <adilger>
Mon, 7 Apr 2003 21:13:32 +0000 (21:13 +0000)
lustre/kernel_patches/patches/ext3-2.4.20-fixes.patch [new file with mode: 0644]
lustre/kernel_patches/pc/ext3-2.4.20-fixes.pc [new file with mode: 0644]
lustre/kernel_patches/txt/ext3-2.4.20-fixes.txt [new file with mode: 0644]

diff --git a/lustre/kernel_patches/patches/ext3-2.4.20-fixes.patch b/lustre/kernel_patches/patches/ext3-2.4.20-fixes.patch
new file mode 100644 (file)
index 0000000..168046b
--- /dev/null
@@ -0,0 +1,114 @@
+ balloc.c |   53 +++++++++++++++++++++++++++++++----------------------
+ 1 files changed, 31 insertions(+), 22 deletions(-)
+
+diff -ru lum-2.4.18-um30/fs/ext3/balloc.c uml-2.4.18-12.5/fs/ext3/balloc.c
+--- lum-2.4.18-um30/fs/ext3/balloc.c   Mon Feb 25 12:38:08 2002
++++ uml-2.4.18-12.5/fs/ext3/balloc.c   Thu Sep 19 13:40:11 2002
+@@ -276,7 +276,8 @@
+       }
+       lock_super (sb);
+       es = sb->u.ext3_sb.s_es;
+-      if (block < le32_to_cpu(es->s_first_data_block) || 
++      if (block < le32_to_cpu(es->s_first_data_block) ||
++          block + count < block ||
+           (block + count) > le32_to_cpu(es->s_blocks_count)) {
+               ext3_error (sb, "ext3_free_blocks",
+                           "Freeing blocks not in datazone - "
+@@ -309,17 +310,6 @@
+       if (!gdp)
+               goto error_return;
+-      if (in_range (le32_to_cpu(gdp->bg_block_bitmap), block, count) ||
+-          in_range (le32_to_cpu(gdp->bg_inode_bitmap), block, count) ||
+-          in_range (block, le32_to_cpu(gdp->bg_inode_table),
+-                    sb->u.ext3_sb.s_itb_per_group) ||
+-          in_range (block + count - 1, le32_to_cpu(gdp->bg_inode_table),
+-                    sb->u.ext3_sb.s_itb_per_group))
+-              ext3_error (sb, "ext3_free_blocks",
+-                          "Freeing blocks in system zones - "
+-                          "Block = %lu, count = %lu",
+-                          block, count);
+-
+       /*
+        * We are about to start releasing blocks in the bitmap,
+        * so we need undo access.
+@@ -345,14 +335,24 @@
+       if (err)
+               goto error_return;
+-      for (i = 0; i < count; i++) {
++      for (i = 0; i < count; i++, block++) {
++              if (block == le32_to_cpu(gdp->bg_block_bitmap) ||
++                  block == le32_to_cpu(gdp->bg_inode_bitmap) ||
++                  in_range(block, le32_to_cpu(gdp->bg_inode_table),
++                           sb->u.ext2_sb.s_itb_per_group)) {
++                      ext3_error(sb, __FUNCTION__,
++                                 "Freeing block in system zone - block = %lu",
++                                 block);
++                      continue;
++              }
++
+               /*
+                * An HJ special.  This is expensive...
+                */
+ #ifdef CONFIG_JBD_DEBUG
+               {
+                       struct buffer_head *debug_bh;
+-                      debug_bh = sb_get_hash_table(sb, block + i);
++                      debug_bh = sb_get_hash_table(sb, block);
+                       if (debug_bh) {
+                               BUFFER_TRACE(debug_bh, "Deleted!");
+                               if (!bh2jh(bitmap_bh)->b_committed_data)
+@@ -365,9 +365,8 @@
+ #endif
+               BUFFER_TRACE(bitmap_bh, "clear bit");
+               if (!ext3_clear_bit (bit + i, bitmap_bh->b_data)) {
+-                      ext3_error (sb, __FUNCTION__,
+-                                    "bit already cleared for block %lu", 
+-                                    block + i);
++                      ext3_error(sb, __FUNCTION__,
++                                 "bit already cleared for block %lu", block);
+                       BUFFER_TRACE(bitmap_bh, "bit already cleared");
+               } else {
+                       dquot_freed_blocks++;
+@@ -415,7 +417,6 @@
+       if (!err) err = ret;
+       if (overflow && !err) {
+-              block += count;
+               count = overflow;
+               goto do_more;
+       }
+@@ -575,6 +577,7 @@
+       ext3_debug ("goal=%lu.\n", goal);
++repeat:
+       /*
+        * First, test whether the goal block is free.
+        */
+@@ -684,10 +686,20 @@
+       if (tmp == le32_to_cpu(gdp->bg_block_bitmap) ||
+           tmp == le32_to_cpu(gdp->bg_inode_bitmap) ||
+           in_range (tmp, le32_to_cpu(gdp->bg_inode_table),
+-                    sb->u.ext3_sb.s_itb_per_group))
+-              ext3_error (sb, "ext3_new_block",
+-                          "Allocating block in system zone - "
+-                          "block = %u", tmp);
++                    EXT3_SB(sb)->s_itb_per_group)) {
++              ext3_error(sb, __FUNCTION__,
++                         "Allocating block in system zone - block = %u", tmp);
++
++              /* Note: This will potentially use up one of the handle's
++               * buffer credits.  Normally we have way too many credits,
++               * so that is OK.  In _very_ rare cases it might not be OK.
++               * We will trigger an assertion if we run out of credits,
++               * and we will have to do a full fsck of the filesystem -
++               * better than randomly corrupting filesystem metadata.
++               */
++              ext3_set_bit(j, bh->b_data);
++              goto repeat;
++      }
+       /* The superblock lock should guard against anybody else beating
+        * us to this point! */
diff --git a/lustre/kernel_patches/pc/ext3-2.4.20-fixes.pc b/lustre/kernel_patches/pc/ext3-2.4.20-fixes.pc
new file mode 100644 (file)
index 0000000..441ced8
--- /dev/null
@@ -0,0 +1 @@
+fs/ext3/balloc.c
diff --git a/lustre/kernel_patches/txt/ext3-2.4.20-fixes.txt b/lustre/kernel_patches/txt/ext3-2.4.20-fixes.txt
new file mode 100644 (file)
index 0000000..b890cbd
--- /dev/null
@@ -0,0 +1,3 @@
+DESC
+Fix for block allocation errors if block bitmap or inode block list is corrupt.
+EDESC