Whamcloud - gitweb
b=4834
authornathan <nathan>
Tue, 22 Mar 2005 00:27:22 +0000 (00:27 +0000)
committernathan <nathan>
Tue, 22 Mar 2005 00:27:22 +0000 (00:27 +0000)
Land b_release_1_4_1 onto b1_4 (20050321_1527)

144 files changed:
ldiskfs/kernel_patches/patches/ext3-extents-2.6.5.patch
ldiskfs/kernel_patches/patches/ext3-extents-2.6.9-rhel4.patch
ldiskfs/kernel_patches/patches/ext3-mballoc2-2.6-suse.patch
ldiskfs/kernel_patches/patches/ext3-mballoc2-2.6.9-rhel4.patch
lustre/ChangeLog
lustre/autoconf/lustre-core.m4
lustre/autoconf/lustre-version.ac
lustre/conf/modules.conf
lustre/include/liblustre.h
lustre/include/linux/lprocfs_status.h
lustre/include/linux/lustre_dlm.h
lustre/include/linux/lustre_fsfilt.h
lustre/include/linux/lustre_idl.h
lustre/include/linux/lustre_import.h
lustre/include/linux/lustre_lib.h
lustre/include/linux/lustre_lite.h
lustre/include/linux/lustre_mds.h
lustre/include/linux/lustre_net.h
lustre/include/linux/obd.h
lustre/include/linux/obd_class.h
lustre/include/linux/obd_support.h
lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-i686-smp.config [new file with mode: 0644]
lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-i686.config [new file with mode: 0644]
lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-ia64-smp.config [new file with mode: 0644]
lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-ia64.config [new file with mode: 0644]
lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-x86_64-smp.config [new file with mode: 0644]
lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-x86_64.config [new file with mode: 0644]
lustre/kernel_patches/patches/configurable-x86-stack-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/configurable-x86-stack-2.4.22-rh.patch [deleted file]
lustre/kernel_patches/patches/dev_read_only-2.6-lnxi.patch [new file with mode: 0644]
lustre/kernel_patches/patches/dev_read_only-2.6-suse.patch
lustre/kernel_patches/patches/dev_read_only_2.4.20-rh.patch
lustre/kernel_patches/patches/dev_read_only_2.4.21-chaos.patch
lustre/kernel_patches/patches/dev_read_only_hp_2.4.20.patch [deleted file]
lustre/kernel_patches/patches/dsp.patch [deleted file]
lustre/kernel_patches/patches/dynamic-locks-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/exports.patch [deleted file]
lustre/kernel_patches/patches/ext3-delete_thread-suse.patch [deleted file]
lustre/kernel_patches/patches/ext3-ea-in-inode-2.4.21-suse2.patch [new file with mode: 0644]
lustre/kernel_patches/patches/ext3-extents-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/ext3-extents-2.4.21-chaos.patch
lustre/kernel_patches/patches/ext3-extents-2.4.21-suse2.patch
lustre/kernel_patches/patches/ext3-extents-2.4.24.patch
lustre/kernel_patches/patches/ext3-extents-2.6.5.patch
lustre/kernel_patches/patches/ext3-extents-2.6.9-rhel4.patch
lustre/kernel_patches/patches/ext3-extents-asyncdel-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/ext3-extents-asyncdel-2.4.21-chaos.patch
lustre/kernel_patches/patches/ext3-extents-asyncdel-2.4.24.patch
lustre/kernel_patches/patches/ext3-htree-suse.patch [deleted file]
lustre/kernel_patches/patches/ext3-init-generation-2.6-suse.patch [deleted file]
lustre/kernel_patches/patches/ext3-mballoc2-2.6-suse.patch
lustre/kernel_patches/patches/ext3-mballoc2-2.6.7.patch [deleted file]
lustre/kernel_patches/patches/ext3-mballoc2-2.6.9-rhel4.patch
lustre/kernel_patches/patches/ext3-o_direct-1.2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/ext3-orphan_lock-suse.patch [deleted file]
lustre/kernel_patches/patches/ext3-pdirops-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/ext3_delete_thread_2.4.20_chaos.patch [deleted file]
lustre/kernel_patches/patches/ext3_orphan_lock-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/extN-wantedi-2.4.22-rh.patch [deleted file]
lustre/kernel_patches/patches/gpl_header-chaos-2.4.20.patch [deleted file]
lustre/kernel_patches/patches/iod-rmap-exports-2.4.20.patch [deleted file]
lustre/kernel_patches/patches/iod-stock-24-exports.patch [deleted file]
lustre/kernel_patches/patches/iod-stock-exports-2.4.22-rh.patch [deleted file]
lustre/kernel_patches/patches/kernel_text_address-2.4.21-suse-171.patch [deleted file]
lustre/kernel_patches/patches/linux-2.4.20-xattr-0.8.54-chaos.patch [deleted file]
lustre/kernel_patches/patches/linux-2.4.21-xattr-0.8.54-suse.patch [deleted file]
lustre/kernel_patches/patches/lustre_version.patch
lustre/kernel_patches/patches/netconsole-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/nfs_export_kernel-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/nfs_export_kernel-2.4.20.patch [deleted file]
lustre/kernel_patches/patches/nfs_export_kernel-2.4.22-rh.patch [deleted file]
lustre/kernel_patches/patches/revert-76chaos.patch [deleted file]
lustre/kernel_patches/patches/sd_iostats-2.6-rhel4.patch [new file with mode: 0644]
lustre/kernel_patches/patches/socket-exports-2.4.22-rh.patch [deleted file]
lustre/kernel_patches/patches/tcp_zero_copy_2.4.20_chaos.patch [deleted file]
lustre/kernel_patches/patches/vfs-pdirops-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/vfs_intent-2.4.20-rh.patch [deleted file]
lustre/kernel_patches/patches/vfs_intent-2.4.21-chaos.patch [deleted file]
lustre/kernel_patches/patches/vfs_intent-2.4.22-rh.patch [deleted file]
lustre/kernel_patches/patches/vfs_intent-2.6-rhel4.patch
lustre/kernel_patches/patches/x86-fpu-crash.patch [deleted file]
lustre/kernel_patches/patches/xattr-0.8.54-2.4.22-rh.patch [deleted file]
lustre/kernel_patches/series/2.6-rhel4.series
lustre/kernel_patches/series/2.6-suse-lnxi.series
lustre/kernel_patches/series/2.6-vanilla.series [deleted file]
lustre/kernel_patches/series/hp-pnnl-2.4.20
lustre/kernel_patches/series/ldiskfs-2.6-vanilla.series [deleted file]
lustre/kernel_patches/series/rh-2.4.20 [deleted file]
lustre/kernel_patches/series/rh-2.4.22 [deleted file]
lustre/kernel_patches/series/suse-2.4.19 [deleted file]
lustre/kernel_patches/series/suse-2.4.21 [deleted file]
lustre/kernel_patches/series/suse-2.4.21-cray [moved from lustre/kernel_patches/series/suse-2.4.21-2 with 96% similarity]
lustre/kernel_patches/series/vanilla-2.4.24
lustre/kernel_patches/targets/2.6-rhel4.target.in [new file with mode: 0644]
lustre/kernel_patches/which_patch
lustre/ldlm/ldlm_lib.c
lustre/ldlm/ldlm_lockd.c
lustre/ldlm/ldlm_resource.c
lustre/liblustre/llite_lib.c
lustre/liblustre/super.c
lustre/llite/dcache.c
lustre/llite/llite_internal.h
lustre/llite/llite_lib.c
lustre/llite/rw.c
lustre/lov/lov_log.c
lustre/lov/lov_obd.c
lustre/lvfs/fsfilt_ext3.c
lustre/mdc/mdc_request.c
lustre/mds/handler.c
lustre/mds/mds_fs.c
lustre/mds/mds_internal.h
lustre/mds/mds_log.c
lustre/mds/mds_lov.c
lustre/mds/mds_open.c
lustre/obdclass/class_obd.c
lustre/obdclass/genops.c
lustre/obdclass/llog_obd.c
lustre/obdclass/llog_test.c
lustre/obdclass/lprocfs_status.c
lustre/obdclass/obd_config.c
lustre/obdclass/sysctl.c
lustre/obdecho/echo.c
lustre/obdecho/echo_client.c
lustre/obdfilter/filter.c
lustre/osc/osc_request.c
lustre/ost/ost_handler.c
lustre/ptlrpc/client.c
lustre/ptlrpc/niobuf.c
lustre/ptlrpc/pinger.c
lustre/ptlrpc/recover.c
lustre/ptlrpc/service.c
lustre/tests/Makefile.am
lustre/tests/Makefile.mk
lustre/tests/cfg/insanity-local.sh
lustre/tests/local.sh
lustre/tests/lov.sh
lustre/tests/recovery-small.sh
lustre/tests/replay-dual.sh
lustre/tests/sanity.sh
lustre/tests/sanityN.sh
lustre/tests/test-framework.sh
lustre/tests/uml.sh
lustre/tests/writemany.c [new file with mode: 0644]
lustre/utils/lconf

index 671fbc0..053c0fb 100644 (file)
@@ -3,9 +3,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 ===================================================================
 --- linux-2.6.5-sles9.orig/fs/ext3/extents.c   2005-02-17 22:07:57.023609040 +0300
 +++ linux-2.6.5-sles9/fs/ext3/extents.c        2005-02-23 01:02:37.396435640 +0300
-@@ -0,0 +1,2356 @@
+@@ -0,0 +1,2349 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -54,17 +54,17 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +{
 +      if (eh->eh_magic != EXT3_EXT_MAGIC) {
 +              printk(KERN_ERR "EXT3-fs: invalid magic = 0x%x\n",
-+                              (unsigned) eh->eh_magic);
++                     (unsigned)eh->eh_magic);
 +              return -EIO;
 +      }
 +      if (eh->eh_max == 0) {
 +              printk(KERN_ERR "EXT3-fs: invalid eh_max = %u\n",
-+                              (unsigned) eh->eh_max);
++                     (unsigned)eh->eh_max);
 +              return -EIO;
 +      }
 +      if (eh->eh_entries > eh->eh_max) {
 +              printk(KERN_ERR "EXT3-fs: invalid eh_entries = %u\n",
-+                              (unsigned) eh->eh_entries);
++                     (unsigned)eh->eh_entries);
 +              return -EIO;
 +      }
 +      return 0;
@@ -107,8 +107,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *  - ENOMEM
 + */
 +static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_extents_tree *tree,
++                             struct ext3_ext_path *path)
 +{
 +      int err;
 +
@@ -129,7 +129,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *  - EIO
 + */
 +static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                        struct ext3_ext_path *path)
 +{
 +      int err;
 +      if (path->p_bh) {
@@ -144,8 +144,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int inline
 +ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
++                 struct ext3_ext_path *path, struct ext3_extent *ex,
++                 int *err)
 +{
 +      int goal, depth, newblock;
 +      struct inode *inode;
@@ -164,7 +164,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              unsigned long colour;
 +
 +              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
++                          EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
 +                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
 +              colour = (current->pid % 16) *
 +                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
@@ -187,8 +187,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 6;
 +#endif
@@ -200,8 +200,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent_idx);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 5;
 +#endif
@@ -212,8 +212,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      sizeof(struct ext3_extent);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 3;
 +#endif
@@ -224,9 +224,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 4;
 +#endif
@@ -234,7 +233,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int k, l = path->p_depth;
@@ -243,12 +242,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      for (k = 0; k <= l; k++, path++) {
 +              if (path->p_idx) {
 +                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
++                                path->p_idx->ei_leaf);
 +              } else if (path->p_ext) {
 +                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
++                                path->p_ext->ee_block,
++                                path->p_ext->ee_len,
++                                path->p_ext->ee_start);
 +              } else
 +                      ext_debug(tree, "  []");
 +      }
@@ -257,7 +256,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int depth = EXT_DEPTH(tree);
@@ -273,7 +272,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +      for (i = 0; i < eh->eh_entries; i++, ex++) {
 +              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +      }
 +      ext_debug(tree, "\n");
 +#endif
@@ -284,11 +283,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      int depth = path->p_depth;
 +      int i;
 +
-+      for (i = 0; i <= depth; i++, path++)
++      for (i = 0; i <= depth; i++, path++) {
 +              if (path->p_bh) {
 +                      brelse(path->p_bh);
 +                      path->p_bh = NULL;
 +              }
++      }
 +}
 +
 +/*
@@ -296,7 +296,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                     struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent_idx *ix;
@@ -322,7 +322,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +      ix += l;
 +      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
++      ext_debug(tree," -> %d->%d ",path->p_idx->ei_block,path->p_idx->ei_leaf);
 +
 +      while (l++ < r) {
 +              if (block < ix->ei_block) 
@@ -330,7 +330,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              path->p_idx = ix++;
 +      }
 +      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -340,9 +340,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              for (k = 0; k < eh->eh_entries; k++, ix++) {
 +                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
 +                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
++                                     ix, EXT_FIRST_INDEX(eh));
 +                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
++                                     ix->ei_block,ix[-1].ei_block);
 +                      }
 +                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
 +                      if (block < ix->ei_block) 
@@ -352,7 +352,6 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              EXT_ASSERT(chix == path->p_idx);
 +      }
 +#endif
-+
 +}
 +
 +/*
@@ -360,7 +359,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                 struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent *ex;
@@ -394,7 +393,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      ex += l;
 +      path->p_ext = ex;
 +      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +      while (l++ < r) {
 +              if (block < ex->ee_block) 
@@ -402,7 +401,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              path->p_ext = ex++;
 +      }
 +      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -418,7 +417,6 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              EXT_ASSERT(chex == path->p_ext);
 +      }
 +#endif
-+
 +}
 +
 +int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
@@ -439,7 +437,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +struct ext3_ext_path *
 +ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
++                   struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      struct buffer_head *bh;
@@ -461,7 +459,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* account possible depth increase */
 +      if (!path) {
 +              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
++                             GFP_NOFS);
 +              if (!path)
 +                      return ERR_PTR(-ENOMEM);
 +      }
@@ -471,7 +469,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* walk through the tree */
 +      while (i) {
 +              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
++                        ppos, eh->eh_entries, eh->eh_max);
 +              ext3_ext_binsearch_idx(tree, path + ppos, block);
 +              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
 +              path[ppos].p_depth = i;
@@ -519,9 +517,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * it check where to insert: before curp or after curp
 + */
 +static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *curp,
++                               int logical, int ptr)
 +{
 +      struct ext3_extent_idx *ix;
 +      int len, err;
@@ -537,9 +535,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent_idx);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
++                                "move %d from 0x%p to 0x%p\n",
++                                logical, ptr, len,
++                                (curp->p_idx + 1), (curp->p_idx + 2));
 +                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
 +              }
 +              ix = curp->p_idx + 1;
@@ -548,9 +546,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              len = len * sizeof(struct ext3_extent_idx);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
++                        "move %d from 0x%p to 0x%p\n",
++                        logical, ptr, len,
++                        curp->p_idx, (curp->p_idx + 1));
 +              memmove(curp->p_idx + 1, curp->p_idx, len);
 +              ix = curp->p_idx;
 +      }
@@ -578,8 +576,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *  - initialize subtree
 + */
 +static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
++                        struct ext3_ext_path *path,
++                        struct ext3_extent *newext, int at)
 +{
 +      struct buffer_head *bh = NULL;
 +      int depth = EXT_DEPTH(tree);
@@ -600,13 +598,13 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              border = path[depth].p_ext[1].ee_block;
 +              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      } else {
 +              border = newext->ee_block;
 +              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      }
 +
 +      /* 
@@ -664,12 +662,11 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      while (path[depth].p_ext <=
 +                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
++                        path[depth].p_ext->ee_block,
++                        path[depth].p_ext->ee_start,
++                        path[depth].p_ext->ee_len,
++                        newblock);
++              memmove(ex++, path[depth].p_ext++, sizeof(struct ext3_extent));
 +              neh->eh_entries++;
 +              m++;
 +      }
@@ -722,21 +719,21 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              fidx->ei_leaf = oldblock;
 +
 +              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
++                        i, newblock, border, oldblock);
 +              /* copy indexes */
 +              m = 0;
 +              path[i].p_idx++;
 +
 +              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
++                        EXT_MAX_INDEX(path[i].p_hdr));
 +              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
++                         EXT_LAST_INDEX(path[i].p_hdr));
 +              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
 +                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
++                                i, path[i].p_idx->ei_block,
++                                path[i].p_idx->ei_leaf, newblock);
 +                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
++                              sizeof(struct ext3_extent_idx));
 +                      neh->eh_entries++;
 +                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
 +                      m++;
@@ -766,7 +763,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* insert new index */
 +      if (!err)
 +              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
++                                          border, newblock);
 +
 +cleanup:
 +      if (bh) {
@@ -796,9 +793,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *    just created block
 + */
 +static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *path,
++                               struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp = path;
 +      struct ext3_extent_header *neh;
@@ -830,7 +827,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* set size of new block */
 +      neh = EXT_BLOCK_HDR(bh);
 +      /* old root could have indexes or leaves
-+       * so calculate e_max right way */
++       * so calculate eh_max right way */
 +      if (EXT_DEPTH(tree))
 +              neh->eh_max = ext3_ext_space_block_idx(tree);
 +      else
@@ -857,7 +854,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      neh = EXT_ROOT_HDR(tree);
 +      fidx = EXT_FIRST_INDEX(neh);
 +      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
++                neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
 +
 +      neh->eh_depth = path->p_depth + 1;
 +      err = ext3_ext_dirty(handle, tree, curp);
@@ -872,9 +869,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * then it requests in-depth growing
 + */
 +static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                                  struct ext3_extents_tree *tree,
++                                  struct ext3_ext_path *path,
++                                  struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp;
 +      int depth, i, err = 0;
@@ -950,12 +947,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              if (depth == path->p_depth) {
 +                      /* leaf */
 +                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
++                          EXT_LAST_EXTENT(path[depth].p_hdr))
 +                              return path[depth].p_ext[1].ee_block;
 +              } else {
 +                      /* index */
 +                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
++                          EXT_LAST_INDEX(path[depth].p_hdr))
 +                              return path[depth].p_idx[1].ei_block;
 +              }
 +              depth--;        
@@ -968,7 +965,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * returns first allocated block from next leaf or EXT_MAX_BLOCK
 + */
 +static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
++                                       struct ext3_ext_path *path)
 +{
 +      int depth;
 +
@@ -984,7 +981,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      
 +      while (depth >= 0) {
 +              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
++                  EXT_LAST_INDEX(path[depth].p_hdr))
 +                      return path[depth].p_idx[1].ei_block;
 +              depth--;        
 +      }
@@ -998,7 +995,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * TODO: do we need to correct tree in all cases?
 + */
 +int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                           struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      int depth = EXT_DEPTH(tree);    
@@ -1048,8 +1045,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int inline
 +ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                         struct ext3_extent *ex1,
++                         struct ext3_extent *ex2)
 +{
 +      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
 +              return 0;
@@ -1071,8 +1068,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * creating new leaf in no-space case
 + */
 +int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
++                         struct ext3_ext_path *path,
++                         struct ext3_extent *newext)
 +{
 +      struct ext3_extent_header * eh;
 +      struct ext3_extent *ex, *fex;
@@ -1088,8 +1085,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* try to insert block into found extent and return */
 +      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
 +              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
++                        newext->ee_len, ex->ee_block, ex->ee_len,
++                        ex->ee_start);
 +              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
 +                      return err;
 +              ex->ee_len += newext->ee_len;
@@ -1117,12 +1114,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              eh = npath[depth].p_hdr;
 +              if (eh->eh_entries < eh->eh_max) {
 +                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
++                                eh->eh_entries);
 +                      path = npath;
 +                      goto repeat;
 +              }
 +              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
++                        eh->eh_entries, eh->eh_max);
 +      }
 +
 +      /*
@@ -1144,8 +1141,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if (!nearex) {
 +              /* there is no extent in this leaf, create first one */
 +              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
++                        newext->ee_block, newext->ee_start,
++                        newext->ee_len);
 +              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
 +      } else if (newext->ee_block > nearex->ee_block) {
 +              EXT_ASSERT(newext->ee_block != nearex->ee_block);
@@ -1154,10 +1151,10 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
++                                "move %d from 0x%p to 0x%p\n",
++                                newext->ee_block, newext->ee_start,
++                                newext->ee_len,
++                                nearex, len, nearex + 1, nearex + 2);
 +                      memmove(nearex + 2, nearex + 1, len);
 +              }
 +              path[depth].p_ext = nearex + 1;
@@ -1166,9 +1163,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
++                        "move %d from 0x%p to 0x%p\n",
++                        newext->ee_block, newext->ee_start, newext->ee_len,
++                        nearex, len, nearex + 1, nearex + 2);
 +              memmove(nearex + 1, nearex, len);
 +              path[depth].p_ext = nearex;
 +      }
@@ -1189,8 +1186,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              /* merge with next extent! */
 +              nearex->ee_len += nearex[1].ee_len;
 +              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
++                      len = (EXT_LAST_EXTENT(eh) - nearex - 1) *
++                              sizeof(struct ext3_extent);
 +                      memmove(nearex + 1, nearex + 2, len);
 +              }
 +              eh->eh_entries--;
@@ -1324,7 +1321,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static inline void
 +ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
++                    __u32 len, __u32 start, int type)
 +{
 +      EXT_ASSERT(len > 0);
 +      if (tree->cex) {
@@ -1341,8 +1338,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
++                        struct ext3_ext_path *path,
++                        unsigned long block)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      unsigned long lblock, len;
@@ -1361,16 +1358,16 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              lblock = block;
 +              len = ex->ee_block - block;
 +              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len);
 +      } else if (block >= ex->ee_block + ex->ee_len) {
 +              lblock = ex->ee_block + ex->ee_len;
 +              len = ext3_ext_next_allocated_block(path);
 +              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) block);
 +              EXT_ASSERT(len > lblock);
 +              len = len - lblock;
 +      } else {
@@ -1384,7 +1381,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static inline int
 +ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
++                struct ext3_extent *ex)
 +{
 +      struct ext3_ext_cache *cex = tree->cex;
 +
@@ -1397,16 +1394,16 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              return EXT3_EXT_CACHE_NO;
 +
 +      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
++                 cex->ec_type == EXT3_EXT_CACHE_EXTENT);
 +      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
 +              ex->ee_block = cex->ec_block;
 +              ex->ee_start = cex->ec_start;
 +              ex->ee_len = cex->ec_len;
 +              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) ex->ee_start);
 +              return cex->ec_type;
 +      }
 +
@@ -1420,7 +1417,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * last index in the block only
 + */
 +int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
++                  struct ext3_ext_path *path)
 +{
 +      struct buffer_head *bh;
 +      int err;
@@ -1434,7 +1431,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if ((err = ext3_ext_dirty(handle, tree, path)))
 +              return err;
 +      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +      bh = sb_find_get_block(tree->inode->i_sb, path->p_idx->ei_leaf);
 +      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
 +      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
@@ -1442,7 +1439,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
++                                   struct ext3_ext_path *path)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      int needed;
@@ -1479,8 +1476,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++                    struct ext3_ext_path *path, unsigned long start,
++                    unsigned long end)
 +{
 +      struct ext3_extent *ex, tex;
 +      struct ext3_ext_path *npath;
@@ -1514,7 +1511,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* FIXME: some callback to free underlying resource
 +       * and correct ee_start? */
 +      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
++                ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
 +
 +      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
 +      if (IS_ERR(npath))
@@ -1528,13 +1525,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      kfree(npath);
 +
 +      return err;
-+                      
 +}
 +
 +static int
 +ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++               struct ext3_ext_path *path, unsigned long start,
++               unsigned long end)
 +{
 +      struct ext3_extent *ex, *fu = NULL, *lu, *le;
 +      int err = 0, correct_index = 0;
@@ -1567,8 +1563,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      }
 +      
 +      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
++      while (ex >= EXT_FIRST_EXTENT(eh) && ex->ee_block + ex->ee_len > start) {
 +              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
 +              path[depth].p_ext = ex;
 +      
@@ -1595,7 +1590,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      block = ex->ee_block; 
 +                      num = 0;
 +                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
++                                 b == ex->ee_block + ex->ee_len - 1);
 +              }
 +
 +              if (ex == EXT_FIRST_EXTENT(eh))
@@ -1637,7 +1632,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      goto out;
 +
 +              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +              ex--;
 +      }
 +
@@ -1701,7 +1696,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
++                        unsigned long start, unsigned long end)
 +{
 +      struct inode *inode = tree->inode;
 +      struct super_block *sb = inode->i_sb;
@@ -1725,8 +1720,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +       */
 +      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
 +      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
++              ext3_error(sb, __FUNCTION__, "Can't allocate path array");
 +              ext3_journal_stop(handle);
 +              return -ENOMEM;
 +      }
@@ -1758,19 +1752,19 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                              ext3_ext_last_covered(path[i].p_hdr, end);
 +                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
 +                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
++                                path[i].p_hdr, path[i].p_hdr->eh_entries);
 +              } else {
 +                      /* we've already was here, see at next index */
 +                      path[i].p_idx--;
 +              }
 +
 +              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
++                        i, EXT_FIRST_INDEX(path[i].p_hdr),
++                        path[i].p_idx);
 +              if (ext3_ext_more_to_rm(path + i)) {
 +                      /* go to the next level */
 +                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
++                                i + 1, path[i].p_idx->ei_leaf);
 +                      memset(path + i + 1, 0, sizeof(*path));
 +                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
 +                      if (!path[i+1].p_bh) {
@@ -1893,7 +1887,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                           struct ext3_extent *ex2)
 +{
 +      /* FIXME: support for large fs */
 +      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
@@ -1903,8 +1897,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                         struct ext3_extent *ex,
++                         unsigned long from, unsigned long to)
 +{
 +      int needed;
 +      
@@ -1919,8 +1913,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                 struct ext3_extent *ex,
++                 unsigned long from, unsigned long to)
 +{
 +      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
 +      handle_t *handle = ext3_journal_start(tree->inode, needed);
@@ -1935,7 +1929,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              num = ex->ee_block + ex->ee_len - from;
 +              start = ex->ee_start + ex->ee_len - num;
 +              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
++                        num, start);
 +              for (i = 0; i < num; i++) {
 +                      bh = sb_find_get_block(tree->inode->i_sb, start + i);
 +                      ext3_forget(handle, 0, tree->inode, bh, start + i);
@@ -1943,17 +1937,17 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              ext3_free_blocks(handle, tree->inode, start, num);
 +      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
 +              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      } else {
 +              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      }
 +      ext3_journal_stop(handle);
 +      return 0;
 +}
 +
 +static int ext3_ext_find_goal(struct inode *inode,
-+                              struct ext3_ext_path *path, unsigned long block)
++                            struct ext3_ext_path *path, unsigned long block)
 +{
 +      struct ext3_inode_info *ei = EXT3_I(inode);
 +      unsigned long bg_start;
@@ -1983,8 +1977,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
++                           struct ext3_ext_path *path,
++                           struct ext3_extent *ex, int *err)
 +{
 +      struct inode *inode = tree->inode;
 +      int newblock, goal;
@@ -2021,7 +2015,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +};
 +
 +void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
++                       struct inode *inode)
 +{
 +      tree->inode = inode;
 +      tree->root = (void *) EXT3_I(inode)->i_data;
@@ -2032,8 +2026,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result,
-+                      int create, int extend_disksize)
++                     long iblock, struct buffer_head *bh_result,
++                     int create, int extend_disksize)
 +{
 +      struct ext3_ext_path *path = NULL;
 +      struct ext3_extent newex;
@@ -2044,7 +2038,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      __clear_bit(BH_New, &bh_result->b_state);
 +      ext3_init_tree_desc(&tree, inode);
 +      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
++                (int) iblock, (unsigned) inode->i_ino);
 +      down(&EXT3_I(inode)->truncate_sem);
 +
 +      /* check in cache */
@@ -2087,11 +2081,11 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
 +                      newblock = iblock - ex->ee_block + ex->ee_start;
 +                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
++                                (int) iblock, ex->ee_block, ex->ee_len,
++                                newblock);
 +                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
++                                            ex->ee_len, ex->ee_start,
++                                            EXT3_EXT_CACHE_EXTENT);
 +                      goto out;
 +              }
 +      }
@@ -2112,7 +2106,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if (!newblock)
 +              goto out2;
 +      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
++                goal, newblock);
 +
 +      /* try to insert new extent into found leaf and return */
 +      newex.ee_block = iblock;
@@ -2130,7 +2124,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      __set_bit(BH_New, &bh_result->b_state);
 +
 +      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
++                            newex.ee_start, EXT3_EXT_CACHE_EXTENT);
 +out:
 +      ext3_ext_show_leaf(&tree, path);
 +      __set_bit(BH_Mapped, &bh_result->b_state);
@@ -2190,8 +2184,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      EXT3_I(inode)->i_disksize = inode->i_size;
 +      ext3_mark_inode_dirty(handle, inode);
 +
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
++      last_block = (inode->i_size + sb->s_blocksize - 1) >>
++                      EXT3_BLOCK_SIZE_BITS(sb);
 +      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
 +      
 +      /* In a multi-transaction truncate, we only make the final
@@ -2259,8 +2253,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      
 +static int
 +ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_ext_cache *newex)
++                       struct ext3_ext_path *path,
++                       struct ext3_ext_cache *newex)
 +{
 +      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
 +
@@ -2284,8 +2278,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_ext_cache *ex)
++                        struct ext3_ext_path *path,
++                        struct ext3_ext_cache *ex)
 +{
 +      struct ext3_extent_tree_stats *buf =
 +              (struct ext3_extent_tree_stats *) tree->private;
@@ -2302,7 +2296,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_ioctl(struct inode *inode, struct file *filp, unsigned int cmd,
-+              unsigned long arg)
++                 unsigned long arg)
 +{
 +      int err = 0;
 +
@@ -2322,7 +2316,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              tree.private = &buf;
 +              down(&EXT3_I(inode)->truncate_sem);
 +              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
++                                        ext3_ext_store_extent_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (err == 0)
 +                      err = buf.err;
@@ -2337,7 +2331,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              buf.leaf_num = 0;
 +              tree.private = &buf;
 +              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
++                                        ext3_ext_collect_stats_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (!err)
 +                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
@@ -2359,19 +2353,26 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +EXPORT_SYMBOL(ext3_ext_walk_space);
 +EXPORT_SYMBOL(ext3_ext_find_goal);
 +EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
 Index: linux-2.6.5-sles9/fs/ext3/ialloc.c
 ===================================================================
 --- linux-2.6.5-sles9.orig/fs/ext3/ialloc.c    2005-02-23 01:01:52.366281264 +0300
 +++ linux-2.6.5-sles9/fs/ext3/ialloc.c 2005-02-23 01:02:37.398435336 +0300
-@@ -647,6 +647,10 @@
+@@ -647,6 +647,18 @@
                DQUOT_FREE_INODE(inode);
                goto fail2;
        }
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              ext3_extents_initialize_blockmap(handle, inode);
-+      }
++      if (test_opt(sb, EXTENTS) && S_ISREG(inode->i_mode)) {
++              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
++              ext3_extents_initialize_blockmap(handle, inode);
++              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
++                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
++                      if (err) goto fail;
++                      EXT3_SET_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS);
++                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
++                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
++              }
++      }
++
        err = ext3_mark_inode_dirty(handle, inode);
        if (err) {
                ext3_std_error(sb, err);
@@ -2385,13 +2386,13 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
  
 +static inline int
 +ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create, int extend_disksize)
++                  struct buffer_head *bh, int create, int extend_disksize)
 +{
 +      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
 +              return ext3_ext_get_block(handle, inode, block, bh, create,
-+                                              extend_disksize);
++                                        extend_disksize);
 +      return ext3_get_block_handle(handle, inode, block, bh, create,
-+                                      extend_disksize);
++                                   extend_disksize);
 +}
 +
  static int ext3_get_block(struct inode *inode, sector_t iblock,
@@ -2404,7 +2405,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
 -      ret = ext3_get_block_handle(handle, inode, iblock,
 -                              bh_result, create, 1);
 +      ret = ext3_get_block_wrap(handle, inode, iblock,
-+                                      bh_result, create, 1);
++                                bh_result, create, 1);
        return ret;
  }
  
@@ -2415,7 +2416,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
 -              ret = ext3_get_block_handle(handle, inode, iblock,
 -                                      bh_result, create, 0);
 +              ret = ext3_get_block_wrap(handle, inode, iblock,
-+                                              bh_result, create, 0);
++                                        bh_result, create, 0);
        if (ret == 0)
                bh_result->b_size = (1 << inode->i_blkbits);
        return ret;
@@ -2451,9 +2452,9 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
        int indirects = (EXT3_NDIR_BLOCKS % bpp) ? 5 : 3;
        int ret;
  
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_writepage_trans_blocks(inode, bpp);
-+ 
++      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
++              return ext3_ext_writepage_trans_blocks(inode, bpp);
++
        if (ext3_should_journal_data(inode))
                ret = 3 * (bpp + indirects) + 2;
        else
@@ -2478,7 +2479,7 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        struct ext3_super_block *es = sbi->s_es;
        int i;
  
-+      ext3_ext_release(sb);
++      ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
        if (!(sb->s_flags & MS_RDONLY)) {
@@ -2526,8 +2527,8 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        percpu_counter_mod(&sbi->s_dirs_counter,
                ext3_count_dirs(sb));
  
-+      ext3_ext_init(sb);
-+ 
++      ext3_ext_init(sb);
++
        return 0;
  
  failed_mount3:
@@ -2550,14 +2551,17 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
 ===================================================================
 --- linux-2.6.5-sles9.orig/include/linux/ext3_fs.h     2005-02-23 01:02:35.823674736 +0300
 +++ linux-2.6.5-sles9/include/linux/ext3_fs.h  2005-02-23 01:02:37.414432904 +0300
-@@ -186,6 +186,7 @@
+@@ -186,8 +186,9 @@
+ #define EXT3_NOTAIL_FL                        0x00008000 /* don't merge file tail */
  #define EXT3_DIRSYNC_FL                       0x00010000 /* dirsync behaviour (directories only) */
  #define EXT3_TOPDIR_FL                        0x00020000 /* Top of directory hierarchies*/
- #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
 +#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
+ #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
  
- #define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
+-#define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
++#define EXT3_FL_USER_VISIBLE          0x000BDFFF /* User visible flags */
  #define EXT3_FL_USER_MODIFIABLE               0x000380FF /* User modifiable flags */
 @@ -211,6 +212,9 @@
  #endif
  #define EXT3_IOC_GETRSVSZ             _IOR('f', 5, long)
@@ -2577,6 +2581,21 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
  #ifndef clear_opt
+@@ -503,11 +509,13 @@
+ #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
+ #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
+ #define EXT3_FEATURE_INCOMPAT_META_BG         0x0010
++#define EXT3_FEATURE_INCOMPAT_EXTENTS         0x0040 /* extents support */
+ #define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
+ #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
+                                        EXT3_FEATURE_INCOMPAT_RECOVER| \
+-                                       EXT3_FEATURE_INCOMPAT_META_BG)
++                                       EXT3_FEATURE_INCOMPAT_META_BG| \
++                                       EXT3_FEATURE_INCOMPAT_EXTENTS)
+ #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
+                                        EXT3_FEATURE_RO_COMPAT_LARGE_FILE| \
+                                        EXT3_FEATURE_RO_COMPAT_BTREE_DIR)
 @@ -729,6 +735,7 @@
  
  
@@ -2592,7 +2611,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
 +/* extents.c */
 +extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
 +extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                              struct buffer_head *, int, int);
++                            struct buffer_head *, int, int);
 +extern void ext3_ext_truncate(struct inode *, struct page *);
 +extern void ext3_ext_init(struct super_block *);
 +extern void ext3_ext_release(struct super_block *);
@@ -2606,7 +2625,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 ===================================================================
 --- linux-2.6.5-sles9.orig/include/linux/ext3_extents.h        2005-02-17 22:07:57.023609040 +0300
 +++ linux-2.6.5-sles9/include/linux/ext3_extents.h     2005-02-23 01:02:37.416432600 +0300
-@@ -0,0 +1,265 @@
+@@ -0,0 +1,264 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -2648,7 +2667,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 + */
 +#define EXT_DEBUG_
 +#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
++#define ext_debug(tree,fmt,a...)                      \
 +do {                                                  \
 +      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
 +              printk(fmt, ##a);                       \
@@ -2761,14 +2780,14 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
 +      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
 +      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
++                                   struct ext3_extent *, unsigned long,
++                                   unsigned long);
 +      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
++                           struct ext3_extent *, unsigned long,
++                           unsigned long);
 +      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
++                       struct ext3_ext_path *, struct ext3_extent *,
++                       int *);
 +};
 +
 +/*
@@ -2778,8 +2797,8 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 + * callback must return valid extent (passed or newly created)
 + */
 +typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_ext_cache *);
++                                  struct ext3_ext_path *,
++                                  struct ext3_ext_cache *);
 +
 +#define EXT_CONTINUE  0
 +#define EXT_BREAK     1
@@ -2831,7 +2850,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +                      && depth != 0);                                 \
 +      BUG_ON((path)[0].p_depth != depth);                             \
 +}
-+      
++
 +
 +/*
 + * this structure is used to gather extents from the tree via ioctl
@@ -2853,13 +2872,13 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +      int leaf_num;
 +};
 +
++extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
 +extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
 +extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
 +extern int ext3_ext_walk_space(struct ext3_extents_tree *, unsigned long, unsigned long, ext_prepare_callback);
 +extern int ext3_ext_remove_space(struct ext3_extents_tree *, unsigned long, unsigned long);
 +extern struct ext3_ext_path * ext3_ext_find_extent(struct ext3_extents_tree *, int, struct ext3_ext_path *);
-+extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_ext_calc_blockmap_metadata(struct inode *, int);
 +
 +static inline void
@@ -2871,7 +2890,6 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +
 +
 +#endif /* _LINUX_EXT3_EXTENTS */
-+
 Index: linux-2.6.5-sles9/include/linux/ext3_fs_i.h
 ===================================================================
 --- linux-2.6.5-sles9.orig/include/linux/ext3_fs_i.h   2005-02-23 01:01:52.425272296 +0300
index 78c5d81..02745cc 100644 (file)
@@ -2,9 +2,9 @@ Index: linux-stage/fs/ext3/extents.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/extents.c 2005-02-25 15:33:48.890198160 +0200
 +++ linux-stage/fs/ext3/extents.c      2005-02-25 15:33:48.917194056 +0200
-@@ -0,0 +1,2313 @@
+@@ -0,0 +1,2347 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -48,6 +48,27 @@ Index: linux-stage/fs/ext3/extents.c
 +#include <linux/ext3_extents.h>
 +#include <asm/uaccess.h>
 +
++
++static inline int ext3_ext_check_header(struct ext3_extent_header *eh)
++{
++      if (eh->eh_magic != EXT3_EXT_MAGIC) {
++              printk(KERN_ERR "EXT3-fs: invalid magic = 0x%x\n",
++                     (unsigned)eh->eh_magic);
++              return -EIO;
++      }
++      if (eh->eh_max == 0) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_max = %u\n",
++                     (unsigned)eh->eh_max);
++              return -EIO;
++      }
++      if (eh->eh_entries > eh->eh_max) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_entries = %u\n",
++                     (unsigned)eh->eh_entries);
++              return -EIO;
++      }
++      return 0;
++}
++
 +static handle_t *ext3_ext_journal_restart(handle_t *handle, int needed)
 +{
 +      int err;
@@ -85,8 +106,8 @@ Index: linux-stage/fs/ext3/extents.c
 + *  - ENOMEM
 + */
 +static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_extents_tree *tree,
++                             struct ext3_ext_path *path)
 +{
 +      int err;
 +
@@ -107,7 +128,7 @@ Index: linux-stage/fs/ext3/extents.c
 + *  - EIO
 + */
 +static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                        struct ext3_ext_path *path)
 +{
 +      int err;
 +      if (path->p_bh) {
@@ -122,8 +143,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int inline
 +ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
++                 struct ext3_ext_path *path, struct ext3_extent *ex,
++                 int *err)
 +{
 +      int goal, depth, newblock;
 +      struct inode *inode;
@@ -142,7 +163,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              unsigned long colour;
 +
 +              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
++                          EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
 +                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
 +              colour = (current->pid % 16) *
 +                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
@@ -165,8 +186,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 6;
 +#endif
@@ -178,8 +199,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent_idx);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 5;
 +#endif
@@ -190,8 +211,8 @@ Index: linux-stage/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      sizeof(struct ext3_extent);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 3;
 +#endif
@@ -202,9 +223,8 @@ Index: linux-stage/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 4;
 +#endif
@@ -212,7 +232,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int k, l = path->p_depth;
@@ -221,12 +241,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      for (k = 0; k <= l; k++, path++) {
 +              if (path->p_idx) {
 +                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
++                                path->p_idx->ei_leaf);
 +              } else if (path->p_ext) {
 +                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
++                                path->p_ext->ee_block,
++                                path->p_ext->ee_len,
++                                path->p_ext->ee_start);
 +              } else
 +                      ext_debug(tree, "  []");
 +      }
@@ -235,7 +255,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int depth = EXT_DEPTH(tree);
@@ -251,7 +271,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +      for (i = 0; i < eh->eh_entries; i++, ex++) {
 +              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +      }
 +      ext_debug(tree, "\n");
 +#endif
@@ -262,11 +282,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      int depth = path->p_depth;
 +      int i;
 +
-+      for (i = 0; i <= depth; i++, path++)
++      for (i = 0; i <= depth; i++, path++) {
 +              if (path->p_bh) {
 +                      brelse(path->p_bh);
 +                      path->p_bh = NULL;
 +              }
++      }
 +}
 +
 +/*
@@ -274,7 +295,7 @@ Index: linux-stage/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                     struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent_idx *ix;
@@ -300,7 +321,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +      ix += l;
 +      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
++      ext_debug(tree," -> %d->%d ",path->p_idx->ei_block,path->p_idx->ei_leaf);
 +
 +      while (l++ < r) {
 +              if (block < ix->ei_block) 
@@ -308,7 +329,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              path->p_idx = ix++;
 +      }
 +      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -318,9 +339,9 @@ Index: linux-stage/fs/ext3/extents.c
 +              for (k = 0; k < eh->eh_entries; k++, ix++) {
 +                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
 +                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
++                                     ix, EXT_FIRST_INDEX(eh));
 +                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
++                                     ix->ei_block,ix[-1].ei_block);
 +                      }
 +                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
 +                      if (block < ix->ei_block) 
@@ -330,7 +351,6 @@ Index: linux-stage/fs/ext3/extents.c
 +              EXT_ASSERT(chix == path->p_idx);
 +      }
 +#endif
-+
 +}
 +
 +/*
@@ -338,7 +358,7 @@ Index: linux-stage/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                 struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent *ex;
@@ -372,7 +392,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      ex += l;
 +      path->p_ext = ex;
 +      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +      while (l++ < r) {
 +              if (block < ex->ee_block) 
@@ -380,7 +400,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              path->p_ext = ex++;
 +      }
 +      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -396,7 +416,6 @@ Index: linux-stage/fs/ext3/extents.c
 +              EXT_ASSERT(chex == path->p_ext);
 +      }
 +#endif
-+
 +}
 +
 +int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
@@ -417,7 +436,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +struct ext3_ext_path *
 +ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
++                   struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      struct buffer_head *bh;
@@ -429,15 +448,17 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +      eh = EXT_ROOT_HDR(tree);
 +      EXT_ASSERT(eh);
++      if (ext3_ext_check_header(eh))
++              goto err;
++
 +      i = depth = EXT_DEPTH(tree);
 +      EXT_ASSERT(eh->eh_max);
 +      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(i == 0 || eh->eh_entries > 0);
 +      
 +      /* account possible depth increase */
 +      if (!path) {
 +              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
++                             GFP_NOFS);
 +              if (!path)
 +                      return ERR_PTR(-ENOMEM);
 +      }
@@ -447,29 +468,34 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* walk through the tree */
 +      while (i) {
 +              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
++                        ppos, eh->eh_entries, eh->eh_max);
 +              ext3_ext_binsearch_idx(tree, path + ppos, block);
 +              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
 +              path[ppos].p_depth = i;
 +              path[ppos].p_ext = NULL;
 +
 +              bh = sb_bread(tree->inode->i_sb, path[ppos].p_block);
-+              if (!bh) {
-+                      ext3_ext_drop_refs(path);
-+                      kfree(path);
-+                      return ERR_PTR(-EIO);
-+              }
++              if (!bh)
++                      goto err;
++
 +              eh = EXT_BLOCK_HDR(bh);
 +              ppos++;
 +              EXT_ASSERT(ppos <= depth);
 +              path[ppos].p_bh = bh;
 +              path[ppos].p_hdr = eh;
 +              i--;
++
++              if (ext3_ext_check_header(eh))
++                      goto err;
 +      }
 +
 +      path[ppos].p_depth = i;
 +      path[ppos].p_hdr = eh;
 +      path[ppos].p_ext = NULL;
++      path[ppos].p_idx = NULL;
++
++      if (ext3_ext_check_header(eh))
++              goto err;
 +
 +      /* find extent */
 +      ext3_ext_binsearch(tree, path + ppos, block);
@@ -477,6 +503,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      ext3_ext_show_path(tree, path);
 +
 +      return path;
++
++err:
++      printk(KERN_ERR "EXT3-fs: header is corrupted!\n");
++      ext3_ext_drop_refs(path);
++      kfree(path);
++      return ERR_PTR(-EIO);
 +}
 +
 +/*
@@ -484,9 +516,9 @@ Index: linux-stage/fs/ext3/extents.c
 + * it check where to insert: before curp or after curp
 + */
 +static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *curp,
++                               int logical, int ptr)
 +{
 +      struct ext3_extent_idx *ix;
 +      int len, err;
@@ -502,9 +534,9 @@ Index: linux-stage/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent_idx);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
++                                "move %d from 0x%p to 0x%p\n",
++                                logical, ptr, len,
++                                (curp->p_idx + 1), (curp->p_idx + 2));
 +                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
 +              }
 +              ix = curp->p_idx + 1;
@@ -513,9 +545,9 @@ Index: linux-stage/fs/ext3/extents.c
 +              len = len * sizeof(struct ext3_extent_idx);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
++                        "move %d from 0x%p to 0x%p\n",
++                        logical, ptr, len,
++                        curp->p_idx, (curp->p_idx + 1));
 +              memmove(curp->p_idx + 1, curp->p_idx, len);
 +              ix = curp->p_idx;
 +      }
@@ -543,8 +575,8 @@ Index: linux-stage/fs/ext3/extents.c
 + *  - initialize subtree
 + */
 +static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
++                        struct ext3_ext_path *path,
++                        struct ext3_extent *newext, int at)
 +{
 +      struct buffer_head *bh = NULL;
 +      int depth = EXT_DEPTH(tree);
@@ -565,13 +597,13 @@ Index: linux-stage/fs/ext3/extents.c
 +      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              border = path[depth].p_ext[1].ee_block;
 +              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      } else {
 +              border = newext->ee_block;
 +              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      }
 +
 +      /* 
@@ -629,12 +661,11 @@ Index: linux-stage/fs/ext3/extents.c
 +      while (path[depth].p_ext <=
 +                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
++                        path[depth].p_ext->ee_block,
++                        path[depth].p_ext->ee_start,
++                        path[depth].p_ext->ee_len,
++                        newblock);
++              memmove(ex++, path[depth].p_ext++, sizeof(struct ext3_extent));
 +              neh->eh_entries++;
 +              m++;
 +      }
@@ -687,21 +718,21 @@ Index: linux-stage/fs/ext3/extents.c
 +              fidx->ei_leaf = oldblock;
 +
 +              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
++                        i, newblock, border, oldblock);
 +              /* copy indexes */
 +              m = 0;
 +              path[i].p_idx++;
 +
 +              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
++                        EXT_MAX_INDEX(path[i].p_hdr));
 +              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
++                         EXT_LAST_INDEX(path[i].p_hdr));
 +              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
 +                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
++                                i, path[i].p_idx->ei_block,
++                                path[i].p_idx->ei_leaf, newblock);
 +                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
++                              sizeof(struct ext3_extent_idx));
 +                      neh->eh_entries++;
 +                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
 +                      m++;
@@ -731,7 +762,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* insert new index */
 +      if (!err)
 +              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
++                                          border, newblock);
 +
 +cleanup:
 +      if (bh) {
@@ -761,9 +792,9 @@ Index: linux-stage/fs/ext3/extents.c
 + *    just created block
 + */
 +static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *path,
++                               struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp = path;
 +      struct ext3_extent_header *neh;
@@ -795,7 +826,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* set size of new block */
 +      neh = EXT_BLOCK_HDR(bh);
 +      /* old root could have indexes or leaves
-+       * so calculate e_max right way */
++       * so calculate eh_max right way */
 +      if (EXT_DEPTH(tree))
 +              neh->eh_max = ext3_ext_space_block_idx(tree);
 +      else
@@ -822,7 +853,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      neh = EXT_ROOT_HDR(tree);
 +      fidx = EXT_FIRST_INDEX(neh);
 +      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
++                neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
 +
 +      neh->eh_depth = path->p_depth + 1;
 +      err = ext3_ext_dirty(handle, tree, curp);
@@ -837,9 +868,9 @@ Index: linux-stage/fs/ext3/extents.c
 + * then it requests in-depth growing
 + */
 +static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                                  struct ext3_extents_tree *tree,
++                                  struct ext3_ext_path *path,
++                                  struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp;
 +      int depth, i, err = 0;
@@ -915,12 +946,12 @@ Index: linux-stage/fs/ext3/extents.c
 +              if (depth == path->p_depth) {
 +                      /* leaf */
 +                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
++                          EXT_LAST_EXTENT(path[depth].p_hdr))
 +                              return path[depth].p_ext[1].ee_block;
 +              } else {
 +                      /* index */
 +                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
++                          EXT_LAST_INDEX(path[depth].p_hdr))
 +                              return path[depth].p_idx[1].ei_block;
 +              }
 +              depth--;        
@@ -933,7 +964,7 @@ Index: linux-stage/fs/ext3/extents.c
 + * returns first allocated block from next leaf or EXT_MAX_BLOCK
 + */
 +static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
++                                       struct ext3_ext_path *path)
 +{
 +      int depth;
 +
@@ -949,7 +980,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      
 +      while (depth >= 0) {
 +              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
++                  EXT_LAST_INDEX(path[depth].p_hdr))
 +                      return path[depth].p_idx[1].ei_block;
 +              depth--;        
 +      }
@@ -963,7 +994,7 @@ Index: linux-stage/fs/ext3/extents.c
 + * TODO: do we need to correct tree in all cases?
 + */
 +int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                           struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      int depth = EXT_DEPTH(tree);    
@@ -1013,8 +1044,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int inline
 +ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                         struct ext3_extent *ex1,
++                         struct ext3_extent *ex2)
 +{
 +      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
 +              return 0;
@@ -1036,8 +1067,8 @@ Index: linux-stage/fs/ext3/extents.c
 + * creating new leaf in no-space case
 + */
 +int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
++                         struct ext3_ext_path *path,
++                         struct ext3_extent *newext)
 +{
 +      struct ext3_extent_header * eh;
 +      struct ext3_extent *ex, *fex;
@@ -1046,7 +1077,6 @@ Index: linux-stage/fs/ext3/extents.c
 +      int depth, len, err, next;
 +
 +      EXT_ASSERT(newext->ee_len > 0);
-+      EXT_ASSERT(newext->ee_len < EXT_CACHE_MARK);
 +      depth = EXT_DEPTH(tree);
 +      ex = path[depth].p_ext;
 +      EXT_ASSERT(path[depth].p_hdr);
@@ -1054,8 +1084,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* try to insert block into found extent and return */
 +      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
 +              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
++                        newext->ee_len, ex->ee_block, ex->ee_len,
++                        ex->ee_start);
 +              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
 +                      return err;
 +              ex->ee_len += newext->ee_len;
@@ -1083,12 +1113,12 @@ Index: linux-stage/fs/ext3/extents.c
 +              eh = npath[depth].p_hdr;
 +              if (eh->eh_entries < eh->eh_max) {
 +                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
++                                eh->eh_entries);
 +                      path = npath;
 +                      goto repeat;
 +              }
 +              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
++                        eh->eh_entries, eh->eh_max);
 +      }
 +
 +      /*
@@ -1110,8 +1140,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      if (!nearex) {
 +              /* there is no extent in this leaf, create first one */
 +              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
++                        newext->ee_block, newext->ee_start,
++                        newext->ee_len);
 +              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
 +      } else if (newext->ee_block > nearex->ee_block) {
 +              EXT_ASSERT(newext->ee_block != nearex->ee_block);
@@ -1120,10 +1150,10 @@ Index: linux-stage/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
++                                "move %d from 0x%p to 0x%p\n",
++                                newext->ee_block, newext->ee_start,
++                                newext->ee_len,
++                                nearex, len, nearex + 1, nearex + 2);
 +                      memmove(nearex + 2, nearex + 1, len);
 +              }
 +              path[depth].p_ext = nearex + 1;
@@ -1132,9 +1162,9 @@ Index: linux-stage/fs/ext3/extents.c
 +              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
++                        "move %d from 0x%p to 0x%p\n",
++                        newext->ee_block, newext->ee_start, newext->ee_len,
++                        nearex, len, nearex + 1, nearex + 2);
 +              memmove(nearex + 1, nearex, len);
 +              path[depth].p_ext = nearex;
 +      }
@@ -1155,8 +1185,8 @@ Index: linux-stage/fs/ext3/extents.c
 +              /* merge with next extent! */
 +              nearex->ee_len += nearex[1].ee_len;
 +              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
++                      len = (EXT_LAST_EXTENT(eh) - nearex - 1) *
++                              sizeof(struct ext3_extent);
 +                      memmove(nearex + 1, nearex + 2, len);
 +              }
 +              eh->eh_entries--;
@@ -1186,7 +1216,8 @@ Index: linux-stage/fs/ext3/extents.c
 +                      unsigned long num, ext_prepare_callback func)
 +{
 +      struct ext3_ext_path *path = NULL;
-+      struct ext3_extent *ex, cbex;
++      struct ext3_ext_cache cbex;
++      struct ext3_extent *ex;
 +      unsigned long next, start = 0, end = 0;
 +      unsigned long last = block + num;
 +      int depth, exists, err = 0;
@@ -1245,14 +1276,20 @@ Index: linux-stage/fs/ext3/extents.c
 +              EXT_ASSERT(end > start);
 +
 +              if (!exists) {
-+                      cbex.ee_block = start;
-+                      cbex.ee_len = end - start;
-+                      cbex.ee_start = 0;
-+              } else
-+                      cbex = *ex;
++                      cbex.ec_block = start;
++                      cbex.ec_len = end - start;
++                      cbex.ec_start = 0;
++                      cbex.ec_type = EXT3_EXT_CACHE_GAP;
++              } else {
++                      cbex.ec_block = ex->ee_block;
++                      cbex.ec_len = ex->ee_len;
++                      cbex.ec_start = ex->ee_start;
++                      cbex.ec_type = EXT3_EXT_CACHE_EXTENT;
++              }
 +
++              EXT_ASSERT(cbex.ec_len > 0);
 +              EXT_ASSERT(path[depth].p_hdr);
-+              err = func(tree, path, &cbex, exists);
++              err = func(tree, path, &cbex);
 +              ext3_ext_drop_refs(path);
 +
 +              if (err < 0)
@@ -1270,7 +1307,7 @@ Index: linux-stage/fs/ext3/extents.c
 +                      path = NULL;
 +              }
 +
-+              block = cbex.ee_block + cbex.ee_len;
++              block = cbex.ec_block + cbex.ec_len;
 +      }
 +
 +      if (path) {
@@ -1283,7 +1320,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static inline void
 +ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
++                    __u32 len, __u32 start, int type)
 +{
 +      EXT_ASSERT(len > 0);
 +      if (tree->cex) {
@@ -1300,8 +1337,8 @@ Index: linux-stage/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
++                        struct ext3_ext_path *path,
++                        unsigned long block)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      unsigned long lblock, len;
@@ -1320,16 +1357,16 @@ Index: linux-stage/fs/ext3/extents.c
 +              lblock = block;
 +              len = ex->ee_block - block;
 +              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len);
 +      } else if (block >= ex->ee_block + ex->ee_len) {
 +              lblock = ex->ee_block + ex->ee_len;
 +              len = ext3_ext_next_allocated_block(path);
 +              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) block);
 +              EXT_ASSERT(len > lblock);
 +              len = len - lblock;
 +      } else {
@@ -1343,7 +1380,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static inline int
 +ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
++                struct ext3_extent *ex)
 +{
 +      struct ext3_ext_cache *cex = tree->cex;
 +
@@ -1356,16 +1393,16 @@ Index: linux-stage/fs/ext3/extents.c
 +              return EXT3_EXT_CACHE_NO;
 +
 +      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
++                 cex->ec_type == EXT3_EXT_CACHE_EXTENT);
 +      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
 +              ex->ee_block = cex->ec_block;
 +              ex->ee_start = cex->ec_start;
 +              ex->ee_len = cex->ec_len;
 +              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) ex->ee_start);
 +              return cex->ec_type;
 +      }
 +
@@ -1379,7 +1416,7 @@ Index: linux-stage/fs/ext3/extents.c
 + * last index in the block only
 + */
 +int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
++                  struct ext3_ext_path *path)
 +{
 +      struct buffer_head *bh;
 +      int err;
@@ -1393,7 +1430,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      if ((err = ext3_ext_dirty(handle, tree, path)))
 +              return err;
 +      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +      bh = sb_find_get_block(tree->inode->i_sb, path->p_idx->ei_leaf);
 +      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
 +      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
@@ -1401,7 +1438,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
++                                   struct ext3_ext_path *path)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      int needed;
@@ -1438,8 +1475,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++                    struct ext3_ext_path *path, unsigned long start,
++                    unsigned long end)
 +{
 +      struct ext3_extent *ex, tex;
 +      struct ext3_ext_path *npath;
@@ -1473,7 +1510,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* FIXME: some callback to free underlying resource
 +       * and correct ee_start? */
 +      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
++                ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
 +
 +      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
 +      if (IS_ERR(npath))
@@ -1487,13 +1524,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      kfree(npath);
 +
 +      return err;
-+                      
 +}
 +
 +static int
 +ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++               struct ext3_ext_path *path, unsigned long start,
++               unsigned long end)
 +{
 +      struct ext3_extent *ex, *fu = NULL, *lu, *le;
 +      int err = 0, correct_index = 0;
@@ -1526,8 +1562,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      }
 +      
 +      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
++      while (ex >= EXT_FIRST_EXTENT(eh) && ex->ee_block + ex->ee_len > start) {
 +              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
 +              path[depth].p_ext = ex;
 +      
@@ -1554,7 +1589,7 @@ Index: linux-stage/fs/ext3/extents.c
 +                      block = ex->ee_block; 
 +                      num = 0;
 +                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
++                                 b == ex->ee_block + ex->ee_len - 1);
 +              }
 +
 +              if (ex == EXT_FIRST_EXTENT(eh))
@@ -1596,7 +1631,7 @@ Index: linux-stage/fs/ext3/extents.c
 +                      goto out;
 +
 +              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +              ex--;
 +      }
 +
@@ -1660,7 +1695,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
++                        unsigned long start, unsigned long end)
 +{
 +      struct inode *inode = tree->inode;
 +      struct super_block *sb = inode->i_sb;
@@ -1684,8 +1719,7 @@ Index: linux-stage/fs/ext3/extents.c
 +       */
 +      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
 +      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
++              ext3_error(sb, __FUNCTION__, "Can't allocate path array");
 +              ext3_journal_stop(handle);
 +              return -ENOMEM;
 +      }
@@ -1717,19 +1751,19 @@ Index: linux-stage/fs/ext3/extents.c
 +                              ext3_ext_last_covered(path[i].p_hdr, end);
 +                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
 +                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
++                                path[i].p_hdr, path[i].p_hdr->eh_entries);
 +              } else {
 +                      /* we've already was here, see at next index */
 +                      path[i].p_idx--;
 +              }
 +
 +              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
++                        i, EXT_FIRST_INDEX(path[i].p_hdr),
++                        path[i].p_idx);
 +              if (ext3_ext_more_to_rm(path + i)) {
 +                      /* go to the next level */
 +                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
++                                i + 1, path[i].p_idx->ei_leaf);
 +                      memset(path + i + 1, 0, sizeof(*path));
 +                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
 +                      if (!path[i+1].p_bh) {
@@ -1852,7 +1886,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                           struct ext3_extent *ex2)
 +{
 +      /* FIXME: support for large fs */
 +      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
@@ -1862,8 +1896,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                         struct ext3_extent *ex,
++                         unsigned long from, unsigned long to)
 +{
 +      int needed;
 +      
@@ -1878,8 +1912,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                 struct ext3_extent *ex,
++                 unsigned long from, unsigned long to)
 +{
 +      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
 +      handle_t *handle = ext3_journal_start(tree->inode, needed);
@@ -1894,7 +1928,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              num = ex->ee_block + ex->ee_len - from;
 +              start = ex->ee_start + ex->ee_len - num;
 +              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
++                        num, start);
 +              for (i = 0; i < num; i++) {
 +                      bh = sb_find_get_block(tree->inode->i_sb, start + i);
 +                      ext3_forget(handle, 0, tree->inode, bh, start + i);
@@ -1902,17 +1936,17 @@ Index: linux-stage/fs/ext3/extents.c
 +              ext3_free_blocks(handle, tree->inode, start, num);
 +      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
 +              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      } else {
 +              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      }
 +      ext3_journal_stop(handle);
 +      return 0;
 +}
 +
 +static int ext3_ext_find_goal(struct inode *inode,
-+                              struct ext3_ext_path *path, unsigned long block)
++                            struct ext3_ext_path *path, unsigned long block)
 +{
 +      struct ext3_inode_info *ei = EXT3_I(inode);
 +      unsigned long bg_start;
@@ -1942,8 +1976,8 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
++                           struct ext3_ext_path *path,
++                           struct ext3_extent *ex, int *err)
 +{
 +      struct inode *inode = tree->inode;
 +      int newblock, goal;
@@ -1980,7 +2014,7 @@ Index: linux-stage/fs/ext3/extents.c
 +};
 +
 +void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
++                       struct inode *inode)
 +{
 +      tree->inode = inode;
 +      tree->root = (void *) EXT3_I(inode)->i_data;
@@ -1991,8 +2025,8 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result,
-+                      int create, int extend_disksize)
++                     long iblock, struct buffer_head *bh_result,
++                     int create, int extend_disksize)
 +{
 +      struct ext3_ext_path *path = NULL;
 +      struct ext3_extent newex;
@@ -2003,7 +2037,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      clear_buffer_new(bh_result);
 +      ext3_init_tree_desc(&tree, inode);
 +      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
++                (int) iblock, (unsigned) inode->i_ino);
 +      down(&EXT3_I(inode)->truncate_sem);
 +
 +      /* check in cache */
@@ -2046,11 +2080,11 @@ Index: linux-stage/fs/ext3/extents.c
 +              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
 +                      newblock = iblock - ex->ee_block + ex->ee_start;
 +                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
++                                (int) iblock, ex->ee_block, ex->ee_len,
++                                newblock);
 +                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
++                                            ex->ee_len, ex->ee_start,
++                                            EXT3_EXT_CACHE_EXTENT);
 +                      goto out;
 +              }
 +      }
@@ -2071,7 +2105,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      if (!newblock)
 +              goto out2;
 +      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
++                goal, newblock);
 +
 +      /* try to insert new extent into found leaf and return */
 +      newex.ee_block = iblock;
@@ -2089,7 +2123,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      set_buffer_new(bh_result);
 +
 +      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
++                            newex.ee_start, EXT3_EXT_CACHE_EXTENT);
 +out:
 +      ext3_ext_show_leaf(&tree, path);
 +      map_bh(bh_result, inode->i_sb, newblock);
@@ -2147,8 +2181,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      EXT3_I(inode)->i_disksize = inode->i_size;
 +      ext3_mark_inode_dirty(handle, inode);
 +
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
++      last_block = (inode->i_size + sb->s_blocksize - 1) >>
++                      EXT3_BLOCK_SIZE_BITS(sb);
 +      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
 +      
 +      /* In a multi-transaction truncate, we only make the final
@@ -2216,13 +2250,14 @@ Index: linux-stage/fs/ext3/extents.c
 +      
 +static int
 +ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *newex, int exist)
++                       struct ext3_ext_path *path,
++                       struct ext3_ext_cache *newex)
 +{
 +      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
 +
-+      if (!exist)
++      if (newex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
++
 +      if (buf->err < 0)
 +              return EXT_BREAK;
 +      if (buf->cur - buf->buffer + sizeof(*newex) > buf->buflen)
@@ -2240,14 +2275,14 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *ex, int exist)
++                        struct ext3_ext_path *path,
++                        struct ext3_ext_cache *ex)
 +{
 +      struct ext3_extent_tree_stats *buf =
 +              (struct ext3_extent_tree_stats *) tree->private;
 +      int depth;
 +
-+      if (!exist)
++      if (ex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
 +
 +      depth = EXT_DEPTH(tree);
@@ -2278,7 +2313,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              tree.private = &buf;
 +              down(&EXT3_I(inode)->truncate_sem);
 +              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
++                                        ext3_ext_store_extent_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (err == 0)
 +                      err = buf.err;
@@ -2293,7 +2328,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              buf.leaf_num = 0;
 +              tree.private = &buf;
 +              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
++                                        ext3_ext_collect_stats_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (!err)
 +                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
@@ -2315,19 +2350,26 @@ Index: linux-stage/fs/ext3/extents.c
 +EXPORT_SYMBOL(ext3_ext_walk_space);
 +EXPORT_SYMBOL(ext3_ext_find_goal);
 +EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
 Index: linux-stage/fs/ext3/ialloc.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/ialloc.c  2005-02-25 14:50:50.304202816 +0200
 +++ linux-stage/fs/ext3/ialloc.c       2005-02-25 15:33:48.920193600 +0200
-@@ -646,6 +646,10 @@
+@@ -646,6 +646,18 @@
                DQUOT_FREE_INODE(inode);
                goto fail2;
        }
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              ext3_extents_initialize_blockmap(handle, inode);
-+      }
++      if (test_opt(sb, EXTENTS) && S_ISREG(inode->i_mode)) {
++              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
++              ext3_extents_initialize_blockmap(handle, inode);
++              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
++                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
++                      if (err) goto fail;
++                      EXT3_SET_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS);
++                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
++                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
++              }
++      }
++
        err = ext3_mark_inode_dirty(handle, inode);
        if (err) {
                ext3_std_error(sb, err);
@@ -2341,13 +2383,13 @@ Index: linux-stage/fs/ext3/inode.c
  
 +static inline int
 +ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create, int extend_disksize)
++                  struct buffer_head *bh, int create, int extend_disksize)
 +{
 +      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
 +              return ext3_ext_get_block(handle, inode, block, bh, create,
-+                                              extend_disksize);
++                                        extend_disksize);
 +      return ext3_get_block_handle(handle, inode, block, bh, create,
-+                                      extend_disksize);
++                                   extend_disksize);
 +}
 +
  static int ext3_get_block(struct inode *inode, sector_t iblock,
@@ -2360,7 +2402,7 @@ Index: linux-stage/fs/ext3/inode.c
 -      ret = ext3_get_block_handle(handle, inode, iblock,
 -                              bh_result, create, 1);
 +      ret = ext3_get_block_wrap(handle, inode, iblock,
-+                                      bh_result, create, 1);
++                                bh_result, create, 1);
        return ret;
  }
  
@@ -2405,9 +2447,9 @@ Index: linux-stage/fs/ext3/inode.c
        int indirects = (EXT3_NDIR_BLOCKS % bpp) ? 5 : 3;
        int ret;
  
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_writepage_trans_blocks(inode, bpp);
-+ 
++      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
++              return ext3_ext_writepage_trans_blocks(inode, bpp);
++
        if (ext3_should_journal_data(inode))
                ret = 3 * (bpp + indirects) + 2;
        else
@@ -2432,18 +2474,16 @@ Index: linux-stage/fs/ext3/super.c
        struct ext3_super_block *es = sbi->s_es;
        int i;
  
-+      ext3_ext_release(sb);
++      ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
        if (!(sb->s_flags & MS_RDONLY)) {
-@@ -457,6 +458,10 @@
+@@ -457,6 +458,8 @@
  #endif
        ei->i_rsv_window.rsv_end = EXT3_RESERVE_WINDOW_NOT_ALLOCATED;
        ei->vfs_inode.i_version = 1;
-+      ei->i_cached_extent[0] = 0;
-+      ei->i_cached_extent[1] = 0;
-+      ei->i_cached_extent[2] = 0;
-+      ei->i_cached_extent[3] = 0;
++      
++      memset(&ei->i_cached_extent, 0, sizeof(ei->i_cached_extent));
        return &ei->vfs_inode;
  }
  
@@ -2482,8 +2522,8 @@ Index: linux-stage/fs/ext3/super.c
        percpu_counter_mod(&sbi->s_dirs_counter,
                ext3_count_dirs(sb));
  
-+      ext3_ext_init(sb);
-+ 
++      ext3_ext_init(sb);
++
        return 0;
  
  failed_mount3:
@@ -2506,14 +2546,17 @@ Index: linux-stage/include/linux/ext3_fs.h
 ===================================================================
 --- linux-stage.orig/include/linux/ext3_fs.h   2005-02-25 14:53:56.424908168 +0200
 +++ linux-stage/include/linux/ext3_fs.h        2005-02-25 15:39:12.841950008 +0200
-@@ -186,6 +186,7 @@
+@@ -186,8 +186,9 @@
  #define EXT3_DIRSYNC_FL                       0x00010000 /* dirsync behaviour (directories only) */
  #define EXT3_TOPDIR_FL                        0x00020000 /* Top of directory hierarchies*/
  #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
 +#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
  
- #define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
+-#define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
++#define EXT3_FL_USER_VISIBLE          0x000BDFFF /* User visible flags */
  #define EXT3_FL_USER_MODIFIABLE               0x000380FF /* User modifiable flags */
+ /*
 @@ -237,6 +238,9 @@
  #endif
  #define EXT3_IOC_GETRSVSZ             _IOR('f', 5, long)
@@ -2524,16 +2567,30 @@ Index: linux-stage/include/linux/ext3_fs.h
  
  /*
   * Structure of an inode on the disk
-@@ -359,6 +363,9 @@
+@@ -359,6 +363,8 @@
  #define EXT3_MOUNT_RESERVATION                0x20000 /* Preallocation */
  #define EXT3_MOUNT_IOPEN              0x40000 /* Allow access via iopen */
  #define EXT3_MOUNT_IOPEN_NOPRIV               0x80000 /* Make iopen world-readable */
 +#define EXT3_MOUNT_EXTENTS            0x100000/* Extents support */
 +#define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
-+
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
  #ifndef _LINUX_EXT2_FS_H
+@@ -503,11 +509,13 @@
+ #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
+ #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
+ #define EXT3_FEATURE_INCOMPAT_META_BG         0x0010
++#define EXT3_FEATURE_INCOMPAT_EXTENTS         0x0040 /* extents support */
+ #define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
+ #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
+                                        EXT3_FEATURE_INCOMPAT_RECOVER| \
+-                                       EXT3_FEATURE_INCOMPAT_META_BG)
++                                       EXT3_FEATURE_INCOMPAT_META_BG| \
++                                       EXT3_FEATURE_INCOMPAT_EXTENTS)
+ #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
+                                        EXT3_FEATURE_RO_COMPAT_LARGE_FILE| \
+                                        EXT3_FEATURE_RO_COMPAT_BTREE_DIR)
 @@ -756,6 +763,7 @@
  
  
@@ -2549,7 +2606,7 @@ Index: linux-stage/include/linux/ext3_fs.h
 +/* extents.c */
 +extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
 +extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                              struct buffer_head *, int, int);
++                            struct buffer_head *, int, int);
 +extern void ext3_ext_truncate(struct inode *, struct page *);
 +extern void ext3_ext_init(struct super_block *);
 +extern void ext3_ext_release(struct super_block *);
@@ -2563,7 +2620,7 @@ Index: linux-stage/include/linux/ext3_extents.h
 ===================================================================
 --- linux-stage.orig/include/linux/ext3_extents.h      2005-02-25 15:33:48.891198008 +0200
 +++ linux-stage/include/linux/ext3_extents.h   2005-02-25 15:33:48.944189952 +0200
-@@ -0,0 +1,252 @@
+@@ -0,0 +1,264 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -2605,7 +2662,7 @@ Index: linux-stage/include/linux/ext3_extents.h
 + */
 +#define EXT_DEBUG_
 +#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
++#define ext_debug(tree,fmt,a...)                      \
 +do {                                                  \
 +      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
 +              printk(fmt, ##a);                       \
@@ -2718,14 +2775,14 @@ Index: linux-stage/include/linux/ext3_extents.h
 +      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
 +      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
 +      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
++                                   struct ext3_extent *, unsigned long,
++                                   unsigned long);
 +      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
++                           struct ext3_extent *, unsigned long,
++                           unsigned long);
 +      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
++                       struct ext3_ext_path *, struct ext3_extent *,
++                       int *);
 +};
 +
 +/*
@@ -2735,8 +2792,8 @@ Index: linux-stage/include/linux/ext3_extents.h
 + * callback must return valid extent (passed or newly created)
 + */
 +typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_extent *, int);
++                                  struct ext3_ext_path *,
++                                  struct ext3_ext_cache *);
 +
 +#define EXT_CONTINUE  0
 +#define EXT_BREAK     1
@@ -2744,7 +2801,6 @@ Index: linux-stage/include/linux/ext3_extents.h
 +
 +
 +#define EXT_MAX_BLOCK 0xffffffff
-+#define EXT_CACHE_MARK        0xffff
 +
 +
 +#define EXT_FIRST_EXTENT(__hdr__) \
@@ -2776,6 +2832,20 @@ Index: linux-stage/include/linux/ext3_extents.h
 +
 +#define EXT_ASSERT(__x__) if (!(__x__)) BUG();
 +
++#define EXT_CHECK_PATH(tree,path)                                     \
++{                                                                     \
++      int depth = EXT_DEPTH(tree);                                    \
++      BUG_ON((unsigned long) (path) < __PAGE_OFFSET);                 \
++      BUG_ON((unsigned long) (path)[depth].p_idx <                    \
++                      __PAGE_OFFSET && (path)[depth].p_idx != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_ext <                    \
++                      __PAGE_OFFSET && (path)[depth].p_ext != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_hdr < __PAGE_OFFSET);    \
++      BUG_ON((unsigned long) (path)[depth].p_bh < __PAGE_OFFSET       \
++                      && depth != 0);                                 \
++      BUG_ON((path)[0].p_depth != depth);                             \
++}
++
 +
 +/*
 + * this structure is used to gather extents from the tree via ioctl
@@ -2797,13 +2867,13 @@ Index: linux-stage/include/linux/ext3_extents.h
 +      int leaf_num;
 +};
 +
++extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
 +extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
 +extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
 +extern int ext3_ext_walk_space(struct ext3_extents_tree *, unsigned long, unsigned long, ext_prepare_callback);
 +extern int ext3_ext_remove_space(struct ext3_extents_tree *, unsigned long, unsigned long);
 +extern struct ext3_ext_path * ext3_ext_find_extent(struct ext3_extents_tree *, int, struct ext3_ext_path *);
-+extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_ext_calc_blockmap_metadata(struct inode *, int);
 +
 +static inline void
@@ -2815,7 +2885,6 @@ Index: linux-stage/include/linux/ext3_extents.h
 +
 +
 +#endif /* _LINUX_EXT3_EXTENTS */
-+
 Index: linux-stage/include/linux/ext3_fs_i.h
 ===================================================================
 --- linux-stage.orig/include/linux/ext3_fs_i.h 2005-02-25 14:50:50.320200384 +0200
@@ -2825,7 +2894,7 @@ Index: linux-stage/include/linux/ext3_fs_i.h
        struct semaphore truncate_sem;
        struct inode vfs_inode;
 +
-+      __u32 i_cached_extent[4];
++      __u32 i_cached_extent[4];
  };
  
  #endif        /* _LINUX_EXT3_FS_I */
index 82957f1..b9bcfac 100644 (file)
@@ -1,10 +1,10 @@
-Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
+Index: linux-2.6.5-suse/fs/ext3/mballoc.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/mballoc.c   2005-02-17 22:07:57.023609040 +0300
-+++ linux-2.6.5-sles9/fs/ext3/mballoc.c        2005-02-23 01:56:19.101662000 +0300
-@@ -0,0 +1,1835 @@
+--- linux-2.6.5-suse.orig/fs/ext3/mballoc.c    2005-03-02 22:42:20.659360368 +0300
++++ linux-2.6.5-suse/fs/ext3/mballoc.c 2005-03-11 16:13:13.000000000 +0300
+@@ -0,0 +1,1863 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -39,6 +39,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +/*
 + * TODO:
++ *   - bitmap/buddy read-ahead (proposed by Oleg Drokin aka green)
 + *   - track min/max extents in each group for better group selection
 + *   - is it worthwhile to use buddies directly if req is 2^N blocks?
 + *   - mb_mark_used() may allocate chunk right after splitting buddy
@@ -96,7 +97,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      __u32   mh_magic;
 +};
 +
-+#define EXT3_MB_MAGIC_V1      0xbaad16fc
++#define EXT3_MB_MAGIC_V1      0xbabd16fd
 +
 +
 +struct ext3_free_extent {
@@ -109,7 +110,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      struct super_block *ac_sb;
 +
 +      /* search goals */
-+struct ext3_free_extent ac_g_ex;
++      struct ext3_free_extent ac_g_ex;
 +      
 +      /* the best found extent */
 +      struct ext3_free_extent ac_b_ex;
@@ -148,47 +149,50 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +void ext3_mb_poll_new_transaction(struct super_block *, handle_t *);
 +void ext3_mb_free_committed_blocks(struct super_block *);
 +
-+#define mb_correct_addr_and_bit(bit,addr)     \
-+{                                             \
-+      if ((unsigned long)addr & 1) {          \
-+              bit += 8;                       \
-+              addr--;                         \
-+      }                                       \
-+      if ((unsigned long)addr & 2) {          \
-+              bit += 16;                      \
-+              addr--;                         \
-+              addr--;                         \
-+      }                                       \
++#if BITS_PER_LONG == 64
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 7UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~7UL);  \
 +}
++#elif BITS_PER_LONG == 32
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 3UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~3UL);  \
++}
++#else
++#error "how many bits you are?!"
++#endif
 +
 +static inline int mb_test_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      return test_bit(bit, addr);
++      return ext2_test_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __set_bit(bit, addr);
++      ext2_set_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      set_bit(bit, addr);
++      ext2_set_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void mb_clear_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __clear_bit(bit, addr);
++      ext2_clear_bit(bit, addr);
 +}
 +
 +static inline void mb_clear_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      clear_bit(bit, addr);
++      ext2_clear_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void *mb_find_buddy(struct ext3_buddy *e3b, int order, int *max)
@@ -199,8 +203,10 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      J_ASSERT(EXT3_MB_BITMAP(e3b) != EXT3_MB_BUDDY(e3b));
 +      J_ASSERT(max != NULL);
 +
-+      if (order > e3b->bd_blkbits + 1)
++      if (order > e3b->bd_blkbits + 1) {
++              *max = 0;
 +              return NULL;
++      }
 +
 +      /* at order 0 we see each particular block */
 +      *max = 1 << (e3b->bd_blkbits + 3);
@@ -234,12 +240,6 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh)) {
-+              ll_rw_block(READ, 1, &e3b->bd_bh);
-+              wait_on_buffer(e3b->bd_bh);
-+      }
-+      J_ASSERT(buffer_uptodate(e3b->bd_bh));
-+
 +      /* load buddy */
 +      e3b->bd_bh2 = sb_getblk(sb, sbi->s_buddy_blocks[group]->bb_buddy);
 +      if (e3b->bd_bh2 == NULL) {
@@ -247,10 +247,15 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh2)) {
++
++      if (!buffer_uptodate(e3b->bd_bh))
++              ll_rw_block(READ, 1, &e3b->bd_bh);
++      if (!buffer_uptodate(e3b->bd_bh2))
 +              ll_rw_block(READ, 1, &e3b->bd_bh2);
-+              wait_on_buffer(e3b->bd_bh2);
-+      }
++
++      wait_on_buffer(e3b->bd_bh);
++      J_ASSERT(buffer_uptodate(e3b->bd_bh));
++      wait_on_buffer(e3b->bd_bh2);
 +      J_ASSERT(buffer_uptodate(e3b->bd_bh2));
 +
 +      e3b->bd_blkbits = sb->s_blocksize_bits;
@@ -300,22 +305,22 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              count = 0;
 +              for (i = 0; i < max; i++) {
 +
-+                      if (!mb_test_bit(i, buddy)) {
++                      if (mb_test_bit(i, buddy)) {
 +                              /* only single bit in buddy2 may be 1 */
-+                              if (mb_test_bit(i << 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit((i<<1)+1, buddy2));
-+                              else if (mb_test_bit((i << 1) + 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
++                              if (!mb_test_bit(i << 1, buddy2))
++                                      J_ASSERT(mb_test_bit((i<<1)+1, buddy2));
++                              else if (!mb_test_bit((i << 1) + 1, buddy2))
++                                      J_ASSERT(mb_test_bit(i << 1, buddy2));
 +                              continue;
 +                      }
 +
 +                      /* both bits in buddy2 must be 0 */
-+                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
-+                      J_ASSERT(!mb_test_bit((i << 1) + 1, buddy2));
++                      J_ASSERT(mb_test_bit(i << 1, buddy2));
++                      J_ASSERT(mb_test_bit((i << 1) + 1, buddy2));
 +
 +                      for (j = 0; j < (1 << order); j++) {
 +                              k = (i * (1 << order)) + j;
-+                              J_ASSERT(mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
++                              J_ASSERT(!mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
 +                      }
 +                      count++;
 +              }
@@ -325,14 +330,14 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +      buddy = mb_find_buddy(e3b, 0, &max);
 +      for (i = 0; i < max; i++) {
-+              if (mb_test_bit(i, buddy))
++              if (!mb_test_bit(i, buddy))
 +                      continue;
 +              /* check used bits only */
 +              for (j = 0; j < e3b->bd_blkbits + 1; j++) {
 +                      buddy2 = mb_find_buddy(e3b, j, &max2);
 +                      k = i >> j;
 +                      J_ASSERT(k < max2);
-+                      J_ASSERT(!mb_test_bit(k, buddy2));
++                      J_ASSERT(mb_test_bit(k, buddy2));
 +              }
 +      }
 +}
@@ -363,7 +368,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      bb = EXT3_MB_BUDDY(e3b);
 +      while (order <= e3b->bd_blkbits + 1) {
 +              block = block >> 1;
-+              if (mb_test_bit(block, bb)) {
++              if (!mb_test_bit(block, bb)) {
 +                      /* this block is part of buddy of order 'order' */
 +                      return order;
 +              }
@@ -424,8 +429,8 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              block = first++;
 +              order = 0;
 +
-+              J_ASSERT(!mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
-+              mb_set_bit(block, EXT3_MB_BITMAP(e3b));
++              J_ASSERT(mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
++              mb_clear_bit(block, EXT3_MB_BITMAP(e3b));
 +              e3b->bd_bd->bb_counters[order]++;
 +
 +              /* start of the buddy */
@@ -433,8 +438,8 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +              do {
 +                      block &= ~1UL;
-+                      if (!mb_test_bit(block, buddy) ||
-+                                      !mb_test_bit(block + 1, buddy))
++                      if (mb_test_bit(block, buddy) ||
++                                      mb_test_bit(block + 1, buddy))
 +                              break;
 +
 +                      /* both the buddies are free, try to coalesce them */
@@ -444,10 +449,10 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                              break;
 +
 +                      if (order > 0) {
-+                              /* for special purposes, we don't clear
++                              /* for special purposes, we don't set
 +                               * free bits in bitmap */
-+                              mb_clear_bit(block, buddy);
-+                              mb_clear_bit(block + 1, buddy);
++                              mb_set_bit(block, buddy);
++                              mb_set_bit(block + 1, buddy);
 +                      }
 +                      e3b->bd_bd->bb_counters[order]--;
 +                      e3b->bd_bd->bb_counters[order]--;
@@ -456,7 +461,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      order++;
 +                      e3b->bd_bd->bb_counters[order]++;
 +
-+                      mb_set_bit(block, buddy2);
++                      mb_clear_bit(block, buddy2);
 +                      buddy = buddy2;
 +              } while (1);
 +      }
@@ -466,7 +471,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +}
 +
 +static int mb_find_extent(struct ext3_buddy *e3b, int order, int block,
-+                              int needed, struct ext3_free_extent *ex)
++                        int needed, struct ext3_free_extent *ex)
 +{
 +      int next, max, ord;
 +      void *buddy;
@@ -476,7 +481,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      buddy = mb_find_buddy(e3b, order, &max);
 +      J_ASSERT(buddy);
 +      J_ASSERT(block < max);
-+      if (!mb_test_bit(block, buddy)) {
++      if (mb_test_bit(block, buddy)) {
 +              ex->fe_len = 0;
 +              ex->fe_start = 0;
 +              ex->fe_group = 0;
@@ -499,7 +504,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      break;
 +
 +              next = (block + 1) * (1 << order);
-+              if (!mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
++              if (mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
 +                      break;
 +
 +              ord = mb_find_order_for_block(e3b, next);
@@ -533,7 +538,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      mlen = 1 << ord;
 +                      buddy = mb_find_buddy(e3b, ord, &max);
 +                      J_ASSERT((start >> ord) < max);
-+                      mb_clear_bit(start >> ord, buddy);
++                      mb_set_bit(start >> ord, buddy);
 +                      e3b->bd_bd->bb_counters[ord]--;
 +                      start += mlen;
 +                      len -= mlen;
@@ -544,20 +549,20 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              /* we have to split large buddy */
 +              J_ASSERT(ord > 0);
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_clear_bit(start >> ord, buddy);
++              mb_set_bit(start >> ord, buddy);
 +              e3b->bd_bd->bb_counters[ord]--;
 +
 +              ord--;
 +              cur = (start >> ord) & ~1U;
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_set_bit(cur, buddy);
-+              mb_set_bit(cur + 1, buddy);
++              mb_clear_bit(cur, buddy);
++              mb_clear_bit(cur + 1, buddy);
 +              e3b->bd_bd->bb_counters[ord]++;
 +              e3b->bd_bd->bb_counters[ord]++;
 +      }
 +
 +      /* now drop all the bits in bitmap */
-+      mb_clear_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
++      mb_set_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
 +
 +      mb_check_buddy(e3b);
 +
@@ -733,7 +738,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      i = e3b->bd_bd->bb_first_free;
 +
 +      while (free && ac->ac_status != AC_STATUS_FOUND) {
-+              i = find_next_bit(bitmap, sb->s_blocksize * 8, i);
++              i = ext2_find_next_zero_bit(bitmap, sb->s_blocksize * 8, i);
 +              if (i >= sb->s_blocksize * 8) {
 +                      J_ASSERT(free == 0);
 +                      break;
@@ -951,7 +956,6 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              /*
 +               * We aren't lucky definitely
 +               */
-+              J_ASSERT(ac.ac_b_ex.fe_len == 0);
 +              DQUOT_FREE_BLOCK(inode, *len);
 +              *errp = -ENOSPC;
 +              block = 0;
@@ -1020,8 +1024,8 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              ext3_error(sb, "ext3_new_block",
 +                          "Allocating block in system zone - "
 +                          "block = %u", block);
-+#if AGGRESSIVE_CHECK
-+      for (i = 0; i < ac.ac_b_len; i++)
++#ifdef AGGRESSIVE_CHECK
++      for (i = 0; i < ac.ac_b_ex.fe_len; i++)
 +              J_ASSERT(!mb_test_bit(ac.ac_b_ex.fe_start + i, bitmap_bh->b_data));
 +#endif
 +      mb_set_bits(bitmap_bh->b_data, ac.ac_b_ex.fe_start, ac.ac_b_ex.fe_len);
@@ -1141,7 +1145,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      
 +      e3b->bd_bd->bb_first_free = grp->mgd_first_free;
 +      e3b->bd_bd->bb_free = grp->mgd_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              e3b->bd_bd->bb_counters[i] = grp->mgd_counters[i];
 +      }
@@ -1155,7 +1159,6 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              printk(KERN_ERR "EXT3-fs: mbgroup %d corrupted (%d != %d)\n",
 +                      e3b->bd_group, e3b->bd_bd->bb_free,
 +                      le16_to_cpu(gdp->bg_free_blocks_count));
-+              BUG();
 +              return -ENODATA;
 +      }
 +
@@ -1166,20 +1169,19 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +int ext3_mb_update_descr(struct ext3_buddy *e3b)
 +{
 +      struct ext3_mb_group_descr *grp;
-+      struct ext3_group_desc *ogdp;
++      struct ext3_group_desc *gdp;
 +      struct buffer_head *bh;
 +      handle_t *handle;
 +      int err, i;
 +
 +      /* additional checks against old group descriptor */
-+      ogdp = ext3_get_group_desc(e3b->bd_sb, e3b->bd_group, NULL);
-+      if (!ogdp)
++      gdp = ext3_get_group_desc(e3b->bd_sb, e3b->bd_group, NULL);
++      if (!gdp)
 +              return -EIO;
-+      if (e3b->bd_bd->bb_free != le16_to_cpu(ogdp->bg_free_blocks_count)) {
++      if (e3b->bd_bd->bb_free != le16_to_cpu(gdp->bg_free_blocks_count)) {
 +              printk(KERN_ERR "EXT3-fs: mbgroup %d corrupted (%d != %d)\n",
 +                      e3b->bd_group, e3b->bd_bd->bb_free,
-+                      le16_to_cpu(ogdp->bg_free_blocks_count));
-+              BUG();
++                      le16_to_cpu(gdp->bg_free_blocks_count));
 +              return -ENODATA;
 +      }
 +
@@ -1187,7 +1189,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      if (err)
 +              return err;
 +      
-+      handle = journal_start(EXT3_SB(e3b->bd_sb)->s_journal, 1);
++      handle = ext3_journal_start(EXT3_SB(e3b->bd_sb)->s_buddy, 1);
 +      if (IS_ERR(handle)) {
 +              err = PTR_ERR(handle);
 +              handle = NULL;
@@ -1199,7 +1201,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              goto out;
 +      grp->mgd_first_free = e3b->bd_bd->bb_first_free;
 +      grp->mgd_free = e3b->bd_bd->bb_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              grp->mgd_counters[i] = e3b->bd_bd->bb_counters[i];
 +      }
@@ -1219,16 +1221,24 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      struct super_block *sb = e3b->bd_sb;
 +      struct buffer_head *bh;
 +      int i, count = 0;
-+      
-+      memset(e3b->bd_bh->b_data, 0, sb->s_blocksize);
-+      memset(e3b->bd_bh2->b_data, 0, sb->s_blocksize);
++
++      mb_debug("generate buddy for group %d\n", e3b->bd_group);
++      memset(e3b->bd_bh->b_data, 0xff, sb->s_blocksize);
++      memset(e3b->bd_bh2->b_data, 0xff, sb->s_blocksize);
 +
 +      bh = read_block_bitmap(sb, e3b->bd_group);
 +      if (bh == NULL)
 +              return -EIO; 
 +
 +      /* mb_free_blocks will set real free */
++      e3b->bd_bd->bb_free = 0;
 +      e3b->bd_bd->bb_first_free = 1 << 15;
++      /* 
++       * if change bb_counters size, don't forget about 
++       * ext3_mb_init_backend() -bzzz
++       */
++      memset(e3b->bd_bd->bb_counters, 0,
++              sizeof(unsigned) * (sb->s_blocksize_bits + 2));
 +
 +      /* loop over the blocks, and create buddies for free ones */
 +      for (i = 0; i < sb->s_blocksize * 8; i++) {
@@ -1291,7 +1301,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              }
 +              db->d_inode->i_flags |= S_IMMUTABLE | S_NOATIME;
 +              *created = 1;
-+              printk("EXT3-fs: no buddy file, regenerate\n");
++              mb_debug("no buddy file, regenerate\n");
 +      }
 +      up(&root->i_sem);
 +      sbi->s_buddy = igrab(db->d_inode);
@@ -1304,8 +1314,10 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      len = sbi->s_groups_count * sb->s_blocksize * 2 +
 +                      buddy_offset * sb->s_blocksize;
 +      if (len != i_size_read(sbi->s_buddy)) {
-+              printk("EXT3-fs: wrong i_size (%u != %u), regenerate\n",
-+                      (unsigned) len, (unsigned) i_size_read(sbi->s_buddy));
++              if (*created == 0)
++                      printk("EXT3-fs: wrong i_size (%u != %u), regenerate\n",
++                              (unsigned) len, 
++                              (unsigned) i_size_read(sbi->s_buddy));
 +              *created = 1;
 +      }
 +
@@ -1313,14 +1325,14 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      for (i = 0; i < buddy_offset; i++) {
 +              handle = ext3_journal_start(sbi->s_buddy, MB_CREDITS);
 +              if (IS_ERR(handle)) {
-+                      printk(KERN_ERR "EXT3-fs: can't start transaction\n");
++                      printk(KERN_ERR "EXT3-fs: cant start transaction\n");
 +                      err = PTR_ERR(handle);
 +                      goto err_out;
 +              }
 +              
 +              bh = ext3_bread(handle, sbi->s_buddy, i, 1, &err);
 +              if (bh == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't getblk grp: %d\n", err);
++                      printk(KERN_ERR "EXT3-fs: cant getblk grp: %d\n", err);
 +                      goto err_out;
 +              }
 +              hdr = (struct ext3_mb_grp_header *) bh->b_data;
@@ -1328,9 +1340,11 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      err = ext3_journal_get_write_access(handle, bh);
 +                      if (err)
 +                              goto err_out;
++                      if (*created == 0)
++                              printk(KERN_ERR 
++                                      "EXT3-fs: invalid header 0x%x in %d,"
++                                      "regenerate\n", hdr->mh_magic, i);
 +                      *created = 1;
-+                      printk("EXT3-fs: invalid header %#x in %d regenerate\n",
-+                             hdr->mh_magic, i);
 +                      hdr->mh_magic = EXT3_MB_MAGIC_V1;
 +                      err = ext3_journal_dirty_metadata(handle, bh);
 +                      if (err)
@@ -1340,12 +1354,16 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              ext3_journal_stop(handle);
 +      }
 +
++      /* 
++       * if change bb_counters size, don't forget about ext3_mb_generate_buddy()
++       */
 +      len = sizeof(struct ext3_buddy_group_blocks);
 +      len += sizeof(unsigned) * (sb->s_blocksize_bits + 2);
 +      for (i = 0; i < sbi->s_groups_count; i++) {
++
 +              sbi->s_buddy_blocks[i] = kmalloc(len, GFP_KERNEL);
 +              if (sbi->s_buddy_blocks[i] == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't allocate buddy mem\n");
++                      printk(KERN_ERR "EXT3-fs: cant allocate mem for buddy\n");
 +                      err = -ENOMEM;
 +                      goto out2;
 +              }
@@ -1353,7 +1371,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +              handle = ext3_journal_start(sbi->s_buddy, MB_CREDITS);
 +              if (IS_ERR(handle)) {
-+                      printk(KERN_ERR "EXT3-fs: can't start transaction\n");
++                      printk(KERN_ERR "EXT3-fs: cant start transaction\n");
 +                      err = PTR_ERR(handle);
 +                      goto out2;
 +              }
@@ -1362,8 +1380,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              block = buddy_offset + i * 2;
 +              bh = ext3_getblk(handle, sbi->s_buddy, block, 1, &err);
 +              if (bh == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't getblk bitmap: %d\n",
-+                             err);
++                      printk(KERN_ERR "EXT3-fs: cant getblk bitmap: %d\n", err);
 +                      goto out2;
 +              }
 +              sbi->s_buddy_blocks[i]->bb_bitmap = bh->b_blocknr;
@@ -1373,7 +1390,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              block = buddy_offset + i * 2 + 1;
 +              bh = ext3_getblk(handle, sbi->s_buddy, block, 1, &err);
 +              if (bh == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't getblk for buddy: %d\n",+                              err);
++                      printk(KERN_ERR "EXT3-fs: cant getblk for buddy: %d\n", err);
 +                      goto out2;
 +              }
 +              sbi->s_buddy_blocks[i]->bb_buddy = bh->b_blocknr;
@@ -1736,6 +1753,19 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      if (err)
 +              goto error_return;
 +
++#ifdef AGGRESSIVE_CHECK
++      {
++              int i;
++              for (i = 0; i < count; i++)
++                      J_ASSERT(mb_test_bit(bit + i, bitmap_bh->b_data));
++      }
++#endif
++      mb_clear_bits(bitmap_bh->b_data, bit, count);
++
++      /* We dirtied the bitmap block */
++      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
++      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
++
 +      if (metadata) {
 +              /* blocks being freed are metadata. these blocks shouldn't
 +               * be used until this transaction is committed */
@@ -1745,21 +1775,18 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              mb_free_blocks(&e3b, bit, count);
 +              ext3_unlock_group(sb, block_group);
 +      }
++
 +      spin_lock(sb_bgl_lock(sbi, block_group));
 +      gdp->bg_free_blocks_count =
 +              cpu_to_le16(le16_to_cpu(gdp->bg_free_blocks_count) + count);
 +      spin_unlock(sb_bgl_lock(sbi, block_group));
++      percpu_counter_mod(&sbi->s_freeblocks_counter, count);
 +      
 +      ext3_mb_dirty_buddy(&e3b);
 +      ext3_mb_release_desc(&e3b);
 +
-+      mb_clear_bits(bitmap_bh->b_data, bit, count);
 +      *freed = count;
 +
-+      /* We dirtied the bitmap block */
-+      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
-+      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
-+
 +      /* And the group descriptor block */
 +      BUFFER_TRACE(gd_bh, "dirtied group descriptor block");
 +      ret = ext3_journal_dirty_metadata(handle, gd_bh);
@@ -1821,6 +1848,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      return ret;
 +}
 +
++
 +extern void ext3_free_blocks_old(handle_t *, struct inode *,
 +                              unsigned long, unsigned long);
 +void ext3_free_blocks(handle_t *handle, struct inode * inode,
@@ -1838,19 +1866,19 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      return;
 +}
 +
-Index: linux-2.6.5-sles9/fs/ext3/super.c
+Index: linux-2.6.5-suse/fs/ext3/super.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/super.c     2005-02-23 01:47:15.291333736 +0300
-+++ linux-2.6.5-sles9/fs/ext3/super.c  2005-02-23 01:48:54.515249408 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/super.c      2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/super.c   2005-02-26 18:40:26.000000000 +0300
 @@ -389,6 +389,7 @@
        struct ext3_super_block *es = sbi->s_es;
        int i;
  
 +      ext3_mb_release(sb);
-       ext3_ext_release(sb);
+       ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
-@@ -540,6 +541,7 @@
+@@ -543,6 +544,7 @@
        Opt_commit, Opt_journal_update, Opt_journal_inum,
        Opt_abort, Opt_data_journal, Opt_data_ordered, Opt_data_writeback,
        Opt_ignore, Opt_barrier, Opt_iopen, Opt_noiopen, Opt_iopen_nopriv,
@@ -1858,7 +1886,7 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        Opt_err, Opt_extents, Opt_extdebug
  };
  
-@@ -587,6 +589,8 @@
+@@ -590,6 +592,8 @@
        {Opt_iopen_nopriv, "iopen_nopriv"},
        {Opt_extents, "extents"},
        {Opt_extdebug, "extdebug"},
@@ -1867,7 +1895,7 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        {Opt_err, NULL}
  };
  
-@@ -808,6 +812,16 @@
+@@ -811,6 +815,16 @@
                case Opt_extdebug:
                        set_opt (sbi->s_mount_opt, EXTDEBUG);
                        break;
@@ -1884,20 +1912,18 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
                default:
                        printk (KERN_ERR
                                "EXT3-fs: Unrecognized mount option \"%s\" "
-@@ -1461,7 +1475,8 @@
+@@ -1464,6 +1478,7 @@
                ext3_count_dirs(sb));
  
-       ext3_ext_init(sb);
-- 
+       ext3_ext_init(sb);
 +      ext3_mb_init(sb, needs_recovery);
-+
        return 0;
  
- failed_mount3:
-Index: linux-2.6.5-sles9/fs/ext3/Makefile
+Index: linux-2.6.5-suse/fs/ext3/Makefile
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/Makefile    2005-02-23 01:02:37.405434272 +0300
-+++ linux-2.6.5-sles9/fs/ext3/Makefile 2005-02-23 01:48:54.517249104 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/Makefile     2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/Makefile  2005-02-26 18:40:26.000000000 +0300
 @@ -5,7 +5,7 @@
  obj-$(CONFIG_EXT3_FS) += ext3.o
  
@@ -1907,10 +1933,10 @@ Index: linux-2.6.5-sles9/fs/ext3/Makefile
  
  ext3-$(CONFIG_EXT3_FS_XATTR)   += xattr.o xattr_user.o xattr_trusted.o
  ext3-$(CONFIG_EXT3_FS_POSIX_ACL) += acl.o
-Index: linux-2.6.5-sles9/fs/ext3/balloc.c
+Index: linux-2.6.5-suse/fs/ext3/balloc.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/balloc.c    2004-11-03 08:36:51.000000000 +0300
-+++ linux-2.6.5-sles9/fs/ext3/balloc.c 2005-02-23 01:48:54.520248648 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/balloc.c     2005-02-02 00:55:47.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/balloc.c  2005-02-26 18:40:26.000000000 +0300
 @@ -78,7 +78,7 @@
   *
   * Return buffer_head on success or NULL in case of failure.
@@ -1938,10 +1964,10 @@ Index: linux-2.6.5-sles9/fs/ext3/balloc.c
                        unsigned long goal, int *errp)
  {
        struct buffer_head *bitmap_bh = NULL;
-Index: linux-2.6.5-sles9/fs/ext3/namei.c
+Index: linux-2.6.5-suse/fs/ext3/namei.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/namei.c     2005-02-23 01:01:46.551165296 +0300
-+++ linux-2.6.5-sles9/fs/ext3/namei.c  2005-02-23 01:48:54.523248192 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/namei.c      2005-02-26 18:40:19.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/namei.c   2005-02-26 18:40:26.000000000 +0300
 @@ -1640,7 +1640,7 @@
   * If the create succeeds, we fill in the inode information
   * with d_instantiate(). 
@@ -1951,10 +1977,10 @@ Index: linux-2.6.5-sles9/fs/ext3/namei.c
                struct nameidata *nd)
  {
        handle_t *handle; 
-Index: linux-2.6.5-sles9/fs/ext3/inode.c
+Index: linux-2.6.5-suse/fs/ext3/inode.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/inode.c     2005-02-23 01:02:37.404434424 +0300
-+++ linux-2.6.5-sles9/fs/ext3/inode.c  2005-02-23 01:48:54.529247280 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/inode.c      2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/inode.c   2005-02-26 18:40:26.000000000 +0300
 @@ -572,7 +572,7 @@
                ext3_journal_forget(handle, branch[i].bh);
        }
@@ -1973,7 +1999,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
        return err;
  }
  
-@@ -1829,7 +1829,7 @@
+@@ -1830,7 +1830,7 @@
                }
        }
  
@@ -1982,7 +2008,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
  }
  
  /**
-@@ -2000,7 +2000,7 @@
+@@ -2001,7 +2001,7 @@
                                ext3_journal_test_restart(handle, inode);
                        }
  
@@ -1991,10 +2017,10 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
  
                        if (parent_bh) {
                                /*
-Index: linux-2.6.5-sles9/fs/ext3/extents.c
+Index: linux-2.6.5-suse/fs/ext3/extents.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/extents.c   2005-02-23 01:02:37.396435640 +0300
-+++ linux-2.6.5-sles9/fs/ext3/extents.c        2005-02-23 01:48:54.533246672 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/extents.c    2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/extents.c 2005-02-26 18:40:26.000000000 +0300
 @@ -774,7 +774,7 @@
                for (i = 0; i < depth; i++) {
                        if (!ablocks[i])
@@ -2036,10 +2062,10 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
        } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
                printk("strange request: removal %lu-%lu from %u:%u\n",
                        from, to, ex->ee_block, ex->ee_len);
-Index: linux-2.6.5-sles9/fs/ext3/xattr.c
+Index: linux-2.6.5-suse/fs/ext3/xattr.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/xattr.c     2005-02-23 01:01:52.387278072 +0300
-+++ linux-2.6.5-sles9/fs/ext3/xattr.c  2005-02-23 01:48:54.537246064 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/xattr.c      2005-02-26 18:40:22.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/xattr.c   2005-02-26 18:40:26.000000000 +0300
 @@ -1366,7 +1366,7 @@
                        new_bh = sb_getblk(sb, block);
                        if (!new_bh) {
@@ -2067,10 +2093,10 @@ Index: linux-2.6.5-sles9/fs/ext3/xattr.c
                get_bh(bh);
                ext3_forget(handle, 1, inode, bh, EXT3_I(inode)->i_file_acl);
        } else {
-Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
+Index: linux-2.6.5-suse/include/linux/ext3_fs.h
 ===================================================================
---- linux-2.6.5-sles9.orig/include/linux/ext3_fs.h     2005-02-23 01:02:37.414432904 +0300
-+++ linux-2.6.5-sles9/include/linux/ext3_fs.h  2005-02-23 01:48:54.539245760 +0300
+--- linux-2.6.5-suse.orig/include/linux/ext3_fs.h      2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/include/linux/ext3_fs.h   2005-02-26 18:40:26.000000000 +0300
 @@ -57,6 +57,14 @@
  #define ext3_debug(f, a...)   do {} while (0)
  #endif
@@ -2090,7 +2116,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
  #define EXT3_MOUNT_IOPEN_NOPRIV               0x80000 /* Make iopen world-readable */
  #define EXT3_MOUNT_EXTENTS            0x100000/* Extents support */
  #define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
-+#define EXT3_MOUNT_MBALLOC            0x100000/* Buddy allocation support */
++#define EXT3_MOUNT_MBALLOC            0x400000/* Buddy allocation support */
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
  #ifndef clear_opt
@@ -2141,10 +2167,10 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
  #endif        /* __KERNEL__ */
  
  #define EXT3_IOC_CREATE_INUM                  _IOW('f', 5, long)
-Index: linux-2.6.5-sles9/include/linux/ext3_fs_sb.h
+Index: linux-2.6.5-suse/include/linux/ext3_fs_sb.h
 ===================================================================
---- linux-2.6.5-sles9.orig/include/linux/ext3_fs_sb.h  2005-02-23 01:01:48.242908112 +0300
-+++ linux-2.6.5-sles9/include/linux/ext3_fs_sb.h       2005-02-23 01:48:54.541245456 +0300
+--- linux-2.6.5-suse.orig/include/linux/ext3_fs_sb.h   2005-02-26 18:40:20.000000000 +0300
++++ linux-2.6.5-suse/include/linux/ext3_fs_sb.h        2005-02-26 18:40:26.000000000 +0300
 @@ -23,10 +23,30 @@
  #define EXT_INCLUDE
  #include <linux/blockgroup_lock.h>
index fcceb30..dc6ffe3 100644 (file)
@@ -2,7 +2,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/mballoc.c 2005-02-25 17:28:41.836311072 +0200
 +++ linux-stage/fs/ext3/mballoc.c      2005-02-25 17:28:41.859307576 +0200
-@@ -0,0 +1,1847 @@
+@@ -0,0 +1,1860 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -39,6 +39,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +
 +/*
 + * TODO:
++ *   - bitmap/buddy read-ahead (proposed by Oleg Drokin aka green)
 + *   - track min/max extents in each group for better group selection
 + *   - is it worthwhile to use buddies directly if req is 2^N blocks?
 + *   - mb_mark_used() may allocate chunk right after splitting buddy
@@ -96,7 +97,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      __u32   mh_magic;
 +};
 +
-+#define EXT3_MB_MAGIC_V1      0xbaad16fc
++#define EXT3_MB_MAGIC_V1      0xbabd16fd
 +
 +
 +struct ext3_free_extent {
@@ -148,47 +149,50 @@ Index: linux-stage/fs/ext3/mballoc.c
 +void ext3_mb_poll_new_transaction(struct super_block *, handle_t *);
 +void ext3_mb_free_committed_blocks(struct super_block *);
 +
-+#define mb_correct_addr_and_bit(bit,addr)     \
-+{                                             \
-+      if ((unsigned long)addr & 1) {          \
-+              bit += 8;                       \
-+              addr--;                         \
-+      }                                       \
-+      if ((unsigned long)addr & 2) {          \
-+              bit += 16;                      \
-+              addr--;                         \
-+              addr--;                         \
-+      }                                       \
++#if BITS_PER_LONG == 64
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 7UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~7UL);  \
 +}
++#elif BITS_PER_LONG == 32
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 3UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~3UL);  \
++}
++#else
++#error "how many bits you are?!"
++#endif
 +
 +static inline int mb_test_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      return test_bit(bit, addr);
++      return ext2_test_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __set_bit(bit, addr);
++      ext2_set_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      set_bit(bit, addr);
++      ext2_set_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void mb_clear_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __clear_bit(bit, addr);
++      ext2_clear_bit(bit, addr);
 +}
 +
 +static inline void mb_clear_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      clear_bit(bit, addr);
++      ext2_clear_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void *mb_find_buddy(struct ext3_buddy *e3b, int order, int *max)
@@ -199,8 +203,10 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      J_ASSERT(EXT3_MB_BITMAP(e3b) != EXT3_MB_BUDDY(e3b));
 +      J_ASSERT(max != NULL);
 +
-+      if (order > e3b->bd_blkbits + 1)
++      if (order > e3b->bd_blkbits + 1) {
++              *max = 0;
 +              return NULL;
++      }
 +
 +      /* at order 0 we see each particular block */
 +      *max = 1 << (e3b->bd_blkbits + 3);
@@ -234,12 +240,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh)) {
-+              ll_rw_block(READ, 1, &e3b->bd_bh);
-+              wait_on_buffer(e3b->bd_bh);
-+      }
-+      J_ASSERT(buffer_uptodate(e3b->bd_bh));
-+
 +      /* load buddy */
 +      e3b->bd_bh2 = sb_getblk(sb, sbi->s_buddy_blocks[group]->bb_buddy);
 +      if (e3b->bd_bh2 == NULL) {
@@ -247,10 +247,15 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh2)) {
++
++      if (!buffer_uptodate(e3b->bd_bh))
++              ll_rw_block(READ, 1, &e3b->bd_bh);
++      if (!buffer_uptodate(e3b->bd_bh2))
 +              ll_rw_block(READ, 1, &e3b->bd_bh2);
-+              wait_on_buffer(e3b->bd_bh2);
-+      }
++
++      wait_on_buffer(e3b->bd_bh);
++      J_ASSERT(buffer_uptodate(e3b->bd_bh));
++      wait_on_buffer(e3b->bd_bh2);
 +      J_ASSERT(buffer_uptodate(e3b->bd_bh2));
 +
 +      e3b->bd_blkbits = sb->s_blocksize_bits;
@@ -300,22 +305,22 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              count = 0;
 +              for (i = 0; i < max; i++) {
 +
-+                      if (!mb_test_bit(i, buddy)) {
++                      if (mb_test_bit(i, buddy)) {
 +                              /* only single bit in buddy2 may be 1 */
-+                              if (mb_test_bit(i << 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit((i<<1)+1, buddy2));
-+                              else if (mb_test_bit((i << 1) + 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
++                              if (!mb_test_bit(i << 1, buddy2))
++                                      J_ASSERT(mb_test_bit((i<<1)+1, buddy2));
++                              else if (!mb_test_bit((i << 1) + 1, buddy2))
++                                      J_ASSERT(mb_test_bit(i << 1, buddy2));
 +                              continue;
 +                      }
 +
 +                      /* both bits in buddy2 must be 0 */
-+                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
-+                      J_ASSERT(!mb_test_bit((i << 1) + 1, buddy2));
++                      J_ASSERT(mb_test_bit(i << 1, buddy2));
++                      J_ASSERT(mb_test_bit((i << 1) + 1, buddy2));
 +
 +                      for (j = 0; j < (1 << order); j++) {
 +                              k = (i * (1 << order)) + j;
-+                              J_ASSERT(mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
++                              J_ASSERT(!mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
 +                      }
 +                      count++;
 +              }
@@ -325,14 +330,14 @@ Index: linux-stage/fs/ext3/mballoc.c
 +
 +      buddy = mb_find_buddy(e3b, 0, &max);
 +      for (i = 0; i < max; i++) {
-+              if (mb_test_bit(i, buddy))
++              if (!mb_test_bit(i, buddy))
 +                      continue;
 +              /* check used bits only */
 +              for (j = 0; j < e3b->bd_blkbits + 1; j++) {
 +                      buddy2 = mb_find_buddy(e3b, j, &max2);
 +                      k = i >> j;
 +                      J_ASSERT(k < max2);
-+                      J_ASSERT(!mb_test_bit(k, buddy2));
++                      J_ASSERT(mb_test_bit(k, buddy2));
 +              }
 +      }
 +}
@@ -363,7 +368,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      bb = EXT3_MB_BUDDY(e3b);
 +      while (order <= e3b->bd_blkbits + 1) {
 +              block = block >> 1;
-+              if (mb_test_bit(block, bb)) {
++              if (!mb_test_bit(block, bb)) {
 +                      /* this block is part of buddy of order 'order' */
 +                      return order;
 +              }
@@ -424,8 +429,8 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              block = first++;
 +              order = 0;
 +
-+              J_ASSERT(!mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
-+              mb_set_bit(block, EXT3_MB_BITMAP(e3b));
++              J_ASSERT(mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
++              mb_clear_bit(block, EXT3_MB_BITMAP(e3b));
 +              e3b->bd_bd->bb_counters[order]++;
 +
 +              /* start of the buddy */
@@ -433,8 +438,8 @@ Index: linux-stage/fs/ext3/mballoc.c
 +
 +              do {
 +                      block &= ~1UL;
-+                      if (!mb_test_bit(block, buddy) ||
-+                                      !mb_test_bit(block + 1, buddy))
++                      if (mb_test_bit(block, buddy) ||
++                                      mb_test_bit(block + 1, buddy))
 +                              break;
 +
 +                      /* both the buddies are free, try to coalesce them */
@@ -444,10 +449,10 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                              break;
 +
 +                      if (order > 0) {
-+                              /* for special purposes, we don't clear
++                              /* for special purposes, we don't set
 +                               * free bits in bitmap */
-+                              mb_clear_bit(block, buddy);
-+                              mb_clear_bit(block + 1, buddy);
++                              mb_set_bit(block, buddy);
++                              mb_set_bit(block + 1, buddy);
 +                      }
 +                      e3b->bd_bd->bb_counters[order]--;
 +                      e3b->bd_bd->bb_counters[order]--;
@@ -456,7 +461,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                      order++;
 +                      e3b->bd_bd->bb_counters[order]++;
 +
-+                      mb_set_bit(block, buddy2);
++                      mb_clear_bit(block, buddy2);
 +                      buddy = buddy2;
 +              } while (1);
 +      }
@@ -476,7 +481,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      buddy = mb_find_buddy(e3b, order, &max);
 +      J_ASSERT(buddy);
 +      J_ASSERT(block < max);
-+      if (!mb_test_bit(block, buddy)) {
++      if (mb_test_bit(block, buddy)) {
 +              ex->fe_len = 0;
 +              ex->fe_start = 0;
 +              ex->fe_group = 0;
@@ -499,7 +504,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                      break;
 +
 +              next = (block + 1) * (1 << order);
-+              if (!mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
++              if (mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
 +                      break;
 +
 +              ord = mb_find_order_for_block(e3b, next);
@@ -533,7 +538,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                      mlen = 1 << ord;
 +                      buddy = mb_find_buddy(e3b, ord, &max);
 +                      J_ASSERT((start >> ord) < max);
-+                      mb_clear_bit(start >> ord, buddy);
++                      mb_set_bit(start >> ord, buddy);
 +                      e3b->bd_bd->bb_counters[ord]--;
 +                      start += mlen;
 +                      len -= mlen;
@@ -544,20 +549,20 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              /* we have to split large buddy */
 +              J_ASSERT(ord > 0);
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_clear_bit(start >> ord, buddy);
++              mb_set_bit(start >> ord, buddy);
 +              e3b->bd_bd->bb_counters[ord]--;
 +
 +              ord--;
 +              cur = (start >> ord) & ~1U;
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_set_bit(cur, buddy);
-+              mb_set_bit(cur + 1, buddy);
++              mb_clear_bit(cur, buddy);
++              mb_clear_bit(cur + 1, buddy);
 +              e3b->bd_bd->bb_counters[ord]++;
 +              e3b->bd_bd->bb_counters[ord]++;
 +      }
 +
 +      /* now drop all the bits in bitmap */
-+      mb_clear_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
++      mb_set_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
 +
 +      mb_check_buddy(e3b);
 +
@@ -733,7 +738,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      i = e3b->bd_bd->bb_first_free;
 +
 +      while (free && ac->ac_status != AC_STATUS_FOUND) {
-+              i = find_next_bit(bitmap, sb->s_blocksize * 8, i);
++              i = ext2_find_next_zero_bit(bitmap, sb->s_blocksize * 8, i);
 +              if (i >= sb->s_blocksize * 8) {
 +                      J_ASSERT(free == 0);
 +                      break;
@@ -951,7 +956,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              /*
 +               * We aren't lucky definitely
 +               */
-+              J_ASSERT(ac.ac_b_ex.fe_len == 0);
 +              DQUOT_FREE_BLOCK(inode, *len);
 +              *errp = -ENOSPC;
 +              block = 0;
@@ -1020,8 +1024,8 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              ext3_error(sb, "ext3_new_block",
 +                          "Allocating block in system zone - "
 +                          "block = %u", block);
-+#if AGGRESSIVE_CHECK
-+      for (i = 0; i < ac.ac_b_len; i++)
++#ifdef AGGRESSIVE_CHECK
++      for (i = 0; i < ac.ac_b_ex.fe_len; i++)
 +              J_ASSERT(!mb_test_bit(ac.ac_b_ex.fe_start + i, bitmap_bh->b_data));
 +#endif
 +      mb_set_bits(bitmap_bh->b_data, ac.ac_b_ex.fe_start, ac.ac_b_ex.fe_len);
@@ -1141,7 +1145,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      
 +      e3b->bd_bd->bb_first_free = grp->mgd_first_free;
 +      e3b->bd_bd->bb_free = grp->mgd_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              e3b->bd_bd->bb_counters[i] = grp->mgd_counters[i];
 +      }
@@ -1197,7 +1201,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              goto out;
 +      grp->mgd_first_free = e3b->bd_bd->bb_first_free;
 +      grp->mgd_free = e3b->bd_bd->bb_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              grp->mgd_counters[i] = e3b->bd_bd->bb_counters[i];
 +      }
@@ -1217,9 +1221,10 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      struct super_block *sb = e3b->bd_sb;
 +      struct buffer_head *bh;
 +      int i, count = 0;
-+      
-+      memset(e3b->bd_bh->b_data, 0, sb->s_blocksize);
-+      memset(e3b->bd_bh2->b_data, 0, sb->s_blocksize);
++
++      mb_debug("generate buddy for group %d\n", e3b->bd_group);
++      memset(e3b->bd_bh->b_data, 0xff, sb->s_blocksize);
++      memset(e3b->bd_bh2->b_data, 0xff, sb->s_blocksize);
 +
 +      bh = read_block_bitmap(sb, e3b->bd_group);
 +      if (bh == NULL)
@@ -1748,6 +1753,19 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      if (err)
 +              goto error_return;
 +
++#ifdef AGGRESSIVE_CHECK
++      {
++              int i;
++              for (i = 0; i < count; i++)
++                      J_ASSERT(mb_test_bit(bit + i, bitmap_bh->b_data));
++      }
++#endif
++      mb_clear_bits(bitmap_bh->b_data, bit, count);
++
++      /* We dirtied the bitmap block */
++      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
++      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
++
 +      if (metadata) {
 +              /* blocks being freed are metadata. these blocks shouldn't
 +               * be used until this transaction is committed */
@@ -1757,21 +1775,18 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              mb_free_blocks(&e3b, bit, count);
 +              ext3_unlock_group(sb, block_group);
 +      }
++
 +      spin_lock(sb_bgl_lock(sbi, block_group));
 +      gdp->bg_free_blocks_count =
 +              cpu_to_le16(le16_to_cpu(gdp->bg_free_blocks_count) + count);
 +      spin_unlock(sb_bgl_lock(sbi, block_group));
++      percpu_counter_mod(&sbi->s_freeblocks_counter, count);
 +      
 +      ext3_mb_dirty_buddy(&e3b);
 +      ext3_mb_release_desc(&e3b);
 +
-+      mb_clear_bits(bitmap_bh->b_data, bit, count);
 +      *freed = count;
 +
-+      /* We dirtied the bitmap block */
-+      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
-+      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
-+
 +      /* And the group descriptor block */
 +      BUFFER_TRACE(gd_bh, "dirtied group descriptor block");
 +      ret = ext3_journal_dirty_metadata(handle, gd_bh);
@@ -1833,7 +1848,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      return ret;
 +}
 +
-+
 +void ext3_free_blocks(handle_t *handle, struct inode * inode,
 +                      unsigned long block, unsigned long count, int metadata)
 +{
@@ -1849,7 +1863,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              DQUOT_FREE_BLOCK(inode, freed);
 +      return;
 +}
-+
 Index: linux-stage/fs/ext3/super.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/super.c   2005-02-25 17:27:00.231757312 +0200
@@ -1859,7 +1872,7 @@ Index: linux-stage/fs/ext3/super.c
        int i;
  
 +      ext3_mb_release(sb);
-       ext3_ext_release(sb);
+       ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
 @@ -592,7 +593,7 @@
@@ -1897,16 +1910,14 @@ Index: linux-stage/fs/ext3/super.c
                default:
                        printk (KERN_ERR
                                "EXT3-fs: Unrecognized mount option \"%s\" "
-@@ -1639,7 +1652,8 @@
+@@ -1639,6 +1652,7 @@
                ext3_count_dirs(sb));
  
-       ext3_ext_init(sb);
-- 
+       ext3_ext_init(sb);
 +      ext3_mb_init(sb, needs_recovery);
-+
        return 0;
  
- failed_mount3:
 Index: linux-stage/fs/ext3/Makefile
 ===================================================================
 --- linux-stage.orig/fs/ext3/Makefile  2005-02-25 17:27:00.228757768 +0200
@@ -2122,8 +2133,8 @@ Index: linux-stage/include/linux/ext3_fs.h
  #define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
 +#define EXT3_MOUNT_MBALLOC            0x400000/* Buddy allocation support */
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
+ #ifndef _LINUX_EXT2_FS_H
 @@ -725,7 +734,7 @@
  extern unsigned long ext3_bg_num_gdb(struct super_block *sb, int group);
  extern int ext3_new_block (handle_t *, struct inode *, unsigned long, int *);
@@ -2184,7 +2195,7 @@ Index: linux-stage/include/linux/ext3_fs_sb.h
  #endif
  #include <linux/rbtree.h>
  
-+#define EXT3_BB_MAX_BLOCKS    30
++#define EXT3_BB_MAX_BLOCKS    30
 +struct ext3_free_metadata {
 +      unsigned short group;
 +      unsigned short num;
@@ -2222,7 +2233,7 @@ Index: linux-stage/include/linux/ext3_fs_sb.h
 +      spinlock_t s_md_lock;
 +      tid_t s_last_transaction;
 +      int s_mb_factor;
-+ 
++
 +      /* stats for buddy allocator */
 +      spinlock_t s_bal_lock;
 +      unsigned long s_bal_reqs;       /* number of reqs with len > 1 */
index 3033df3..cbd61f7 100644 (file)
        - fix several locking issues related to i_size (5492,5624,5654,5672)
        - don't move pending lock onto export if it is already evicted (5683)
        - fix kernel oops when creating .foo in unlinked directory (5548)
+       - fix deadlock in obdfilter statistics vs. object create (5811)
+       - use time_{before,after} to avoid timer jiffies wrap (5882)
+       - shutdown --force/--failover stability (3607,3651,4797,5203,4834)
+       - Do not leak request if server was not able to process it (5154)
+       - If mds_open unable to find parent dir, make that negative lookup(5154)
        * miscellania
        - fix lustre/lustrefs init scripts for SuSE (patch from Scali, 5702)
        - don't hold the pinger_sem in ptlrpc_pinger_sending_on_import
        - change obd_increase_kms to obd_adjust_kms (up or down) (5654)
        - lconf, lmc search both /usr/lib and /usr/lib64 for Python libs (5800)
+       - support for RHEL4 kernel on i686 (5773)
+       - provide error messages when incompatible logs are encountered (5898)
 
 2005-02-18  Cluster File Systems, Inc. <info@clusterfs.com>
        * version 1.4.0.10 (1.4.1 release candidate 1)
index c816f62..ab926f2 100644 (file)
@@ -261,6 +261,27 @@ fi
 ])
 
 #
+# LC_FUNC_DEV_SET_RDONLY
+#
+# check for the old-style dev_set_rdonly which took an extra "devno" param
+# and can only set a single device to discard writes at one time
+#
+AC_DEFUN([LC_FUNC_DEV_SET_RDONLY],
+[AC_MSG_CHECKING([if kernel has old single-device dev_set_rdonly])
+HAVE_OLD_DSR="`grep -c -s 'dev_set_rdonly.*no_write' $LINUX/drivers/block/ll_rw_blk.c`"
+if test x$HAVE_OLD_DSR != "x1" ; then
+       HAVE_OLD_DSR="`grep -c -s 'dev_set_rdonly.*no_write' $LINUX/drivers/block/blkpg.c`"
+fi
+if test x$HAVE_OLD_DSR = "x1" ; then
+        AC_DEFINE(HAVE_OLD_DEV_SET_RDONLY, 1,
+                [kernel has old single-device dev_set_rdonly])
+        AC_MSG_RESULT(yes)
+else
+        AC_MSG_RESULT(no)
+fi
+])
+
+#
 # LC_CONFIG_BACKINGFS
 #
 # whether to use extN or ldiskfs instead of ext3
@@ -319,8 +340,7 @@ case $BACKINGFS in
                LC_FSHOOKS([
                        LDISKFS_SERIES="2.6-suse.series"
                ],[
-                       AC_MSG_ERROR([Only SuSE 2.6 kernels (with fshooks) are supported at this time])
-                       LDISKFS_SERIES="2.6-vanilla.series"
+                       LDISKFS_SERIES="2.6-rhel4.series"
                ])
                AC_SUBST(LDISKFS_SERIES)
                ;;
@@ -381,6 +401,7 @@ LC_HEADER_MM_INLINE
 LC_STRUCT_INODE
 LC_FUNC_REGISTER_CACHE
 LC_FUNC_GRAB_CACHE_PAGE_NOWAIT_GFP
+LC_FUNC_DEV_SET_RDONLY
 ])
 
 #
@@ -460,6 +481,7 @@ lustre/include/linux/Makefile
 lustre/include/lustre/Makefile
 lustre/kernel_patches/targets/2.6-suse.target
 lustre/kernel_patches/targets/2.6-vanilla.target
+lustre/kernel_patches/targets/2.6-rhel4.target
 lustre/kernel_patches/targets/hp_pnnl-2.4.target
 lustre/kernel_patches/targets/rh-2.4.target
 lustre/kernel_patches/targets/rhel-2.4.target
index 907a11d..68e6b6d 100644 (file)
@@ -1 +1 @@
-m4_define([LUSTRE_VERSION],[1.4.0.10])
+m4_define([LUSTRE_VERSION],[1.4.1])
index 0fb0a35..a5bdefa 100644 (file)
@@ -1,6 +1,8 @@
 # sample modules.conf for autoloading lustre modules on zeroconf clients
 
 add below kptlrouter portals
+#add below ksocknal kptlrouter
+#add below kqswnal kptlrouter
 add below ptlrpc ksocknal
 add below llite lov osc 
 alias lustre llite
index bbadd08..8e130d0 100644 (file)
@@ -620,6 +620,7 @@ static inline int schedule_timeout(signed long t)
 })
 #define time_after(a, b) ((long)(b) - (long)(a) < 0)
 #define time_before(a, b) time_after(b,a)
+#define time_after_eq(a,b)     ((long)(a) - (long)(b) >= 0)
 
 struct timer_list {
         struct list_head tl_list;
@@ -630,7 +631,7 @@ struct timer_list {
 
 static inline int timer_pending(struct timer_list *l)
 {
-        if (l->expires > jiffies)
+        if (time_after(l->expires, jiffies))
                 return 1;
         else
                 return 0;
index bc79915..6c0adbd 100644 (file)
@@ -216,6 +216,8 @@ extern int lprocfs_obd_cleanup(struct obd_device *obd);
 
 extern int lprocfs_rd_u64(char *page, char **start, off_t off,
                           int count, int *eof, void *data);
+extern int lprocfs_rd_atomic(char *page, char **start, off_t off,
+                          int count, int *eof, void *data);
 extern int lprocfs_rd_uuid(char *page, char **start, off_t off,
                            int count, int *eof, void *data);
 extern int lprocfs_rd_name(char *page, char **start, off_t off,
index bf4e9e2..77c5f05 100644 (file)
@@ -163,7 +163,8 @@ struct ldlm_namespace {
         char                  *ns_name;
         __u32                  ns_client; /* is this a client-side lock tree? */
         struct list_head      *ns_hash; /* hash table for ns */
-        __u32                  ns_refcount; /* count of resources in the hash */
+        wait_queue_head_t      ns_refcount_waitq; /* for cleanup */
+        atomic_t               ns_refcount; /* count of resources in the hash */
         struct list_head       ns_root_list; /* all root resources in ns */
         struct lustre_lock     ns_lock; /* protects hash, refcount, list */
         struct list_head       ns_list_chain; /* position in global NS list */
@@ -174,11 +175,10 @@ struct ldlm_namespace {
         struct list_head       ns_unused_list; /* all root resources in ns */
         int                    ns_nr_unused;
         unsigned int           ns_max_unused;
-        unsigned long          ns_next_dump;   /* next dump time */
+        unsigned long          ns_next_dump;   /* next debug dump, jiffies */
 
         spinlock_t             ns_counter_lock;
         __u64                  ns_locks;
-        __u64                  ns_resources;
         ldlm_res_policy        ns_policy;
         struct ldlm_valblock_ops *ns_lvbo;
         void                    *ns_lvbp;
@@ -248,18 +248,11 @@ struct ldlm_lock {
 
         /* Server-side-only members */
         struct list_head      l_pending_chain;  /* callbacks pending */
-        unsigned long         l_callback_timeout;
+        unsigned long         l_callback_timeout; /* jiffies */
 
         __u32                 l_pid;            /* pid which created this lock */
 };
 
-#define LDLM_PLAIN       10
-#define LDLM_EXTENT      11
-#define LDLM_FLOCK       12
-
-#define LDLM_MIN_TYPE 10
-#define LDLM_MAX_TYPE 12
-
 struct ldlm_resource {
         struct ldlm_namespace *lr_namespace;
         struct list_head       lr_hash;
index cb257e7..4e55481 100644 (file)
@@ -112,7 +112,12 @@ static inline void *fsfilt_start_log(struct obd_device *obd,
 {
         unsigned long now = jiffies;
         void *parent_handle = oti ? oti->oti_handle : NULL;
-        void *handle = obd->obd_fsops->fs_start(inode, op, parent_handle, logs);
+        void *handle;
+        
+        if (obd->obd_fail)
+                return ERR_PTR(-EROFS);
+
+        handle = obd->obd_fsops->fs_start(inode, op, parent_handle, logs);
         CDEBUG(D_INFO, "started handle %p (%p)\n", handle, parent_handle);
 
         if (oti != NULL) {
@@ -142,8 +147,13 @@ static inline void *fsfilt_brw_start_log(struct obd_device *obd,
 {
         unsigned long now = jiffies;
         void *parent_handle = oti ? oti->oti_handle : NULL;
-        void *handle = obd->obd_fsops->fs_brw_start(objcount, fso, niocount, nb,
-                                                    parent_handle, logs);
+        void *handle;
+
+        if (obd->obd_fail)
+                return ERR_PTR(-EROFS);
+
+        handle = obd->obd_fsops->fs_brw_start(objcount, fso, niocount, nb,
+                                              parent_handle, logs);
         CDEBUG(D_INFO, "started handle %p (%p)\n", handle, parent_handle);
 
         if (oti != NULL) {
@@ -236,11 +246,10 @@ static inline int fsfilt_send_bio(int rw, struct obd_device *obd,
                                   struct inode *inode, void *bio)
 {
         LASSERTF(rw == OBD_BRW_WRITE || rw == OBD_BRW_READ, "%x\n", rw);
-
+        
         if (rw == OBD_BRW_READ)
                 return obd->obd_fsops->fs_send_bio(READ, inode, bio);
-        else
-                return obd->obd_fsops->fs_send_bio(WRITE, inode, bio);
+        return obd->obd_fsops->fs_send_bio(WRITE, inode, bio);
 }
 
 static inline ssize_t fsfilt_readpage(struct obd_device *obd,
index e1aa3c9..63c0b4d 100644 (file)
@@ -669,6 +669,15 @@ typedef enum {
         LCK_NL = 32
 } ldlm_mode_t;
 
+typedef enum {
+        LDLM_PLAIN     = 10,
+        LDLM_EXTENT    = 11,
+        LDLM_FLOCK     = 12,
+        LDLM_MAX_TYPE
+} ldlm_type_t;
+
+#define LDLM_MIN_TYPE LDLM_PLAIN
+
 struct ldlm_extent {
         __u64 start;
         __u64 end;
@@ -702,7 +711,7 @@ struct ldlm_intent {
 extern void lustre_swab_ldlm_intent (struct ldlm_intent *i);
 
 struct ldlm_resource_desc {
-        __u32 lr_type;
+        ldlm_type_t lr_type;
         __u32 lr_padding;
         struct ldlm_res_id lr_name;
 };
index db1cd90..481f082 100644 (file)
@@ -68,8 +68,8 @@ struct obd_import {
         __u64                     imp_peer_committed_transno;
         struct obd_uuid           imp_target_uuid; /* XXX -> lustre_name */
         struct lustre_handle      imp_remote_handle;
-        unsigned long             imp_next_ping;
-        
+        unsigned long             imp_next_ping;   /* jiffies */
+
         /* Protects flags, level, generation, conn_cnt, *_list */
         spinlock_t                imp_lock;
 
index 3e04929..380629a 100644 (file)
@@ -412,7 +412,7 @@ static inline void obd_ioctl_freedata(char *buf, int len)
 
 
 #define OBD_IOC_STATFS                 _IOWR('f', 113, long)
-#define OBD_IOC_SYNC                   _IOR ('f', 114, long)
+#define OBD_IOC_SYNC                   _IOW ('f', 114, long)
 #define OBD_IOC_READ2                  _IOWR('f', 115, long)
 #define OBD_IOC_FORMAT                 _IOWR('f', 116, long)
 #define OBD_IOC_PARTITION              _IOWR('f', 117, long)
index 9316230..c5c045d 100644 (file)
 /* careful, this is easy to screw up */
 #define PAGE_CACHE_MAXBYTES ((__u64)(~0UL) << PAGE_CACHE_SHIFT)
 
-
-/*
-struct lustre_intent_data {
-        __u64 it_lock_handle[2];
-        __u32 it_disposition;
-        __u32 it_status;
-        __u32 it_lock_mode;
-        }; */
-
-#define LL_IT2STR(it) ((it) ? ldlm_it2str((it)->it_op) : "0")
-
-static inline struct lookup_intent *ll_nd2it(struct nameidata *nd)
-{
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
-        return &nd->intent;
-#else
-        return nd->intent;
-#endif
-}
-
-struct ll_dentry_data {
-        int                      lld_cwd_count;
-        int                      lld_mnt_count;
-        struct obd_client_handle lld_cwd_och;
-        struct obd_client_handle lld_mnt_och;
-};
-
-#define ll_d2d(de) ((struct ll_dentry_data*) de->d_fsdata)
-
-extern struct file_operations ll_pgcache_seq_fops;
-
-#define LLI_INODE_MAGIC                 0x111d0de5
-#define LLI_INODE_DEAD                  0xdeadd00d
-#define LLI_F_HAVE_OST_SIZE_LOCK        0
-#define LLI_F_HAVE_MDS_SIZE_LOCK        1
-struct ll_inode_info {
-        int                     lli_inode_magic;
-        struct lov_stripe_md   *lli_smd;
-        char                   *lli_symlink_name;
-        struct semaphore        lli_open_sem;
-        struct semaphore        lli_size_sem;
-        __u64                   lli_maxbytes;
-        __u64                   lli_io_epoch;
-        unsigned long           lli_flags;
-
-        /* this lock protects s_d_w and p_w_ll and mmap_cnt */
-        spinlock_t              lli_lock;
-        int                     lli_send_done_writing;
-        struct list_head        lli_pending_write_llaps;
-        atomic_t                lli_mmap_cnt;
-
-        struct list_head        lli_close_item;
-
-        /* for writepage() only to communicate to fsync */
-        int                     lli_async_rc;
-
-        struct file_operations *ll_save_ifop;
-        struct file_operations *ll_save_ffop;
-        struct file_operations *ll_save_wfop;
-        struct file_operations *ll_save_wrfop;
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
-        struct inode            lli_vfs_inode;
-#endif
-};
-
-// FIXME: replace the name of this with LL_I to conform to kernel stuff
-// static inline struct ll_inode_info *LL_I(struct inode *inode)
-static inline struct ll_inode_info *ll_i2info(struct inode *inode)
-{
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
-        return container_of(inode, struct ll_inode_info, lli_vfs_inode);
-#else
-        return (struct ll_inode_info *)&(inode->u.generic_ip);
-#endif
-}
-
 /* lprocfs.c */
 enum {
          LPROC_LL_DIRTY_HITS = 0,
index 20843f5..6beb16c 100644 (file)
@@ -153,7 +153,7 @@ int mds_update_server_data(struct obd_device *, int force_sync);
 
 /* mds/mds_fs.c */
 int mds_fs_setup(struct obd_device *obddev, struct vfsmount *mnt);
-int mds_fs_cleanup(struct obd_device *obddev, int failover);
+int mds_fs_cleanup(struct obd_device *obddev);
 #endif
 
 /* mds/mds_lov.c */
index 21ddb59..7fccdef 100644 (file)
@@ -297,7 +297,7 @@ struct ptlrpc_request {
         int rq_reqlen;
         struct lustre_msg *rq_reqmsg;
 
-        int rq_timeout;
+        int rq_timeout;                         /* seconds */
         int rq_replen;
         struct lustre_msg *rq_repmsg;
         __u64 rq_transno;
@@ -336,7 +336,7 @@ struct ptlrpc_request {
         void  *rq_cb_data;
 
         struct ptlrpc_bulk_desc *rq_bulk;       /* client side bulk */
-        time_t rq_sent;                         /* when the request was sent */
+        time_t rq_sent;                         /* when request sent, seconds */
 
         /* Multi-rpc bits */
         struct list_head rq_set_chain;
@@ -738,10 +738,10 @@ ptlrpc_rs_decref(struct ptlrpc_reply_state *rs)
 
 /* ldlm/ldlm_lib.c */
 int client_obd_setup(struct obd_device *obddev, obd_count len, void *buf);
-int client_obd_cleanup(struct obd_device * obddev, int flags);
+int client_obd_cleanup(struct obd_device * obddev);
 int client_connect_import(struct lustre_handle *conn, struct obd_device *obd,
                           struct obd_uuid *cluuid);
-int client_disconnect_export(struct obd_export *exp, int failover);
+int client_disconnect_export(struct obd_export *exp);
 
 /* ptlrpc/pinger.c */
 int ptlrpc_pinger_add_import(struct obd_import *imp);
index 9f24687..c6146bd 100644 (file)
@@ -485,7 +485,8 @@ struct obd_device {
         int obd_minor;
         unsigned int obd_attached:1, obd_set_up:1, obd_recovering:1,
                 obd_abort_recovery:1, obd_replayable:1, obd_no_transno:1,
-                obd_no_recov:1, obd_stopping:1, obd_starting:1;
+                obd_no_recov:1, obd_stopping:1, obd_starting:1, 
+                obd_force:1, obd_fail:1;
         atomic_t obd_refcount;
         wait_queue_head_t obd_refcount_waitq;
         struct proc_dir_entry *obd_proc_entry;
@@ -499,7 +500,7 @@ struct obd_device {
         struct fsfilt_operations *obd_fsops;
         spinlock_t              obd_osfs_lock;
         struct obd_statfs       obd_osfs;
-        unsigned long           obd_osfs_age;
+        unsigned long           obd_osfs_age;   /* jiffies */
         struct obd_run_ctxt     obd_ctxt;
         struct llog_ctxt        *obd_llog_ctxt[LLOG_MAX_CTXTS];
         struct obd_device       *obd_observer;
@@ -560,12 +561,12 @@ struct obd_ops {
         int (*o_attach)(struct obd_device *dev, obd_count len, void *data);
         int (*o_detach)(struct obd_device *dev);
         int (*o_setup) (struct obd_device *dev, obd_count len, void *data);
-        int (*o_precleanup)(struct obd_device *dev, int flags);
-        int (*o_cleanup)(struct obd_device *dev, int flags);
+        int (*o_precleanup)(struct obd_device *dev);
+        int (*o_cleanup)(struct obd_device *dev);
         int (*o_postrecov)(struct obd_device *dev);
         int (*o_connect)(struct lustre_handle *conn, struct obd_device *src,
                          struct obd_uuid *cluuid);
-        int (*o_disconnect)(struct obd_export *exp, int flags);
+        int (*o_disconnect)(struct obd_export *exp);
 
         int (*o_statfs)(struct obd_device *obd, struct obd_statfs *osfs,
                         unsigned long max_age);
index cfbd032..d7b340f 100644 (file)
@@ -84,6 +84,7 @@ int class_attach(struct lustre_cfg *lcfg);
 int class_setup(struct obd_device *obd, struct lustre_cfg *lcfg);
 int class_cleanup(struct obd_device *obd, struct lustre_cfg *lcfg);
 int class_detach(struct obd_device *obd, struct lustre_cfg *lcfg);
+void class_decref(struct obd_device *obd);
 
 /* Passed as data param to class_config_parse_llog */
 struct config_llog_instance {
@@ -137,9 +138,9 @@ struct obd_type *class_get_type(char *name);
 void class_put_type(struct obd_type *type);
 int class_connect(struct lustre_handle *conn, struct obd_device *obd,
                   struct obd_uuid *cluuid);
-int class_disconnect(struct obd_export *exp, int failover);
-void class_disconnect_exports(struct obd_device *obddev, int failover);
-void class_disconnect_stale_exports(struct obd_device *obddev, int failover);
+int class_disconnect(struct obd_export *exp);
+void class_disconnect_exports(struct obd_device *obddev);
+void class_disconnect_stale_exports(struct obd_device *obddev);
 /* generic operations shared by various OBD types */
 int class_multi_setup(struct obd_device *obddev, uint32_t len, void *data);
 int class_multi_cleanup(struct obd_device *obddev);
@@ -170,22 +171,6 @@ do {                                                            \
         }                                                       \
 } while (0)
 
-#define OBD_CHECK_DEV_STOPPING(obd)                             \
-do {                                                            \
-        OBD_CHECK_DEV(obd);                                     \
-        if (!(obd)->obd_set_up) {                               \
-                CERROR("Device %d not setup\n",                 \
-                       (obd)->obd_minor);                       \
-                RETURN(-ENODEV);                                \
-        }                                                       \
-                                                                \
-        if (!(obd)->obd_stopping) {                             \
-                CERROR("Device %d not stopping\n",              \
-                       (obd)->obd_minor);                       \
-                RETURN(-ENODEV);                                \
-        }                                                       \
-} while (0)
-
 /* ensure obd_setup and !obd_stopping */
 #define OBD_CHECK_DEV_ACTIVE(obd)                               \
 do {                                                            \
@@ -292,7 +277,7 @@ static inline int obd_setup(struct obd_device *obd, int datalen, void *data)
         RETURN(rc);
 }
 
-static inline int obd_precleanup(struct obd_device *obd, int flags)
+static inline int obd_precleanup(struct obd_device *obd)
 {
         int rc;
         ENTRY;
@@ -300,20 +285,20 @@ static inline int obd_precleanup(struct obd_device *obd, int flags)
         OBD_CHECK_OP(obd, precleanup, 0);
         OBD_COUNTER_INCREMENT(obd, precleanup);
 
-        rc = OBP(obd, precleanup)(obd, flags);
+        rc = OBP(obd, precleanup)(obd);
         RETURN(rc);
 }
 
-static inline int obd_cleanup(struct obd_device *obd, int flags)
+static inline int obd_cleanup(struct obd_device *obd)
 {
         int rc;
         ENTRY;
-
-        OBD_CHECK_DEV_STOPPING(obd);
+        
+        OBD_CHECK_DEV(obd);                                     
         OBD_CHECK_OP(obd, cleanup, 0);
         OBD_COUNTER_INCREMENT(obd, cleanup);
 
-        rc = OBP(obd, cleanup)(obd, flags);
+        rc = OBP(obd, cleanup)(obd);
         RETURN(rc);
 }
 
@@ -483,7 +468,7 @@ static inline int obd_connect(struct lustre_handle *conn,
         RETURN(rc);
 }
 
-static inline int obd_disconnect(struct obd_export *exp, int flags)
+static inline int obd_disconnect(struct obd_export *exp)
 {
         int rc;
         ENTRY;
@@ -491,7 +476,7 @@ static inline int obd_disconnect(struct obd_export *exp, int flags)
         EXP_CHECK_OP(exp, disconnect);
         OBD_COUNTER_INCREMENT(exp->exp_obd, disconnect);
 
-        rc = OBP(exp->exp_obd, disconnect)(exp, flags);
+        rc = OBP(exp->exp_obd, disconnect)(exp);
         RETURN(rc);
 }
 
index fb35c49..5ced170 100644 (file)
@@ -126,6 +126,7 @@ extern wait_queue_head_t obd_race_waitq;
 #define OBD_FAIL_LDLM_CREATE_RESOURCE    0x30a
 #define OBD_FAIL_LDLM_ENQUEUE_BLOCKED    0x30b
 #define OBD_FAIL_LDLM_REPLY              0x30c
+#define OBD_FAIL_LDLM_RECOV_CLIENTS      0x30d
 
 #define OBD_FAIL_OSC                     0x400
 #define OBD_FAIL_OSC_BRW_READ_BULK       0x401
@@ -203,7 +204,7 @@ do {                                                                         \
 do {                                                            \
         if  (OBD_FAIL_CHECK_ONCE(id)) {                         \
                 CERROR("obd_race id %x sleeping\n", (id));      \
-                sleep_on(&obd_race_waitq);                      \
+                interruptible_sleep_on(&obd_race_waitq);                      \
                 CERROR("obd_fail_race id %x awake\n", (id));    \
         } else if ((obd_fail_loc & OBD_FAIL_MASK_LOC) ==        \
                     ((id) & OBD_FAIL_MASK_LOC)) {               \
@@ -225,18 +226,55 @@ do {                                                            \
 # if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
 #  define BDEVNAME_DECLARE_STORAGE(foo) char foo[BDEVNAME_SIZE]
 #  define ll_bdevname(SB, STORAGE) __bdevname(kdev_t_to_nr(SB->s_dev), STORAGE)
-#  define ll_lock_kernel lock_kernel()
-#  define ll_sbdev(SB)    ((SB)->s_bdev)
-void dev_set_rdonly(struct block_device *, int);
+#  define ll_sbdev(SB)       ((SB)->s_bdev)
+#  define ll_sbdev_type      struct block_device *
+   int fsync_bdev(struct block_device *);
+#  define ll_sbdev_sync      fsync_bdev
+#  define ll_lock_kernel     lock_kernel()
 # else
 #  define BDEVNAME_DECLARE_STORAGE(foo) char __unused_##foo
-#  define ll_sbdev(SB)    (kdev_t_to_nr((SB)->s_dev))
 #  define ll_bdevname(SB,STORAGE) ((void)__unused_##STORAGE,bdevname(ll_sbdev(SB)))
+#  define ll_sbdev(SB)       (kdev_t_to_nr((SB)->s_dev))
+#  define ll_sbdev_type      kdev_t
+#  define ll_sbdev_sync      fsync_dev
 #  define ll_lock_kernel
-void dev_set_rdonly(kdev_t, int);
 # endif
 
-void dev_clear_rdonly(int);
+                                        
+#ifdef HAVE_OLD_DEV_SET_RDONLY
+  void dev_set_rdonly(ll_sbdev_type, int no_write);
+  void dev_clear_rdonly(int no_write);
+#else
+  void dev_set_rdonly(ll_sbdev_type);
+  void dev_clear_rdonly(ll_sbdev_type);
+#endif
+int dev_check_rdonly(ll_sbdev_type);
+#define ll_check_rdonly dev_check_rdonly
+
+static inline void ll_set_rdonly(ll_sbdev_type dev)
+{
+        CDEBUG(D_IOCTL | D_HA, "set dev %ld rdonly\n", (long)dev);
+        ll_sbdev_sync(dev);
+#ifdef HAVE_OLD_DEV_SET_RDONLY
+        dev_set_rdonly(dev, 2);
+#else        
+        dev_set_rdonly(dev);
+#endif
+}
+
+static inline void ll_clear_rdonly(ll_sbdev_type dev)
+{
+        CDEBUG(D_IOCTL | D_HA, "unset dev %ld rdonly\n", (long)dev);
+        if (dev_check_rdonly(dev)) {
+                ll_sbdev_sync(dev);
+#ifdef HAVE_OLD_DEV_SET_RDONLY
+                dev_clear_rdonly(2);
+#else
+                dev_clear_rdonly(dev);
+#endif        
+        }
+}
+
 
 static inline void OBD_FAIL_WRITE(int id, struct super_block *sb)
 {
@@ -244,7 +282,7 @@ static inline void OBD_FAIL_WRITE(int id, struct super_block *sb)
                 BDEVNAME_DECLARE_STORAGE(tmp);
                 CERROR("obd_fail_loc=%x, fail write operation on %s\n",
                        id, ll_bdevname(sb, tmp));
-                dev_set_rdonly(ll_sbdev(sb), 2);
+                ll_set_rdonly(ll_sbdev(sb));
                 /* We set FAIL_ONCE because we never "un-fail" a device */
                 obd_fail_loc |= OBD_FAILED | OBD_FAIL_ONCE;
         }
diff --git a/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-i686-smp.config b/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-i686-smp.config
new file mode 100644 (file)
index 0000000..f8e83ec
--- /dev/null
@@ -0,0 +1,2740 @@
+#
+# Automatically generated make config: don't edit
+#
+CONFIG_MMU=y
+CONFIG_SMP=y
+# CONFIG_HOTPLUG_CPU is not set
+CONFIG_LOCALVERSION=""
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_CLEAN_COMPILE=y
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+
+#
+# General setup
+#
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+CONFIG_BSD_PROCESS_ACCT=y
+# CONFIG_BSD_PROCESS_ACCT_V3 is not set
+CONFIG_SYSCTL=y
+CONFIG_LOG_BUF_SHIFT=17
+# CONFIG_IKCONFIG is not set
+# CONFIG_EMBEDDED is not set
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_ALL is not set
+CONFIG_KALLSYMS_EXTRA_PASS=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+# CONFIG_PREEMPT is not set
+CONFIG_PREEMPT_VOLUNTARY=y
+CONFIG_POSIX_MQUEUE=y
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+CONFIG_MODVERSIONS=y
+CONFIG_KMOD=y
+CONFIG_MODULE_SIG=y
+# CONFIG_MODULE_SIG_FORCE is not set
+
+#
+# Bus options (PCI, PCMCIA, EISA, MCA, ISA)
+#
+CONFIG_PCI=y
+CONFIG_PCI_MSI=y
+CONFIG_PCI_LEGACY_PROC=y
+# CONFIG_PCI_NAMES is not set
+CONFIG_ISA=y
+# CONFIG_EISA is not set
+# CONFIG_MCA is not set
+# CONFIG_SCx200 is not set
+CONFIG_HOTPLUG=y
+
+#
+# PCMCIA/CardBus support
+#
+CONFIG_PCMCIA=m
+# CONFIG_PCMCIA_DEBUG is not set
+CONFIG_YENTA=y
+CONFIG_CARDBUS=y
+# CONFIG_I82092 is not set
+CONFIG_I82365=m
+CONFIG_PD6729=m
+CONFIG_TCIC=m
+CONFIG_PCMCIA_PROBE=y
+
+#
+# Executable file formats
+#
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_AOUT is not set
+CONFIG_BINFMT_MISC=y
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_FW_LOADER=y
+
+#
+# Memory Technology Devices (MTD)
+#
+CONFIG_MTD=m
+# CONFIG_MTD_DEBUG is not set
+CONFIG_MTD_PARTITIONS=m
+CONFIG_MTD_CONCAT=m
+CONFIG_MTD_REDBOOT_PARTS=m
+CONFIG_MTD_CMDLINE_PARTS=y
+CONFIG_MTD_PARTITIONS=y
+#
+# User Modules And Translation Layers
+#
+CONFIG_MTD_CHAR=m
+CONFIG_MTD_BLOCK=m
+CONFIG_MTD_BLOCK_RO=m
+CONFIG_FTL=m
+CONFIG_NFTL=m
+CONFIG_NFTL_RW=y
+# CONFIG_INFTL is not set
+
+#
+# RAM/ROM/Flash chip drivers
+#
+CONFIG_MTD_CFI=m
+CONFIG_MTD_JEDECPROBE=m
+CONFIG_MTD_GEN_PROBE=m
+# CONFIG_MTD_CFI_ADV_OPTIONS is not set
+CONFIG_MTD_CFI_INTELEXT=m
+CONFIG_MTD_CFI_AMDSTD=m
+CONFIG_MTD_CFI_STAA=m
+CONFIG_MTD_RAM=m
+CONFIG_MTD_ROM=m
+CONFIG_MTD_ABSENT=m
+# CONFIG_MTD_OBSOLETE_CHIPS is not set
+
+#
+# Mapping drivers for chip access
+#
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PHYSMAP is not set
+# CONFIG_MTD_PNC2000 is not set
+CONFIG_MTD_SC520CDP=m
+CONFIG_MTD_NETSC520=m
+CONFIG_MTD_SBC_GXX=m
+CONFIG_MTD_ELAN_104NC=m
+CONFIG_MTD_SCx200_DOCFLASH=m
+# CONFIG_MTD_AMD76XROM is not set
+# CONFIG_MTD_SCB2_FLASH is not set
+# CONFIG_MTD_NETtel is not set
+# CONFIG_MTD_DILNETPC is not set
+# CONFIG_MTD_L440GX is not set
+# CONFIG_MTD_PCI is not set
+
+#
+# Self-contained MTD device drivers
+#
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_PMC551_BUGFIX is not set
+# CONFIG_MTD_PMC551_DEBUG is not set
+# CONFIG_MTD_SLRAM is not set
+CONFIG_MTD_MTDRAM=m
+CONFIG_MTDRAM_TOTAL_SIZE=4096
+CONFIG_MTDRAM_ERASE_SIZE=128
+# CONFIG_MTD_BLKMTD is not set
+
+#
+# Disk-On-Chip Device Drivers
+#
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+CONFIG_MTD_DOCPROBE=m
+# CONFIG_MTD_DOCPROBE_ADVANCED is not set
+CONFIG_MTD_DOCPROBE_ADDRESS=0
+
+#
+# NAND Flash Device Drivers
+#
+CONFIG_MTD_NAND=m
+# CONFIG_MTD_NAND_VERIFY_WRITE is not set
+CONFIG_MTD_NAND_IDS=m
+
+# CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
+# CONFIG_MTD_REDBOOT_PARTS_READONLY is not set
+CONFIG_MTD_CFI_AMDSTD_RETRY=3
+# CONFIG_MTD_ICHXROM is not set
+# CONFIG_MTD_PHRAM is not set
+# CONFIG_MTD_NAND_DISKONCHIP is not set
+# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set
+
+
+#
+# Parallel port support
+#
+CONFIG_PARPORT=m
+CONFIG_PARPORT_PC=m
+CONFIG_PARPORT_PC_CML1=m
+CONFIG_PARPORT_SERIAL=m
+# CONFIG_PARPORT_PC_FIFO is not set
+# CONFIG_PARPORT_PC_SUPERIO is not set
+CONFIG_PARPORT_PC_PCMCIA=m
+# CONFIG_PARPORT_OTHER is not set
+CONFIG_PARPORT_1284=y
+
+#
+# Plug and Play support
+#
+CONFIG_PNP=y
+# CONFIG_PNP_DEBUG is not set
+
+#
+# Protocols
+#
+# CONFIG_ISAPNP is not set
+# CONFIG_PNPBIOS is not set
+
+#
+# Block devices
+#
+CONFIG_BLK_DEV_FD=m
+# CONFIG_BLK_DEV_XD is not set
+# CONFIG_PARIDE is not set
+CONFIG_BLK_CPQ_DA=m
+CONFIG_BLK_CPQ_CISS_DA=m
+CONFIG_CISS_SCSI_TAPE=y
+CONFIG_BLK_DEV_DAC960=m
+# CONFIG_BLK_DEV_UMEM is not set
+CONFIG_BLK_DEV_LOOP=m
+CONFIG_BLK_DEV_CRYPTOLOOP=m
+CONFIG_BLK_DEV_NBD=m
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=16384
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_BLK_DEV_ATIIXP=y
+CONFIG_BLK_DEV_DELKIN=y
+CONFIG_BLK_DEV_IT8212=y
+CONFIG_LBD=y
+# CONFIG_DCSSBLK is not set
+
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_IDE_GENERIC=y
+# CONFIG_HPT34X_AUTODMA is not set
+
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_HD_IDE is not set
+CONFIG_BLK_DEV_IDEDISK=y
+CONFIG_IDEDISK_MULTI_MODE=y
+CONFIG_BLK_DEV_IDECS=m
+CONFIG_BLK_DEV_IDECD=y
+# CONFIG_BLK_DEV_IDETAPE is not set
+CONFIG_BLK_DEV_IDEFLOPPY=y
+CONFIG_BLK_DEV_IDESCSI=m
+# CONFIG_IDE_TASK_IOCTL is not set
+# CONFIG_IDE_TASKFILE_IO is not set
+# CONFIG_BLK_DEV_IDE_SATA is not set
+
+#
+# IDE chipset support/bugfixes
+#
+# CONFIG_BLK_DEV_CMD640 is not set
+# CONFIG_BLK_DEV_CMD640_ENHANCED is not set
+CONFIG_BLK_DEV_IDEPNP=y
+CONFIG_BLK_DEV_IDEPCI=y
+CONFIG_IDEPCI_SHARE_IRQ=y
+# CONFIG_BLK_DEV_OFFBOARD is not set
+CONFIG_BLK_DEV_GENERIC=y
+# CONFIG_BLK_DEV_OPTI621 is not set
+CONFIG_BLK_DEV_RZ1000=y
+CONFIG_BLK_DEV_IDEDMA_PCI=y
+# CONFIG_BLK_DEV_IDEDMA_FORCED is not set
+CONFIG_IDEDMA_PCI_AUTO=y
+# CONFIG_IDEDMA_ONLYDISK is not set
+CONFIG_BLK_DEV_AEC62XX=y
+CONFIG_BLK_DEV_ALI15X3=y
+# CONFIG_WDC_ALI15X3 is not set
+CONFIG_BLK_DEV_AMD74XX=y
+CONFIG_BLK_DEV_CMD64X=y
+CONFIG_BLK_DEV_TRIFLEX=y
+CONFIG_BLK_DEV_CY82C693=y
+CONFIG_BLK_DEV_CS5520=y
+CONFIG_BLK_DEV_CS5530=y
+CONFIG_BLK_DEV_HPT34X=y
+CONFIG_BLK_DEV_HPT366=y
+# CONFIG_BLK_DEV_SC1200 is not set
+CONFIG_BLK_DEV_PIIX=y
+# CONFIG_BLK_DEV_NS87415 is not set
+CONFIG_BLK_DEV_PDC202XX_OLD=y
+# CONFIG_PDC202XX_BURST is not set
+CONFIG_BLK_DEV_PDC202XX_NEW=y
+CONFIG_PDC202XX_FORCE=y
+CONFIG_BLK_DEV_SVWKS=y
+CONFIG_BLK_DEV_SIIMAGE=y
+CONFIG_BLK_DEV_SIS5513=y
+CONFIG_BLK_DEV_SLC90E66=y
+# CONFIG_BLK_DEV_TRM290 is not set
+CONFIG_BLK_DEV_VIA82CXXX=y
+# CONFIG_IDE_CHIPSETS is not set
+CONFIG_BLK_DEV_IDEDMA=y
+# CONFIG_IDEDMA_IVB is not set
+CONFIG_IDEDMA_AUTO=y
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+CONFIG_SCSI=m
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=m
+CONFIG_CHR_DEV_ST=m
+CONFIG_CHR_DEV_OSST=m
+CONFIG_BLK_DEV_SR=m
+CONFIG_BLK_DEV_SR_VENDOR=y
+CONFIG_CHR_DEV_SG=m
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SPI_ATTRS=y
+CONFIG_SCSI_FC_ATTRS=y
+
+#
+# SCSI low-level drivers
+#
+CONFIG_BLK_DEV_3W_XXXX_RAID=m
+CONFIG_SCSI_3W_9XXX=m
+# CONFIG_SCSI_7000FASST is not set
+CONFIG_SCSI_ACARD=m
+CONFIG_SCSI_AHA152X=m
+# CONFIG_SCSI_AHA1542 is not set
+CONFIG_SCSI_AACRAID=m
+CONFIG_SCSI_AIC7XXX=m
+CONFIG_AIC7XXX_CMDS_PER_DEVICE=4
+CONFIG_AIC7XXX_RESET_DELAY_MS=15000
+# CONFIG_AIC7XXX_PROBE_EISA_VL is not set
+# CONFIG_AIC7XXX_BUILD_FIRMWARE is not set
+# CONFIG_AIC7XXX_DEBUG_ENABLE is not set
+CONFIG_AIC7XXX_DEBUG_MASK=0
+# CONFIG_AIC7XXX_REG_PRETTY_PRINT is not set
+CONFIG_SCSI_AIC7XXX_OLD=m
+CONFIG_SCSI_AIC79XX=m
+CONFIG_AIC79XX_CMDS_PER_DEVICE=4
+CONFIG_AIC79XX_RESET_DELAY_MS=15000
+# CONFIG_AIC79XX_BUILD_FIRMWARE is not set
+# CONFIG_AIC79XX_ENABLE_RD_STRM is not set
+# CONFIG_AIC79XX_DEBUG_ENABLE is not set
+CONFIG_AIC79XX_DEBUG_MASK=0
+# CONFIG_AIC79XX_REG_PRETTY_PRINT is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_IN2000 is not set
+CONFIG_MEGARAID_NEWGEN=y
+CONFIG_MEGARAID_MM=m
+CONFIG_MEGARAID_MAILBOX=m
+CONFIG_SCSI_SATA=y
+CONFIG_SCSI_SATA_SVW=m
+CONFIG_SCSI_ATA_PIIX=m
+CONFIG_SCSI_SATA_PROMISE=m
+CONFIG_SCSI_SATA_VIA=m
+CONFIG_BLK_DEV_SX8=m
+CONFIG_SCSI_SATA_VITESSE=m
+CONFIG_SCSI_SATA_SIL=m
+CONFIG_SCSI_SATA_SIS=m
+CONFIG_SCSI_SATA_SX4=m
+CONFIG_SCSI_SATA_NV=m
+CONFIG_SCSI_SATA_AHCI=m
+
+# CONFIG_SCSI_BUSLOGIC is not set
+CONFIG_SCSI_INITIO=m
+# CONFIG_SCSI_OMIT_FLASHPOINT is not set
+# CONFIG_SCSI_CPQFCTS is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_DTC3280 is not set
+# CONFIG_SCSI_EATA is not set
+# CONFIG_SCSI_EATA_PIO is not set
+CONFIG_SCSI_FUTURE_DOMAIN=m
+CONFIG_SCSI_GDTH=m
+# CONFIG_SCSI_GENERIC_NCR5380 is not set
+# CONFIG_SCSI_GENERIC_NCR5380_MMIO is not set
+CONFIG_SCSI_IPS=m
+# CONFIG_SCSI_INIA100 is not set
+CONFIG_SCSI_PPA=m
+CONFIG_SCSI_IMM=m
+# CONFIG_SCSI_IZIP_EPP16 is not set
+# CONFIG_SCSI_IZIP_SLOW_CTR is not set
+# CONFIG_SCSI_NCR53C406A is not set
+CONFIG_SCSI_SYM53C8XX_2=m
+CONFIG_SCSI_SYM53C8XX_DMA_ADDRESSING_MODE=1
+CONFIG_SCSI_SYM53C8XX_DEFAULT_TAGS=16
+CONFIG_SCSI_SYM53C8XX_MAX_TAGS=64
+# CONFIG_SCSI_SYM53C8XX_IOMAPPED is not set
+# CONFIG_SCSI_PAS16 is not set
+# CONFIG_SCSI_PSI240I is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_SCSI_QLOGIC_FC is not set
+# CONFIG_SCSI_QLOGIC_FC_FIRMWARE is not set
+CONFIG_SCSI_QLOGIC_1280=m
+# CONFIG_SCSI_SYM53C416 is not set
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_T128 is not set
+# CONFIG_SCSI_U14_34F is not set
+# CONFIG_SCSI_ULTRASTOR is not set
+# CONFIG_SCSI_NSP32 is not set
+# CONFIG_SCSI_DEBUG is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_SCSI_QLA2XXX=m
+CONFIG_SCSI_QLA21XX=m
+CONFIG_SCSI_QLA22XX=m
+CONFIG_SCSI_QLA2300=m
+CONFIG_SCSI_QLA2322=m
+CONFIG_SCSI_QLA6312=m
+CONFIG_SCSI_QLA6322=m
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_DPT_I2O is not set
+
+CONFIG_SCSI_LPFC=m
+
+#
+# PCMCIA SCSI adapter support
+#
+# CONFIG_PCMCIA_AHA152X is not set
+CONFIG_PCMCIA_FDOMAIN=m
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+
+
+#
+# Old CD-ROM drivers (not SCSI, not IDE)
+#
+# CONFIG_CD_NO_IDESCSI is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+CONFIG_MD=y
+CONFIG_BLK_DEV_MD=y
+CONFIG_MD_LINEAR=m
+CONFIG_MD_RAID0=m
+CONFIG_MD_RAID1=m
+CONFIG_MD_RAID5=m
+CONFIG_MD_RAID6=m
+CONFIG_MD_RAID10=m
+CONFIG_MD_MULTIPATH=m
+CONFIG_BLK_DEV_DM=m
+CONFIG_DM_SNAPSHOT=m
+CONFIG_DM_MIRROR=m
+CONFIG_DM_ZERO=m
+CONFIG_DM_CRYPT=m
+
+#
+# Fusion MPT device support
+#
+CONFIG_FUSION=m
+CONFIG_FUSION_MAX_SGE=40
+CONFIG_FUSION_CTL=m
+CONFIG_FUSION_LAN=m
+
+#
+# IEEE 1394 (FireWire) support (EXPERIMENTAL)
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# Subsystem Options
+#
+# CONFIG_IEEE1394_VERBOSEDEBUG is not set
+CONFIG_IEEE1394_OUI_DB=y
+
+#
+# Device Drivers
+#
+# CONFIG_IEEE1394_PCILYNX is not set
+CONFIG_IEEE1394_OHCI1394=m
+
+#
+# Protocol Drivers
+#
+CONFIG_IEEE1394_VIDEO1394=m
+CONFIG_IEEE1394_SBP2=m
+# CONFIG_IEEE1394_SBP2_PHYS_DMA is not set
+# CONFIG_IEEE1394_ETH1394 is not set
+CONFIG_IEEE1394_DV1394=m
+CONFIG_IEEE1394_RAWIO=m
+CONFIG_IEEE1394_CMP=m
+CONFIG_IEEE1394_AMDTP=m
+# CONFIG_IEEE1394_EXTRA_CONFIG_ROMS is not set
+
+#
+# I2O device support
+#
+CONFIG_I2O=m
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+CONFIG_PACKET=y
+CONFIG_PACKET_MMAP=y
+CONFIG_NETLINK_DEV=y
+CONFIG_UNIX=y
+CONFIG_NET_KEY=m
+CONFIG_INET=y
+CONFIG_INET_TUNNEL=m
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_FWMARK=y
+CONFIG_IP_ROUTE_MULTIPATH=y
+CONFIG_IP_ROUTE_VERBOSE=y
+# CONFIG_IP_PNP is not set
+CONFIG_NET_IPIP=m
+CONFIG_NET_IPGRE=m
+CONFIG_NET_IPGRE_BROADCAST=y
+CONFIG_IP_MROUTE=y
+CONFIG_IP_PIMSM_V1=y
+CONFIG_IP_PIMSM_V2=y
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+CONFIG_INET_AH=m
+CONFIG_INET_ESP=m
+CONFIG_INET_IPCOMP=m
+CONFIG_NETCONSOLE=m
+# CONFIG_NETPOLL_RX is not set
+CONFIG_NETPOLL_TRAP=y
+CONFIG_NET_POLL_CONTROLLER=y
+CONFIG_NETDUMP=m
+CONFIG_DISKDUMP=m
+CONFIG_SCSI_DUMP=m
+CONFIG_SD_IOSTATS=y
+
+#
+# IP: Virtual Server Configuration
+#
+CONFIG_IP_VS=m
+# CONFIG_IP_VS_DEBUG is not set
+CONFIG_IP_VS_TAB_BITS=12
+CONFIG_IP_VS_PROTO_TCP=y
+CONFIG_IP_VS_PROTO_UDP=y
+CONFIG_IP_VS_PROTO_ESP=y
+CONFIG_IP_VS_PROTO_AH=y
+CONFIG_IP_VS_RR=m
+CONFIG_IP_VS_WRR=m
+CONFIG_IP_VS_LC=m
+CONFIG_IP_VS_WLC=m
+CONFIG_IP_VS_LBLC=m
+CONFIG_IP_VS_LBLCR=m
+CONFIG_IP_VS_DH=m
+CONFIG_IP_VS_SH=m
+CONFIG_IP_VS_SED=m
+CONFIG_IP_VS_NQ=m
+CONFIG_IP_VS_FTP=m
+
+
+CONFIG_IPV6=m
+CONFIG_IPV6_PRIVACY=y
+CONFIG_INET6_AH=m
+CONFIG_INET6_ESP=m
+CONFIG_INET6_IPCOMP=m
+CONFIG_IPV6_TUNNEL=m
+# CONFIG_DECNET is not set
+CONFIG_BRIDGE=m
+CONFIG_NETFILTER=y
+# CONFIG_NETFILTER_DEBUG is not set
+CONFIG_BRIDGE_NETFILTER=y
+
+#
+# IP: Netfilter Configuration
+#
+CONFIG_IP_NF_CONNTRACK=m
+CONFIG_IP_NF_FTP=m
+CONFIG_IP_NF_IRC=m
+CONFIG_IP_NF_TFTP=m
+CONFIG_IP_NF_AMANDA=m
+CONFIG_IP_NF_QUEUE=m
+CONFIG_IP_NF_RAW=m
+CONFIG_IP_NF_IPTABLES=m
+CONFIG_IP_NF_MATCH_COMMENT=m
+CONFIG_IP_NF_MATCH_LIMIT=m
+CONFIG_IP_NF_MATCH_IPRANGE=m
+CONFIG_IP_NF_MATCH_MAC=m
+CONFIG_IP_NF_MATCH_PKTTYPE=m
+CONFIG_IP_NF_MATCH_MARK=m
+CONFIG_IP_NF_MATCH_MULTIPORT=m
+CONFIG_IP_NF_MATCH_TOS=m
+CONFIG_IP_NF_MATCH_RECENT=m
+CONFIG_IP_NF_MATCH_ECN=m
+CONFIG_IP_NF_MATCH_DSCP=m
+CONFIG_IP_NF_MATCH_AH_ESP=m
+CONFIG_IP_NF_MATCH_LENGTH=m
+CONFIG_IP_NF_MATCH_TTL=m
+CONFIG_IP_NF_MATCH_TCPMSS=m
+CONFIG_IP_NF_MATCH_HELPER=m
+CONFIG_IP_NF_MATCH_STATE=m
+CONFIG_IP_NF_MATCH_CONNTRACK=m
+CONFIG_IP_NF_MATCH_OWNER=m
+CONFIG_IP_NF_MATCH_PHYSDEV=m
+CONFIG_IP_NF_MATCH_ADDRTYPE=m
+CONFIG_IP_NF_MATCH_REALM=m
+CONFIG_IP_NF_MATCH_SCTP=m
+CONFIG_IP_NF_FILTER=m
+CONFIG_IP_NF_TARGET_REJECT=m
+CONFIG_IP_NF_NAT=m
+CONFIG_IP_NF_NAT_NEEDED=y
+CONFIG_IP_NF_TARGET_MASQUERADE=m
+CONFIG_IP_NF_TARGET_REDIRECT=m
+CONFIG_IP_NF_TARGET_NETMAP=m
+CONFIG_IP_NF_TARGET_SAME=m
+CONFIG_IP_NF_TARGET_NOTRACK=m
+CONFIG_IP_NF_NAT_LOCAL=y
+CONFIG_IP_NF_NAT_SNMP_BASIC=m
+CONFIG_IP_NF_NAT_IRC=m
+CONFIG_IP_NF_NAT_FTP=m
+CONFIG_IP_NF_NAT_TFTP=m
+CONFIG_IP_NF_NAT_AMANDA=m
+CONFIG_IP_NF_MANGLE=m
+CONFIG_IP_NF_TARGET_TOS=m
+CONFIG_IP_NF_TARGET_ECN=m
+CONFIG_IP_NF_TARGET_DSCP=m
+CONFIG_IP_NF_TARGET_MARK=m
+CONFIG_IP_NF_TARGET_CLASSIFY=m
+CONFIG_IP_NF_TARGET_LOG=m
+CONFIG_IP_NF_TARGET_ULOG=m
+CONFIG_IP_NF_TARGET_TCPMSS=m
+CONFIG_IP_NF_ARPTABLES=m
+CONFIG_IP_NF_ARPFILTER=m
+CONFIG_IP_NF_ARP_MANGLE=m
+CONFIG_IP_NF_CT_ACCT=y
+CONFIG_IP_NF_CT_PROTO_SCTP=m
+# CONFIG_IP_NF_COMPAT_IPCHAINS is not set
+# CONFIG_IP_NF_COMPAT_IPFWADM is not set
+
+#
+# IPv6: Netfilter Configuration
+#
+# CONFIG_IP6_NF_QUEUE is not set
+CONFIG_IP6_NF_IPTABLES=m
+CONFIG_IP6_NF_MATCH_LIMIT=m
+CONFIG_IP6_NF_MATCH_MAC=m
+CONFIG_IP6_NF_MATCH_RT=m
+CONFIG_IP6_NF_MATCH_OPTS=m
+CONFIG_IP6_NF_MATCH_FRAG=m
+CONFIG_IP6_NF_MATCH_HL=m
+CONFIG_IP6_NF_MATCH_MULTIPORT=m
+CONFIG_IP6_NF_MATCH_OWNER=m
+CONFIG_IP6_NF_MATCH_MARK=m
+CONFIG_IP6_NF_MATCH_IPV6HEADER=m
+CONFIG_IP6_NF_MATCH_AHESP=m
+CONFIG_IP6_NF_MATCH_LENGTH=m
+CONFIG_IP6_NF_MATCH_EUI64=m
+CONFIG_IP6_NF_MATCH_PHYSDEV=m
+CONFIG_IP6_NF_FILTER=m
+CONFIG_IP6_NF_TARGET_LOG=m
+CONFIG_IP6_NF_MANGLE=m
+CONFIG_IP6_NF_TARGET_MARK=m
+CONFIG_IP6_NF_RAW=m
+
+
+#
+# Bridge: Netfilter Configuration
+#
+CONFIG_BRIDGE_NF_EBTABLES=m
+CONFIG_BRIDGE_EBT_BROUTE=m
+CONFIG_BRIDGE_EBT_T_FILTER=m
+CONFIG_BRIDGE_EBT_T_NAT=m
+CONFIG_BRIDGE_EBT_802_3=m
+CONFIG_BRIDGE_EBT_AMONG=m
+CONFIG_BRIDGE_EBT_ARP=m
+CONFIG_BRIDGE_EBT_IP=m
+CONFIG_BRIDGE_EBT_LIMIT=m
+CONFIG_BRIDGE_EBT_MARK=m
+CONFIG_BRIDGE_EBT_PKTTYPE=m
+CONFIG_BRIDGE_EBT_STP=m
+CONFIG_BRIDGE_EBT_VLAN=m
+CONFIG_BRIDGE_EBT_ARPREPLY=m
+CONFIG_BRIDGE_EBT_DNAT=m
+CONFIG_BRIDGE_EBT_MARK_T=m
+CONFIG_BRIDGE_EBT_REDIRECT=m
+CONFIG_BRIDGE_EBT_SNAT=m
+CONFIG_BRIDGE_EBT_LOG=m
+CONFIG_XFRM=y
+CONFIG_XFRM_USER=y
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+CONFIG_IP_SCTP=m
+# CONFIG_SCTP_DBG_MSG is not set
+# CONFIG_SCTP_DBG_OBJCNT is not set
+# CONFIG_SCTP_HMAC_NONE is not set
+# CONFIG_SCTP_HMAC_SHA1 is not set
+CONFIG_SCTP_HMAC_MD5=y
+CONFIG_ATM=m
+CONFIG_VLAN_8021Q=m
+CONFIG_LLC=m
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_IPX_INTERN is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+CONFIG_COPS_DAYNA=y
+CONFIG_COPS_TANGENT=y
+# CONFIG_IPDDP is not set
+CONFIG_IPDDP_ENCAP=y
+CONFIG_IPDDP_DECAP=y
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+CONFIG_NET_DIVERT=y
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_NET_HW_FLOWCONTROL is not set
+
+#
+# QoS and/or fair queueing
+#
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_CBQ=m
+CONFIG_NET_SCH_HTB=m
+CONFIG_NET_SCH_PRIO=m
+CONFIG_NET_SCH_RED=m
+CONFIG_NET_SCH_SFQ=m
+CONFIG_NET_SCH_TEQL=m
+CONFIG_NET_SCH_TBF=m
+CONFIG_NET_SCH_GRED=m
+CONFIG_NET_SCH_DSMARK=m
+CONFIG_NET_SCH_INGRESS=m
+CONFIG_NET_SCH_HFSC=m
+CONFIG_NET_SCH_NETEM=m
+CONFIG_NET_QOS=y
+CONFIG_NET_ESTIMATOR=y
+CONFIG_NET_CLS=y
+CONFIG_NET_CLS_TCINDEX=m
+CONFIG_NET_CLS_ROUTE4=m
+CONFIG_NET_CLS_ROUTE=y
+CONFIG_NET_CLS_FW=m
+CONFIG_NET_CLS_U32=m
+CONFIG_NET_CLS_RSVP=m
+CONFIG_NET_CLS_RSVP6=m
+CONFIG_NET_CLS_POLICE=y
+# CONFIG_NET_ACT_POLICE is not set
+CONFIG_CLS_U32_PERF=y
+CONFIG_NET_CLS_IND=y
+# CONFIG_NET_CLS_ACT is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+CONFIG_NETDEVICES=y
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+CONFIG_DUMMY=m
+CONFIG_BONDING=m
+# CONFIG_EQUALIZER is not set
+CONFIG_TUN=m
+CONFIG_ETHERTAP=m
+# CONFIG_NET_SB1000 is not set
+
+#
+# ATM
+# 
+CONFIG_ATM_CLIP=m
+CONFIG_ATM_LANE=m
+CONFIG_ATM_BR2684=m
+CONFIG_NET_SCH_ATM=m
+CONFIG_ATM_TCP=m
+CONFIG_ATM_LANAI=m
+CONFIG_ATM_ENI=m
+CONFIG_ATM_FIRESTREAM=m
+# CONFIG_ATM_ZATM is not set
+CONFIG_ATM_IDT77252=m
+CONFIG_ATM_AMBASSADOR=m
+CONFIG_ATM_HORIZON=m
+CONFIG_ATM_FORE200E_MAYBE=m
+CONFIG_ATM_HE=m
+CONFIG_PPPOATM=m
+CONFIG_ATM_NICSTAR=m
+# CONFIG_ATM_IA is not set
+
+
+# CONFIG_ATM_CLIP_NO_ICMP is not set
+# CONFIG_ATM_MPOA is not set
+# CONFIG_ATM_BR2684_IPFILTER is not set
+# CONFIG_ATM_ENI_DEBUG is not set
+# CONFIG_ATM_ENI_TUNE_BURST is not set
+# CONFIG_ATM_ZATM_DEBUG is not set
+# CONFIG_ATM_IDT77252_DEBUG is not set
+# CONFIG_ATM_IDT77252_RCV_ALL is not set
+# CONFIG_ATM_AMBASSADOR_DEBUG is not set
+# CONFIG_ATM_HORIZON_DEBUG is not set
+# CONFIG_ATM_FORE200E_PCA is not set
+# CONFIG_ATM_HE_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_IDT77105 is not set
+# CONFIG_ATM_IA_DEBUG is not set
+
+
+
+
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=m
+CONFIG_HAPPYMEAL=m
+CONFIG_SUNGEM=m
+CONFIG_NET_VENDOR_3COM=y
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+CONFIG_VORTEX=m
+CONFIG_TYPHOON=m
+# CONFIG_LANCE is not set
+CONFIG_NET_VENDOR_SMC=y
+# CONFIG_WD80x3 is not set
+# CONFIG_ULTRA is not set
+CONFIG_SMC9194=m
+CONFIG_NET_VENDOR_RACAL=y
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+
+#
+# Tulip family network device support
+#
+CONFIG_NET_TULIP=y
+CONFIG_DE2104X=m
+CONFIG_TULIP=m
+# CONFIG_TULIP_NAPI is not set
+
+# CONFIG_TULIP_MWI is not set
+CONFIG_TULIP_MMIO=y
+# CONFIG_NI5010 is not set
+# CONFIG_PCMCIA_XIRTULIP is not set
+CONFIG_DE4X5=m
+CONFIG_WINBOND_840=m
+CONFIG_DM9102=m
+CONFIG_PCMCIA_XIRCOM=m
+# CONFIG_AT1700 is not set
+# CONFIG_DEPCA is not set
+CONFIG_HP100=m
+# CONFIG_NET_ISA is not set
+# CONFIG_EWRK3 is not set
+CONFIG_E2100=m
+CONFIG_EEXPRESS=m
+CONFIG_EEXPRESS_PRO=m
+CONFIG_HPLAN_PLUS=m
+CONFIG_HPLAN=m
+CONFIG_LP486E=m
+CONFIG_ETH16I=m
+CONFIG_NE2000=m
+CONFIG_ZNET=m
+CONFIG_SEEQ8005=m
+CONFIG_LNE390=m
+CONFIG_NE3210=m
+CONFIG_ES3210=m
+CONFIG_NET_PCI=y
+CONFIG_PCNET32=m
+CONFIG_AMD8111_ETH=m
+CONFIG_AMD8111E_NAPI=y
+CONFIG_ADAPTEC_STARFIRE=m
+CONFIG_ADAPTEC_STARFIRE_NAPI=y
+# CONFIG_AC3200 is not set
+CONFIG_APRICOT=m
+CONFIG_B44=m
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+CONFIG_EEPRO100=m
+# CONFIG_EEPRO100_PIO is not set
+CONFIG_E100=m
+CONFIG_E100_NAPI=y
+CONFIG_FEALNX=m
+CONFIG_FORCEDETH=m
+CONFIG_NATSEMI=m
+CONFIG_NE2K_PCI=m
+CONFIG_8139CP=m
+CONFIG_8139TOO=m
+CONFIG_8139TOO_PIO=y
+# CONFIG_8139TOO_TUNE_TWISTER is not set
+CONFIG_8139TOO_8129=y
+# CONFIG_8139_OLD_RX_RESET is not set
+CONFIG_SIS900=m
+CONFIG_EPIC100=m
+# CONFIG_SUNDANCE is not set
+# CONFIG_SUNDANCE_MMIO is not set
+CONFIG_TLAN=m
+CONFIG_VIA_RHINE=m
+CONFIG_VIA_RHINE_MMIO=y
+CONFIG_VIA_VELOCITY=m
+CONFIG_NET_POCKET=y
+# CONFIG_ATP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+CONFIG_ACENIC=m
+# CONFIG_ACENIC_OMIT_TIGON_I is not set
+CONFIG_DL2K=m
+CONFIG_E1000=m
+CONFIG_E1000_NAPI=y
+CONFIG_NS83820=m
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+CONFIG_R8169=m
+CONFIG_R8169_NAPI=y
+CONFIG_SK98LIN=m
+CONFIG_TIGON3=m
+
+#
+# Ethernet (10000 Mbit)
+#
+CONFIG_IXGB=m
+CONFIG_IXGB_NAPI=y
+CONFIG_S2IO=m
+CONFIG_S2IO_NAPI=y
+CONFIG_FDDI=y
+# CONFIG_DEFXX is not set
+# CONFIG_SKFP is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PLIP is not set
+CONFIG_PPP=m
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_ASYNC=m
+CONFIG_PPP_SYNC_TTY=m
+CONFIG_PPP_DEFLATE=m
+CONFIG_IPPP_FILTER=y
+# CONFIG_PPP_BSDCOMP is not set
+CONFIG_PPPOE=m
+# CONFIG_SLIP is not set
+
+#
+# Wireless LAN (non-hamradio)
+#
+CONFIG_NET_RADIO=y
+
+#
+# Obsolete Wireless cards support (pre-802.11)
+#
+# CONFIG_STRIP is not set
+# CONFIG_ARLAN is not set
+CONFIG_WAVELAN=m
+CONFIG_PCMCIA_WAVELAN=m
+CONFIG_PCMCIA_NETWAVE=m
+
+#
+# Wireless 802.11 Frequency Hopping cards support
+#
+# CONFIG_PCMCIA_RAYCS is not set
+
+#
+# Wireless 802.11b ISA/PCI cards support
+#
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
+CONFIG_AIRO=m
+CONFIG_HERMES=m
+CONFIG_PLX_HERMES=m
+CONFIG_TMD_HERMES=m
+CONFIG_PCI_HERMES=m
+CONFIG_ATMEL=m
+CONFIG_PCI_ATMEL=m
+CONFIG_PRISM54=m
+
+#
+# Wireless 802.11b Pcmcia/Cardbus cards support
+#
+CONFIG_PCMCIA_HERMES=m
+CONFIG_AIRO_CS=m
+CONFIG_PCMCIA_ATMEL=m
+CONFIG_PCMCIA_WL3501=m
+CONFIG_NET_WIRELESS=y
+
+#
+# Token Ring devices
+#
+CONFIG_TR=y
+CONFIG_IBMOL=m
+CONFIG_3C359=m
+CONFIG_TMS380TR=m
+CONFIG_TMSPCI=m
+CONFIG_ABYSS=m
+CONFIG_IBMTR=m
+CONFIG_IBMLS=m
+CONFIG_SKISA=m
+CONFIG_PROTEON=m
+CONFIG_SMCTR=m
+CONFIG_PCMCIA_IBMTR=m
+
+
+CONFIG_NET_FC=y
+# CONFIG_SHAPER is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+
+#
+# PCMCIA network device support
+#
+CONFIG_NET_PCMCIA=y
+CONFIG_PCMCIA_3C589=m
+CONFIG_PCMCIA_3C574=m
+CONFIG_PCMCIA_FMVJ18X=m
+CONFIG_PCMCIA_PCNET=m
+CONFIG_PCMCIA_NMCLAN=m
+CONFIG_PCMCIA_SMC91C92=m
+CONFIG_PCMCIA_XIRC2PS=m
+CONFIG_PCMCIA_AXNET=m
+
+#
+# Amateur Radio support
+#
+# CONFIG_HAMRADIO is not set
+
+#
+# IrDA (infrared) support
+#
+# CONFIG_IRDA is not set
+# CONFIG_IRDA is not set
+# CONFIG_IRDA_DEBUG is not set
+CONFIG_IRLAN=m
+CONFIG_IRNET=m
+CONFIG_IRCOMM=m
+# CONFIG_IRDA_ULTRA is not set
+CONFIG_IRDA_CACHE_LAST_LSAP=y
+CONFIG_IRDA_FAST_RR=y
+CONFIG_IRTTY_SIR=m
+CONFIG_DONGLE=y
+CONFIG_ESI_DONGLE=m
+CONFIG_ACTISYS_DONGLE=m
+CONFIG_TEKRAM_DONGLE=m
+CONFIG_IRPORT_SIR=m
+# CONFIG_DONGLE_OLD is not set
+CONFIG_LITELINK_DONGLE=m
+CONFIG_MA600_DONGLE=m
+CONFIG_GIRBIL_DONGLE=m
+CONFIG_MCP2120_DONGLE=m
+CONFIG_OLD_BELKIN_DONGLE=m
+CONFIG_ACT200L_DONGLE=m
+
+CONFIG_USB_IRDA=m
+CONFIG_NSC_FIR=m
+CONFIG_SIGMATEL_FIR=m
+# CONFIG_WINBOND_FIR is not set
+# CONFIG_TOSHIBA_FIR is not set
+# CONFIG_SMC_IRCC_FIR is not set
+# CONFIG_ALI_FIR is not set
+# CONFIG_VLSI_FIR is not set
+# CONFIG_VIA_FIR is not set
+
+
+
+#
+# Bluetooth support
+#
+CONFIG_BT=m
+CONFIG_BT_L2CAP=m
+CONFIG_BT_SCO=m
+CONFIG_BT_CMTP=m
+CONFIG_BT_RFCOMM=m
+CONFIG_BT_RFCOMM_TTY=y
+CONFIG_BT_BNEP=m
+CONFIG_BT_BNEP_MC_FILTER=y
+CONFIG_BT_BNEP_PROTO_FILTER=y
+CONFIG_BT_HIDP=m
+
+#
+# Bluetooth device drivers
+#
+CONFIG_BT_HCIUSB=m
+CONFIG_BT_HCIUART=m
+CONFIG_BT_HCIUART_H4=y
+CONFIG_BT_HCIUART_BCSP=y
+CONFIG_BT_HCIUART_BCSP_TXCRC=y
+CONFIG_BT_HCIDTL1=m
+CONFIG_BT_HCIBT3C=m
+CONFIG_BT_HCIBLUECARD=m
+CONFIG_BT_HCIBTUART=m
+CONFIG_BT_HCIVHCI=m
+CONFIG_BT_HCIUSB_SCO=y
+CONFIG_BT_HCIBCM203X=m
+CONFIG_BT_HCIBFUSB=m
+CONFIG_USB_BLUETOOTH_TTY=m
+
+#
+# ISDN subsystem
+#
+
+CONFIG_ISDN=m
+CONFIG_ISDN_I4L=m
+CONFIG_ISDN_DRV_AVMB1_B1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCI=m
+CONFIG_ISDN_DRV_AVMB1_T1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCMCIA=m
+CONFIG_ISDN_DRV_AVMB1_T1PCI=m
+CONFIG_ISDN_DRV_AVMB1_C4=m
+
+CONFIG_ISDN_PPP=y
+CONFIG_ISDN_PPP_VJ=y
+CONFIG_ISDN_MPP=y
+# CONFIG_ISDN_PPP_BSDCOMP is not set
+CONFIG_ISDN_TTY_FAX=y
+CONFIG_DE_AOC=y
+
+CONFIG_ISDN_AUDIO=y
+
+CONFIG_ISDN_DRV_HISAX=m
+CONFIG_ISDN_DRV_ICN=m
+CONFIG_ISDN_DRV_PCBIT=m
+CONFIG_ISDN_DRV_SC=m
+CONFIG_ISDN_DRV_ACT2000=m
+CONFIG_ISDN_DRV_TPAM=m
+CONFIG_ISDN_DRV_AVMB1_B1PCIV4=y
+CONFIG_ISDN_DRV_AVMB1_AVM_CS=m
+
+CONFIG_ISDN_CAPI_CAPIDRV=m
+
+CONFIG_HISAX_EURO=y
+CONFIG_HISAX_1TR6=y
+CONFIG_HISAX_NI1=y
+CONFIG_HISAX_MAX_CARDS=8
+CONFIG_HISAX_16_0=y
+CONFIG_HISAX_16_3=y
+CONFIG_HISAX_TELESPCI=y
+CONFIG_HISAX_S0BOX=y
+CONFIG_HISAX_AVM_A1=y
+CONFIG_HISAX_FRITZPCI=y
+CONFIG_HISAX_AVM_A1_PCMCIA=y
+CONFIG_HISAX_ELSA=y
+CONFIG_HISAX_IX1MICROR2=y
+CONFIG_HISAX_DIEHLDIVA=y
+CONFIG_HISAX_ASUSCOM=y
+CONFIG_HISAX_TELEINT=y
+CONFIG_HISAX_HFCS=y
+CONFIG_HISAX_SEDLBAUER=y
+CONFIG_HISAX_SPORTSTER=y
+CONFIG_HISAX_MIC=y
+CONFIG_HISAX_NETJET=y
+CONFIG_HISAX_NETJET_U=y
+CONFIG_HISAX_NICCY=y
+CONFIG_HISAX_ISURF=y
+CONFIG_HISAX_HSTSAPHIR=y
+CONFIG_HISAX_BKM_A4T=y
+CONFIG_HISAX_SCT_QUADRO=y
+CONFIG_HISAX_GAZEL=y
+CONFIG_HISAX_HFC_PCI=y
+CONFIG_HISAX_W6692=y
+CONFIG_HISAX_HFC_SX=y
+CONFIG_HISAX_ENTERNOW_PCI=y
+# CONFIG_HISAX_DEBUG is not set
+CONFIG_HISAX_AVM_A1_CS=m
+CONFIG_HISAX_ST5481=m
+CONFIG_HISAX_HFCUSB=m
+CONFIG_HISAX_FRITZ_PCIPNP=m
+CONFIG_HISAX_NO_SENDCOMPLETE=y
+CONFIG_HISAX_NO_LLC=y
+CONFIG_HISAX_NO_KEYPAD=y
+CONFIG_HISAX_SEDLBAUER_CS=m
+CONFIG_HISAX_ELSA_CS=m
+CONFIG_HISAX_TELES_CS=m
+
+CONFIG_ISDN_DRV_LOOP=m
+CONFIG_HYSDN=m
+CONFIG_HYSDN_CAPI=y
+
+
+#
+# CAPI subsystem
+#
+CONFIG_ISDN_CAPI=m
+CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON=y
+CONFIG_ISDN_CAPI_MIDDLEWARE=y
+CONFIG_ISDN_CAPI_CAPI20=m
+CONFIG_ISDN_CAPI_CAPIFS_BOOL=y
+CONFIG_ISDN_CAPI_CAPIFS=m
+
+#
+# CAPI hardware drivers
+#
+
+#
+# Active AVM cards
+#
+CONFIG_CAPI_AVM=y
+
+#
+# Active Eicon DIVA Server cards
+#
+CONFIG_CAPI_EICON=y
+CONFIG_ISDN_DIVAS=m
+CONFIG_ISDN_DIVAS_BRIPCI=y
+CONFIG_ISDN_DIVAS_PRIPCI=y
+CONFIG_ISDN_DIVAS_DIVACAPI=m
+CONFIG_ISDN_DIVAS_USERIDI=m
+CONFIG_ISDN_DIVAS_MAINT=m
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+CONFIG_INPUT_JOYDEV=m
+# CONFIG_INPUT_TSDEV is not set
+CONFIG_INPUT_EVDEV=y
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input I/O drivers
+#
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=m
+CONFIG_GAMEPORT_NS558=m
+CONFIG_GAMEPORT_L4=m
+CONFIG_GAMEPORT_EMU10K1=m
+CONFIG_GAMEPORT_VORTEX=m
+CONFIG_GAMEPORT_FM801=m
+CONFIG_GAMEPORT_CS461x=m
+CONFIG_SERIO=y
+CONFIG_SERIO_I8042=y
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_RAW is not set
+
+# CONFIG_SERIO_CT82C710 is not set
+# CONFIG_SERIO_PARKBD is not set
+# CONFIG_SERIO_PCIPS2 is not set
+
+#
+# Input Device Drivers
+#
+CONFIG_INPUT_KEYBOARD=y
+CONFIG_KEYBOARD_ATKBD=y
+# CONFIG_KEYBOARD_SUNKBD is not set
+# CONFIG_KEYBOARD_XTKBD is not set
+# CONFIG_KEYBOARD_NEWTON is not set
+# CONFIG_KEYBOARD_LKKBD is not set
+CONFIG_INPUT_MOUSE=y
+CONFIG_MOUSE_PS2=y
+CONFIG_MOUSE_SERIAL=m
+CONFIG_MOUSE_INPORT=m
+CONFIG_MOUSE_ATIXL=y
+CONFIG_MOUSE_LOGIBM=m
+CONFIG_MOUSE_PC110PAD=m
+CONFIG_MOUSE_VSXXXAA=m
+CONFIG_INPUT_JOYSTICK=y
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+CONFIG_JOYSTICK_JOYDUMP=m
+CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_GUNZE=m
+CONFIG_INPUT_MISC=y
+CONFIG_INPUT_PCSPKR=m
+CONFIG_INPUT_UINPUT=m 
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+CONFIG_SERIAL_NONSTANDARD=y
+# CONFIG_ROCKETPORT is not set
+CONFIG_SYNCLINK=m
+CONFIG_SYNCLINKMP=m
+CONFIG_N_HDLC=m
+CONFIG_STALDRV=y
+# CONFIG_FTAPE is not set
+CONFIG_IBM_ASM=m
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_CS=m
+# CONFIG_SERIAL_8250_ACPI is not set
+CONFIG_SERIAL_8250_NR_UARTS=4
+CONFIG_SERIAL_8250_EXTENDED=y
+# CONFIG_SERIAL_8250_MANY_PORTS is not set
+CONFIG_SERIAL_8250_SHARE_IRQ=y
+CONFIG_SERIAL_8250_DETECT_IRQ=y
+CONFIG_SERIAL_8250_MULTIPORT=y
+CONFIG_SERIAL_8250_RSA=y
+# CONFIG_COMPUTONE is not set
+# CONFIG_CYCLADES is not set
+# CONFIG_DIGIEPCA is not set
+# CONFIG_DIGI is not set
+# CONFIG_ESPSERIAL is not set
+# CONFIG_MOXA_INTELLIO is not set
+# CONFIG_MOXA_SMARTIO is not set
+# CONFIG_ISI is not set
+# CONFIG_RISCOM8 is not set
+# CONFIG_SPECIALIX is not set
+# CONFIG_SX is not set
+# CONFIG_RIO is not set
+# CONFIG_STALLION is not set
+# CONFIG_ISTALLION is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+# CONFIG_LEGACY_PTYS is not set
+CONFIG_PRINTER=m
+CONFIG_LP_CONSOLE=y
+CONFIG_PPDEV=m
+# CONFIG_TIPAR is not set
+
+#
+# I2C support
+#
+CONFIG_I2C=m
+CONFIG_I2C_CHARDEV=m
+
+#
+# I2C Algorithms
+#
+# CONFIG_I2C_DEBUG_ALGO is not set
+CONFIG_I2C_ALGOBIT=m
+CONFIG_I2C_ALGOPCF=m
+
+#
+# I2C Hardware Bus support
+#
+CONFIG_I2C_ALI1535=m
+CONFIG_I2C_ALI15X3=m
+CONFIG_I2C_AMD756=m
+CONFIG_I2C_AMD8111=m
+CONFIG_I2C_I801=m
+CONFIG_I2C_I810=m
+CONFIG_I2C_ISA=m
+CONFIG_I2C_NFORCE2=m
+CONFIG_I2C_PIIX4=m
+CONFIG_I2C_PROSAVAGE=m
+CONFIG_I2C_SAVAGE4=m
+# CONFIG_SCx200_ACB is not set
+CONFIG_I2C_SIS5595=m
+CONFIG_I2C_SIS630=m
+CONFIG_I2C_SIS96X=m
+CONFIG_I2C_VIA=m
+CONFIG_I2C_VIAPRO=m
+CONFIG_I2C_VOODOO3=m
+# CONFIG_I2C_ELEKTOR is not set
+CONFIG_I2C_PARPORT=m
+CONFIG_I2C_PARPORT_LIGHT=m
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+# CONFIG_I2C_PARPORT is not set
+CONFIG_I2C_ALI1563=m
+# CONFIG_I2C_PARPORT_LIGHT is not set
+CONFIG_I2C_ALGOPCA=m
+# CONFIG_I2C_PCA_ISA is not set
+
+
+#
+# I2C Hardware Sensors Chip support
+#
+CONFIG_I2C_SENSOR=m
+CONFIG_SENSORS_ADM1021=m
+CONFIG_SENSORS_EEPROM=m
+CONFIG_SENSORS_IT87=m
+CONFIG_SENSORS_LM75=m
+CONFIG_SENSORS_LM78=m
+CONFIG_SENSORS_LM80=m
+CONFIG_SENSORS_LM83=m
+CONFIG_SENSORS_LM85=m
+CONFIG_SENSORS_VIA686A=m
+CONFIG_SENSORS_W83781D=m
+CONFIG_SENSORS_ASB100=m
+CONFIG_SENSORS_LM90=m
+CONFIG_SENSORS_W83L785TS=m
+CONFIG_SENSORS_FSCHER=m
+CONFIG_SENSORS_GL518SM=m
+CONFIG_SENSORS_DS1621=m
+CONFIG_SENSORS_W83627HF=m
+CONFIG_SENSORS_PCF8574=m
+CONFIG_SENSORS_PCF8591=m
+CONFIG_SENSORS_RTC8564=m
+CONFIG_SENSORS_MAX1619=m
+CONFIG_SENSORS_ADM1025=m
+CONFIG_SENSORS_ADM1031=m
+CONFIG_SENSORS_LM77=m
+CONFIG_SENSORS_SMSC47M1=m
+
+# CONFIG_W1 is not set
+
+#
+# Mice
+#
+CONFIG_CRASH=m
+
+#
+# IPMI
+#
+CONFIG_IPMI_HANDLER=m
+# CONFIG_IPMI_PANIC_EVENT is not set
+CONFIG_IPMI_DEVICE_INTERFACE=m
+CONFIG_IPMI_WATCHDOG=m
+CONFIG_IPMI_SI=m
+CONFIG_IPMI_POWEROFF=m
+
+#
+# Watchdog Cards
+#
+CONFIG_WATCHDOG=y
+# CONFIG_WATCHDOG_NOWAYOUT is not set
+CONFIG_SOFT_WATCHDOG=m
+CONFIG_WDT=m
+# CONFIG_WDT_501 is not set
+CONFIG_WDTPCI=m
+CONFIG_WDT_501_PCI=y
+CONFIG_PCWATCHDOG=m
+CONFIG_ACQUIRE_WDT=m
+CONFIG_ADVANTECH_WDT=m
+CONFIG_EUROTECH_WDT=m
+CONFIG_IB700_WDT=m
+CONFIG_I8XX_TCO=m
+# CONFIG_MIXCOMWD is not set
+# CONFIG_SCx200_WDT is not set
+# CONFIG_60XX_WDT is not set
+CONFIG_W83877F_WDT=m
+CONFIG_W83627HF_WDT=m
+CONFIG_MACHZ_WDT=m
+CONFIG_SC520_WDT=m
+CONFIG_ALIM7101_WDT=m
+CONFIG_ALIM1535_WDT=m
+CONFIG_SC1200_WDT=m
+CONFIG_WAFER_WDT=m
+CONFIG_CPU5_WDT=m
+CONFIG_PCIPCWATCHDOG=m
+CONFIG_USBPCWATCHDOG=m
+
+
+CONFIG_HW_RANDOM=m
+CONFIG_NVRAM=m
+CONFIG_RTC=y
+CONFIG_DTLK=m
+# CONFIG_R3964 is not set
+# CONFIG_APPLICOM is not set
+CONFIG_SONYPI=m
+
+#
+# Ftape, the floppy tape device driver
+#
+CONFIG_AGP=y
+CONFIG_AGP_ALI=y
+CONFIG_AGP_ATI=y
+CONFIG_AGP_AMD=y
+CONFIG_AGP_AMD64=y
+CONFIG_AGP_INTEL=y
+CONFIG_AGP_INTEL_MCH=y
+CONFIG_AGP_NVIDIA=y
+CONFIG_AGP_SIS=y
+CONFIG_AGP_SWORKS=y
+CONFIG_AGP_VIA=y
+CONFIG_AGP_EFFICEON=y
+CONFIG_DRM=y
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+CONFIG_DRM_R128=m
+CONFIG_DRM_RADEON=m
+CONFIG_DRM_I810=m
+CONFIG_DRM_I830=m
+CONFIG_DRM_MGA=m
+# CONFIG_DRM_SIS is not set
+CONFIG_DRM_I915=m
+
+
+
+#
+# PCMCIA character devices
+#
+CONFIG_SYNCLINK_CS=m
+
+
+
+# CONFIG_MWAVE is not set
+CONFIG_RAW_DRIVER=y
+CONFIG_MAX_RAW_DEVS=8192
+CONFIG_HANGCHECK_TIMER=m
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Video For Linux
+#
+
+#
+# Video Adapters
+#
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+CONFIG_VIDEO_OVCAMCHIP=m
+
+
+#
+# Radio Adapters
+#
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+CONFIG_DVB_CORE=m
+
+#
+# Supported Frontend Modules
+#
+CONFIG_DVB_STV0299=m
+# CONFIG_DVB_SP887X is not set
+# CONFIG_DVB_ALPS_TDLB7 is not set
+CONFIG_DVB_ALPS_TDMB7=m
+CONFIG_DVB_ATMEL_AT76C651=m
+CONFIG_DVB_CX24110=m
+CONFIG_DVB_GRUNDIG_29504_491=m
+CONFIG_DVB_GRUNDIG_29504_401=m
+CONFIG_DVB_MT312=m
+CONFIG_DVB_VES1820=m
+CONFIG_DVB_VES1X93=m
+CONFIG_DVB_TWINHAN_DST=m
+CONFIG_DVB_TTUSB_DEC=m
+CONFIG_DVB_BT8XX=m
+# CONFIG_DVB_TDA1004X is not set
+CONFIG_DVB_NXT6000=m
+
+#
+# Supported SAA7146 based PCI Adapters
+#
+CONFIG_DVB_AV7110=m
+CONFIG_DVB_AV7110_OSD=y
+# CONFIG_DVB_AV7110_FIRMWARE is not set
+CONFIG_DVB_BUDGET=m
+CONFIG_DVB_BUDGET_CI=m
+CONFIG_DVB_BUDGET_AV=m
+CONFIG_DVB_BUDGET_PATCH=m
+
+#
+# Supported USB Adapters
+#
+CONFIG_DVB_TTUSB_BUDGET=m
+
+#
+# Supported FlexCopII (B2C2) Adapters
+#
+CONFIG_DVB_B2C2_SKYSTAR=m
+CONFIG_VIDEO_SAA7146=m
+CONFIG_VIDEO_SAA7146_VV=m
+CONFIG_VIDEO_VIDEOBUF=m
+CONFIG_VIDEO_TUNER=m
+CONFIG_VIDEO_BUF=m
+CONFIG_VIDEO_BTCX=m
+
+#
+# Graphics support
+#
+CONFIG_FB=y
+# CONFIG_FB_CYBER2000 is not set
+# CONFIG_FB_IMSTT is not set
+CONFIG_FB_VGA16=m
+CONFIG_FB_VESA=y
+CONFIG_VIDEO_SELECT=y
+# CONFIG_FB_HGA is not set
+CONFIG_FB_RIVA=m
+# CONFIG_FB_RIVA_DEBUG is not set
+# CONFIG_FB_RIVA_I2C is not set
+CONFIG_FB_I810=m
+CONFIG_FB_I810_GTF=y
+# CONFIG_FB_MATROX is not set
+CONFIG_FB_MATROX_MILLENIUM=y
+CONFIG_FB_MATROX_MYSTIQUE=y
+CONFIG_FB_MATROX_G450=y
+CONFIG_FB_MATROX_G100=y
+CONFIG_FB_MATROX_I2C=m
+CONFIG_FB_MATROX_MAVEN=m
+CONFIG_FB_MATROX_MULTIHEAD=y
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_RADEON_DEBUG is not set
+# CONFIG_FB_RADEON_OLD is not set
+CONFIG_FB_RADEON_I2C=y
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_ATY is not set
+CONFIG_FB_ATY_CT=y
+CONFIG_FB_ATY_GX=y
+# CONFIG_FB_ATY_XL_INIT is not set
+# CONFIG_FB_SIS is not set
+CONFIG_FB_SIS_300=y
+CONFIG_FB_SIS_315=y
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VIRTUAL is not set
+CONFIG_FB_KYRO=m
+# CONFIG_FB_PM2 is not set
+# CONFIG_FB_PM2_FIFO_DISCONNECT is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+CONFIG_FB_CIRRUS=m
+
+#
+# Console display driver support
+#
+CONFIG_VGA_CONSOLE=y
+CONFIG_MDA_CONSOLE=m
+CONFIG_DUMMY_CONSOLE=y
+CONFIG_FRAMEBUFFER_CONSOLE=y
+# CONFIG_FONTS is not set
+
+
+#
+# Logo configuration
+#
+CONFIG_LOGO=y
+# CONFIG_LOGO_LINUX_MONO is not set
+# CONFIG_LOGO_LINUX_VGA16 is not set
+CONFIG_LOGO_LINUX_CLUT224=y
+
+#
+# Sound
+#
+CONFIG_SOUND=m
+
+#
+# Advanced Linux Sound Architecture
+#
+CONFIG_SND=m
+CONFIG_SND_SEQUENCER=m
+CONFIG_SND_SEQ_DUMMY=m
+CONFIG_SND_OSSEMUL=y
+CONFIG_SND_MIXER_OSS=m
+CONFIG_SND_PCM_OSS=m
+CONFIG_SND_SEQUENCER_OSS=y
+CONFIG_SND_RTCTIMER=m
+# CONFIG_SND_VERBOSE_PRINTK is not set
+# CONFIG_SND_DEBUG is not set
+CONFIG_SND_BIT32_EMUL=y
+
+#
+# Generic devices
+#
+CONFIG_SND_DUMMY=m
+CONFIG_SND_VIRMIDI=m
+CONFIG_SND_MTPAV=m
+# CONFIG_SND_SERIAL_U16550 is not set
+CONFIG_SND_MPU401=m
+
+#
+# ISA devices
+#
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+
+#
+# PCI devices
+#
+CONFIG_SND_ALI5451=m
+CONFIG_SND_AZT3328=m
+CONFIG_SND_CS46XX=m
+CONFIG_SND_CS46XX_NEW_DSP=y
+CONFIG_SND_CS4281=m
+CONFIG_SND_EMU10K1=m
+CONFIG_SND_KORG1212=m
+CONFIG_SND_NM256=m
+CONFIG_SND_RME32=m
+CONFIG_SND_RME96=m
+CONFIG_SND_RME9652=m
+CONFIG_SND_HDSP=m
+CONFIG_SND_TRIDENT=m
+CONFIG_SND_YMFPCI=m
+CONFIG_SND_ALS4000=m
+CONFIG_SND_CMIPCI=m
+CONFIG_SND_ENS1370=m
+CONFIG_SND_ENS1371=m
+CONFIG_SND_ES1938=m
+CONFIG_SND_ES1968=m
+CONFIG_SND_MAESTRO3=m
+CONFIG_SND_FM801=m
+CONFIG_SND_ICE1712=m
+CONFIG_SND_ICE1724=m
+CONFIG_SND_INTEL8X0=m
+CONFIG_SND_SONICVIBES=m
+CONFIG_SND_VIA82XX=m
+CONFIG_SND_VX222=m
+CONFIG_SND_BT87X=m
+CONFIG_SND_ATIIXP=m
+CONFIG_SND_ATIIXP_MODEM=m
+CONFIG_SND_AU8810=m
+CONFIG_SND_AU8820=m
+CONFIG_SND_AU8830=m
+CONFIG_SND_MIXART=m
+CONFIG_SND_FM801_TEA575X=m
+CONFIG_SND_INTEL8X0M=m
+CONFIG_SND_PDAUDIOCF=m
+
+
+#
+# ALSA USB devices
+#
+CONFIG_SND_USB_AUDIO=m
+CONFIG_SND_USB_USX2Y=m
+
+#
+# PCMCIA devices
+#
+# CONFIG_SND_VXPOCKET is not set
+# CONFIG_SND_VXP440 is not set
+
+#
+# Open Sound System
+#
+# CONFIG_SOUND_PRIME is not set
+# CONFIG_SOUND_BT878 is not set
+# CONFIG_SOUND_CMPCI is not set
+
+#
+# USB support
+#
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+CONFIG_USB_DEVICEFS=y
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+CONFIG_USB_SUSPEND=y
+
+#
+# USB Host Controller Drivers
+#
+CONFIG_USB_EHCI_HCD=m
+CONFIG_USB_EHCI_SPLIT_ISO=y
+CONFIG_USB_EHCI_ROOT_HUB_TT=y
+CONFIG_USB_OHCI_HCD=m
+CONFIG_USB_UHCI_HCD=m
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_AUDIO is not set
+
+#
+# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem
+#
+CONFIG_USB_MIDI=m
+CONFIG_USB_ACM=m
+CONFIG_USB_PRINTER=m
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_USB_STORAGE=m
+# CONFIG_USB_STORAGE_DEBUG is not set
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_DPCM=y
+CONFIG_USB_STORAGE_HP8200e=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_RW_DETECT=y
+
+#
+# USB Human Interface Devices (HID)
+#
+CONFIG_USB_HID=y
+CONFIG_USB_HIDINPUT=y
+CONFIG_HID_FF=y
+CONFIG_HID_PID=y
+CONFIG_LOGITECH_FF=y
+CONFIG_THRUSTMASTER_FF=y
+CONFIG_USB_HIDDEV=y
+
+#
+# USB HID Boot Protocol drivers
+#
+# CONFIG_USB_KBD is not set
+# CONFIG_USB_MOUSE is not set
+CONFIG_USB_AIPTEK=m
+CONFIG_USB_WACOM=m
+CONFIG_USB_KBTAB=m
+CONFIG_USB_POWERMATE=m
+CONFIG_USB_XPAD=m
+
+#
+# USB Imaging devices
+#
+CONFIG_USB_MDC800=m
+CONFIG_USB_MICROTEK=m
+CONFIG_USB_HPUSBSCSI=m
+
+#
+# USB Multimedia devices
+#
+CONFIG_USB_DABUSB=m
+CONFIG_USB_VICAM=m
+CONFIG_USB_DSBR=m
+CONFIG_USB_IBMCAM=m
+CONFIG_USB_KONICAWC=m
+CONFIG_USB_OV511=m
+CONFIG_USB_SE401=m
+CONFIG_USB_STV680=m
+CONFIG_USB_SN9C102=m
+
+#
+# USB Network adaptors
+#
+CONFIG_USB_CATC=m
+CONFIG_USB_KAWETH=m
+CONFIG_USB_PEGASUS=m
+CONFIG_USB_RTL8150=m
+CONFIG_USB_USBNET=m
+CONFIG_USB_SPEEDTOUCH=m
+
+#
+# USB Host-to-Host Cables
+#
+CONFIG_USB_AN2720=y
+CONFIG_USB_BELKIN=y
+CONFIG_USB_GENESYS=y
+CONFIG_USB_NET1080=y
+CONFIG_USB_PL2301=y
+
+#
+# Intelligent USB Devices/Gadgets
+#
+CONFIG_USB_ARMLINUX=y
+CONFIG_USB_EPSON2888=y
+CONFIG_USB_ZAURUS=y
+CONFIG_USB_CDCETHER=y
+
+#
+# USB Network Adapters
+#
+CONFIG_USB_AX8817X=y
+
+#
+# USB port drivers
+#
+CONFIG_USB_USS720=m
+
+#
+# USB Serial Converter support
+#
+CONFIG_USB_SERIAL=m
+CONFIG_USB_SERIAL_GENERIC=y
+CONFIG_USB_SERIAL_BELKIN=m
+CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m
+CONFIG_USB_SERIAL_EMPEG=m
+CONFIG_USB_SERIAL_FTDI_SIO=m
+CONFIG_USB_SERIAL_VISOR=m
+CONFIG_USB_SERIAL_IPAQ=m
+CONFIG_USB_SERIAL_IR=m
+CONFIG_USB_SERIAL_EDGEPORT=m
+CONFIG_USB_SERIAL_EDGEPORT_TI=m
+CONFIG_USB_SERIAL_KEYSPAN_PDA=m
+CONFIG_USB_SERIAL_KEYSPAN=m
+CONFIG_USB_SERIAL_KEYSPAN_MPR=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XA=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XB=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19=y
+CONFIG_USB_SERIAL_KEYSPAN_USA18X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QW=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QI=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y
+CONFIG_USB_SERIAL_KLSI=m
+CONFIG_USB_SERIAL_KOBIL_SCT=m
+CONFIG_USB_SERIAL_MCT_U232=m
+CONFIG_USB_SERIAL_PL2303=m
+CONFIG_USB_SERIAL_SAFE=m
+CONFIG_USB_SERIAL_SAFE_PADDED=y
+CONFIG_USB_SERIAL_CYBERJACK=m
+CONFIG_USB_SERIAL_XIRCOM=m
+CONFIG_USB_SERIAL_OMNINET=m
+CONFIG_USB_SERIAL_WHITEHEAT=m
+CONFIG_USB_EZUSB=y
+CONFIG_USB_EMI62=m
+CONFIG_USB_LED=m
+CONFIG_USB_G_SERIAL=m
+
+
+#
+# USB Miscellaneous drivers
+#
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_TIGL is not set
+CONFIG_USB_AUERSWALD=m
+CONFIG_USB_RIO500=m
+CONFIG_USB_LCD=m
+CONFIG_USB_TEST=m
+# CONFIG_USB_GADGET is not set
+# CONFIG_USB_GADGET_PXA2XX is not set
+# CONFIG_USB_GADGET_GOKU is not set
+# CONFIG_USB_GADGET_SA1100 is not set
+CONFIG_USB_ZERO=m
+CONFIG_USB_ETH=m
+CONFIG_USB_GADGETFS=m
+CONFIG_USB_W9968CF=m
+CONFIG_USB_PWC=m
+CONFIG_USB_LEGOTOWER=m
+CONFIG_USB_FILE_STORAGE=m
+# CONFIG_USB_FILE_STORAGE_TEST is not set
+CONFIG_USB_MTOUCH=m
+CONFIG_USB_ATI_REMOTE=m
+CONFIG_USB_ALI_M5632=y
+# CONFIG_USB_CYTHERM is not set
+CONFIG_USB_EGALAX=m
+CONFIG_USB_PHIDGETSERVO=m
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT2_FS_POSIX_ACL=y
+CONFIG_EXT2_FS_SECURITY=y
+CONFIG_EXT3_FS=m
+CONFIG_EXT3_FS_XATTR=y
+CONFIG_EXT3_FS_POSIX_ACL=y
+CONFIG_EXT3_FS_SECURITY=y
+CONFIG_JBD=m
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_REISERFS_CHECK is not set
+CONFIG_REISERFS_PROC_INFO=y
+CONFIG_REISERFS_FS_XATTR=y
+CONFIG_REISERFS_FS_POSIX_ACL=y
+CONFIG_REISERFS_FS_SECURITY=y
+# CONFIG_JFS_FS is not set
+# CONFIG_JFS_DEBUG is not set
+# CONFIG_JFS_STATISTICS is not set
+CONFIG_JFS_POSIX_ACL=y
+# CONFIG_XFS_FS is not set
+# CONFIG_XFS_RT is not set
+CONFIG_XFS_QUOTA=y
+CONFIG_XFS_POSIX_ACL=y
+CONFIG_XFS_SECURITY=y
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_QUOTA=y
+# CONFIG_QFMT_V1 is not set
+CONFIG_QFMT_V2=y
+CONFIG_QUOTACTL=y
+# CONFIG_AUTOFS_FS is not set
+CONFIG_AUTOFS4_FS=m
+
+#
+# CD-ROM/DVD Filesystems
+#
+CONFIG_ISO9660_FS=y
+CONFIG_JOLIET=y
+CONFIG_ZISOFS=y
+CONFIG_ZISOFS_FS=y
+CONFIG_UDF_FS=m
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=m
+CONFIG_MSDOS_FS=m
+CONFIG_VFAT_FS=m
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="ascii"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+# CONFIG_DEVFS_FS is not set
+CONFIG_DEVPTS_FS_XATTR=y
+CONFIG_DEVPTS_FS_SECURITY=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_XATTR=y
+CONFIG_TMPFS_SECURITY=y
+CONFIG_HUGETLBFS=y
+CONFIG_HUGETLB_PAGE=y
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not seta
+# CONFIG_AFFS_FS is not set
+# uses sleepon and needs a major update
+CONFIG_HFS_FS=m
+CONFIG_HFSPLUS_FS=m
+# CONFIG_BEFS_FS is not set
+# CONFIG_BEFS_DEBUG is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_JFFS_FS is not set
+CONFIG_JFFS2_FS=m
+CONFIG_JFFS2_FS_DEBUG=0
+CONFIG_JFFS2_FS_NAND=y
+CONFIG_CRAMFS=m
+CONFIG_VXFS_FS=m
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_QNX4FS_RW is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_UFS_FS_WRITE is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=m
+CONFIG_NFS_V3=y
+CONFIG_NFS_V4=y
+CONFIG_NFS_DIRECTIO=y
+CONFIG_NFSD=m
+CONFIG_NFSD_V3=y
+CONFIG_NFSD_V4=y
+CONFIG_NFSD_TCP=y
+CONFIG_LOCKD=m
+CONFIG_LOCKD_V4=y
+CONFIG_EXPORTFS=m
+CONFIG_SUNRPC=m
+CONFIG_SUNRPC_GSS=m
+CONFIG_RPCSEC_GSS_KRB5=m
+CONFIG_RPCSEC_GSS_SPKM3=m
+CONFIG_SMB_FS=m
+# CONFIG_SMB_NLS_DEFAULT is not set
+CONFIG_CIFS=m
+# CONFIG_CIFS_STATS is not set
+CONFIG_CIFS_XATTR=y
+CONFIG_CIFS_POSIX=y
+# CONFIG_NCP_FS is not set
+CONFIG_NCPFS_PACKET_SIGNING=y
+CONFIG_NCPFS_IOCTL_LOCKING=y
+CONFIG_NCPFS_STRONG=y
+CONFIG_NCPFS_NFS_NS=y
+CONFIG_NCPFS_OS2_NS=y
+CONFIG_NCPFS_SMALLDOS=y
+CONFIG_NCPFS_NLS=y
+CONFIG_NCPFS_EXTRAS=y
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+# CONFIG_RXRPC is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_ACORN_PARTITION is not set
+CONFIG_OSF_PARTITION=y
+# CONFIG_AMIGA_PARTITION is not set
+# CONFIG_ATARI_PARTITION is not set
+CONFIG_MAC_PARTITION=y
+CONFIG_MSDOS_PARTITION=y
+CONFIG_BSD_DISKLABEL=y
+CONFIG_MINIX_SUBPARTITION=y
+CONFIG_SOLARIS_X86_PARTITION=y
+CONFIG_UNIXWARE_DISKLABEL=y
+# CONFIG_LDM_PARTITION is not set
+CONFIG_SGI_PARTITION=y
+# CONFIG_ULTRIX_PARTITION is not set
+CONFIG_SUN_PARTITION=y
+CONFIG_EFI_PARTITION=y
+CONFIG_NLS=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS_DEFAULT="utf8"
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_CODEPAGE_737=m
+CONFIG_NLS_CODEPAGE_775=m
+CONFIG_NLS_CODEPAGE_850=m
+CONFIG_NLS_CODEPAGE_852=m
+CONFIG_NLS_CODEPAGE_855=m
+CONFIG_NLS_CODEPAGE_857=m
+CONFIG_NLS_CODEPAGE_860=m
+CONFIG_NLS_CODEPAGE_861=m
+CONFIG_NLS_CODEPAGE_862=m
+CONFIG_NLS_CODEPAGE_863=m
+CONFIG_NLS_CODEPAGE_864=m
+CONFIG_NLS_CODEPAGE_865=m
+CONFIG_NLS_CODEPAGE_866=m
+CONFIG_NLS_CODEPAGE_869=m
+CONFIG_NLS_CODEPAGE_936=m
+CONFIG_NLS_CODEPAGE_950=m
+CONFIG_NLS_CODEPAGE_932=m
+CONFIG_NLS_CODEPAGE_949=m
+CONFIG_NLS_CODEPAGE_874=m
+CONFIG_NLS_ISO8859_8=m
+CONFIG_NLS_CODEPAGE_1250=m
+CONFIG_NLS_CODEPAGE_1251=m
+CONFIG_NLS_ISO8859_1=m
+CONFIG_NLS_ISO8859_2=m
+CONFIG_NLS_ISO8859_3=m
+CONFIG_NLS_ISO8859_4=m
+CONFIG_NLS_ISO8859_5=m
+CONFIG_NLS_ISO8859_6=m
+CONFIG_NLS_ISO8859_7=m
+CONFIG_NLS_ISO8859_9=m
+CONFIG_NLS_ISO8859_13=m
+CONFIG_NLS_ISO8859_14=m
+CONFIG_NLS_ISO8859_15=m
+CONFIG_NLS_KOI8_R=m
+CONFIG_NLS_KOI8_U=m
+CONFIG_NLS_UTF8=m
+CONFIG_NLS_ASCII=y
+
+#
+# Profiling support
+#
+CONFIG_PROFILING=y
+CONFIG_OPROFILE=m
+
+#
+# Tux
+#
+CONFIG_TUX=m
+CONFIG_TUX_EXTCGI=y
+# CONFIG_TUX_EXTENDED_LOG is not set
+# CONFIG_TUX_DEBUG is not set
+
+
+#
+# Kernel hacking
+#
+CONFIG_DEBUG_KERNEL=y
+# CONFIG_DEBUG_SLAB is not set
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_HIGHMEM=y
+# CONFIG_DEBUG_INFO is not set
+CONFIG_DEBUG_SPINLOCK_SLEEP=y
+# CONFIG_FRAME_POINTER is not set
+CONFIG_CC_OPTIMIZE_FOR_SIZE=y
+# CONFIG_DEBUG_DRIVER is not set
+
+#
+# Security options
+#
+CONFIG_SECURITY=y
+CONFIG_SECURITY_NETWORK=y
+CONFIG_SECURITY_CAPABILITIES=y
+# CONFIG_SECURITY_ROOTPLUG is not set
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM=y
+CONFIG_SECURITY_SELINUX_DISABLE=y
+CONFIG_SECURITY_SELINUX_DEVELOP=y
+CONFIG_SECURITY_SELINUX_AVC_STATS=y
+# CONFIG_SECURITY_SELINUX_MLS is not set
+CONFIG_SECURITY_SELINUX_BOOTPARAM_VALUE=1
+CONFIG_AUDIT=y
+CONFIG_AUDITSYSCALL=y
+
+#
+# Cryptographic options
+#
+CONFIG_CRYPTO=y
+CONFIG_CRYPTO_HMAC=y
+CONFIG_CRYPTO_NULL=m
+CONFIG_CRYPTO_MD4=m
+CONFIG_CRYPTO_MD5=m
+CONFIG_CRYPTO_SHA1=y
+CONFIG_CRYPTO_SHA256=m
+CONFIG_CRYPTO_SHA512=m
+CONFIG_CRYPTO_DES=m
+CONFIG_CRYPTO_BLOWFISH=m
+CONFIG_CRYPTO_TWOFISH=m
+CONFIG_CRYPTO_SERPENT=m
+CONFIG_CRYPTO_AES=m
+CONFIG_CRYPTO_CAST5=m
+CONFIG_CRYPTO_CAST6=m
+CONFIG_CRYPTO_DEFLATE=m
+CONFIG_CRYPTO_ARC4=m
+CONFIG_CRYPTO_MICHAEL_MIC=m
+# CONFIG_CRYPTO_TEST is not set
+CONFIG_LIBCRC32C=m
+CONFIG_CRYPTO_CRC32C=m
+CONFIG_CRYPTO_SIGNATURE_DSA=y
+CONFIG_CRYPTO_MPILIB=y
+CONFIG_CRYPTO_TEA=m
+CONFIG_CRYPTO_KHAZAD=m
+CONFIG_CRYPTO_WP512=m
+
+#
+# Library routines
+#
+CONFIG_CRC32=m
+CONFIG_CRC_CCITT=m
+
+CONFIG_ZLIB_INFLATE=y
+CONFIG_ZLIB_DEFLATE=m
+CONFIG_PC=y
+# CONFIG_SCSI_BUSLOGIC is not set
+# CONFIG_SCSI_INIA100 is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+# CONFIG_IPX is not set
+# CONFIG_IPDDP is not set
+# CONFIG_IRDA is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_ISAPNP is not set
+# CONFIG_PCMCIA_AHA152X is not set
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_IEEE1394 is not set
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_WD80x3 is not set
+# CONFIG_IRDA is not set
+# CONFIG_GAMEPORT is not set
+# CONFIG_DVB is not set
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+# CONFIG_REISERFS_FS is not set
+# CONFIG_XFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_ROMFS_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_BINFMT_AOUT is not set
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+# CONFIG_DRM_SIS is not set
+# CONFIG_BLK_DEV_UMEM is not set
+# CONFIG_MWAVE is not set
+# CONFIG_ROCKETPORT is not set
+# CONFIG_R3964 is not set
+# CONFIG_TIPAR is not set
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+# CONFIG_VIDEO_DEV is not set
+# CONFIG_PLIP is not set
+# CONFIG_FB_MATROX is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_HGA is not set
+# CONFIG_FB_ATY is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_AHA1542 is not set
+CONFIG_SCSI_FUTURE_DOMAIN=m
+# CONFIG_SCSI_IN2000 is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_I82092 is not set
+# CONFIG_YELLOWFIN is not set
+# CONFIG_SUNDANCE is not set
+# CONFIG_ULTRA is not set
+# CONFIG_SKFP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+# CONFIG_AC3200 is not set
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+# CONFIG_LANCE is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+# CONFIG_HAMACHI is not set
+CONFIG_HP100=m
+# CONFIG_EQUALIZER is not set
+# CONFIG_NET_SB1000 is not set
+# CONFIG_DEPCA is not set
+# CONFIG_ATP is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_INFTL is not set
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PCI is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_AUDIT=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_JFS_FS is not set
+# CONFIG_I2C_PCA_ISA is not set
+CONFIG_RAW_DRIVER=y
+# CONFIG_MTD_SCB2_FLASH is not set
+CONFIG_UID16=y
+# CONFIG_X86_PC is not set
+# CONFIG_X86_ELAN is not set
+# CONFIG_X86_VOYAGER is not set
+# CONFIG_X86_NUMAQ is not set
+# CONFIG_X86_SUMMIT is not set
+# CONFIG_X86_BIGSMP is not set
+# CONFIG_X86_VISWS is not set
+CONFIG_X86_GENERICARCH=y
+# CONFIG_X86_ES7000 is not set
+# CONFIG_M386 is not set
+# CONFIG_M486 is not set
+# CONFIG_M586 is not set
+# CONFIG_M586TSC is not set
+# CONFIG_M586MMX is not set
+CONFIG_M686=y
+# CONFIG_MPENTIUMII is not set
+# CONFIG_MPENTIUMIII is not set
+# CONFIG_MPENTIUMM is not set
+# CONFIG_MPENTIUM4 is not set
+# CONFIG_MK6 is not set
+# CONFIG_MK7 is not set
+# CONFIG_MK8 is not set
+# CONFIG_MCRUSOE is not set
+# CONFIG_MWINCHIPC6 is not set
+# CONFIG_MWINCHIP2 is not set
+# CONFIG_MWINCHIP3D is not set
+# CONFIG_MCYRIXIII is not set
+# CONFIG_MVIAC3_2 is not set
+CONFIG_X86_GENERIC=y
+CONFIG_X86_CMPXCHG=y
+CONFIG_X86_XADD=y
+CONFIG_X86_L1_CACHE_SHIFT=7
+CONFIG_RWSEM_XCHGADD_ALGORITHM=y
+CONFIG_X86_PPRO_FENCE=y
+CONFIG_X86_WP_WORKS_OK=y
+CONFIG_X86_INVLPG=y
+CONFIG_X86_BSWAP=y
+CONFIG_X86_POPAD_OK=y
+CONFIG_X86_GOOD_APIC=y
+CONFIG_X86_INTEL_USERCOPY=y
+CONFIG_X86_USE_PPRO_CHECKSUM=y
+# CONFIG_HPET is not set
+CONFIG_HPET_TIMER=y
+CONFIG_HPET_EMULATE_RTC=y
+CONFIG_NR_CPUS=32
+CONFIG_X86_LOCAL_APIC=y
+CONFIG_X86_IO_APIC=y
+CONFIG_X86_TSC=y
+CONFIG_X86_MCE=y
+# CONFIG_X86_MCE_NONFATAL is not set
+CONFIG_X86_MCE_P4THERMAL=y
+CONFIG_TOSHIBA=m
+CONFIG_I8K=m
+CONFIG_SONYPI=m
+CONFIG_MICROCODE=m
+CONFIG_X86_MSR=m
+CONFIG_X86_CPUID=m
+CONFIG_EDD=m
+# CONFIG_NUMA is not set
+# CONFIG_NOHIGHMEM is not set
+CONFIG_HIGHMEM4G=y
+CONFIG_HIGHMEM64G=y
+# CONFIG_HIGHMEM64G is not set
+CONFIG_HIGHMEM=y
+CONFIG_HIGHPTE=y
+# CONFIG_MATH_EMULATION is not set
+CONFIG_MTRR=y
+CONFIG_HAVE_DEC_LOCK=y
+# CONFIG_X86_UP_APIC is not set
+CONFIG_X86_PM_TIMER=y
+# CONFIG_X86_4G is not set
+# CONFIG_EFI is not set
+CONFIG_REGPARM=y
+# CONFIG_PCI_GOBIOS is not set
+# CONFIG_PCI_GODIRECT is not set
+# CONFIG_PCI_GOMMCONFIG is not set
+CONFIG_PCI_GOANY=y
+CONFIG_MDA_CONSOLE=m
+CONFIG_SYNCLINK_CS=m
+CONFIG_SYNCLINK=m
+CONFIG_SYNCLINKMP=m
+CONFIG_HP100=m
+CONFIG_PCMCIA_FDOMAIN=m
+CONFIG_SCSI_FUTURE_DOMAIN=m
+CONFIG_CRASH=m
+CONFIG_CAPI_EICON=y
+CONFIG_I2O=m
+CONFIG_I2O_BLOCK=m
+CONFIG_I2O_SCSI=m
+CONFIG_I2O_PROC=m
+CONFIG_I2O_CONFIG=y
+CONFIG_APM=y
+# CONFIG_APM_IGNORE_USER_SUSPEND is not set
+# CONFIG_APM_DO_ENABLE is not set
+CONFIG_APM_CPU_IDLE=y
+# CONFIG_APM_DISPLAY_BLANK is not set
+CONFIG_APM_RTC_IS_GMT=y
+# CONFIG_APM_ALLOW_INTS is not set
+# CONFIG_APM_REAL_MODE_POWER_OFF is not set
+CONFIG_X86_FIND_SMP_CONFIG=y
+CONFIG_X86_MPPARSE=y
+CONFIG_ACPI=y
+CONFIG_ACPI_BOOT=y
+CONFIG_ACPI_INTERPRETER=y
+CONFIG_ACPI_SLEEP=y
+CONFIG_ACPI_AC=m
+CONFIG_ACPI_BATTERY=m
+CONFIG_ACPI_BUTTON=m
+CONFIG_ACPI_FAN=y
+CONFIG_ACPI_PROCESSOR=y
+CONFIG_ACPI_THERMAL=y
+CONFIG_ACPI_ASUS=m
+CONFIG_ACPI_TOSHIBA=m
+# CONFIG_ACPI_DEBUG is not set
+CONFIG_ACPI_BUS=y
+CONFIG_ACPI_EC=y
+CONFIG_ACPI_POWER=y
+CONFIG_ACPI_PCI=y
+CONFIG_ACPI_SYSTEM=y
+CONFIG_ACPI_NUMA=y
+CONFIG_ACPI_BLACKLIST_YEAR=2001
+CONFIG_X86_ACPI_CPUFREQ=y
+# CONFIG_X86_ACPI_CPUFREQ_PROC_INTF is not set
+CONFIG_X86_POWERNOW_K6=m
+CONFIG_X86_POWERNOW_K7=y
+CONFIG_X86_POWERNOW_K8=m
+# CONFIG_X86_GX_SUSPMOD is not set
+# CONFIG_X86_SPEEDSTEP_CENTRINO is not set
+CONFIG_X86_SPEEDSTEP_ICH=y
+CONFIG_X86_SPEEDSTEP_SMI=m
+CONFIG_X86_SPEEDSTEP_LIB=y
+# CONFIG_X86_SPEEDSTEP_RELAXED_CAP_CHECK is not set
+CONFIG_X86_P4_CLOCKMOD=m
+CONFIG_X86_LONGRUN=y
+CONFIG_X86_LONGHAUL=y
+CONFIG_X86_SMP=y
+CONFIG_X86_HT=y
+CONFIG_X86_BIOS_REBOOT=y
+CONFIG_X86_TRAMPOLINE=y
+CONFIG_TUX=m
+CONFIG_NVRAM=m
+CONFIG_IBM_ASM=m
+CONFIG_CRYPTO_AES_586=m
+CONFIG_GENERIC_ISA_DMA=y
+CONFIG_SCHED_SMT=y
+# CONFIG_IRQBALANCE is not set
+# CONFIG_SOFTWARE_SUSPEND is not set
+# CONFIG_PM_DEBUG is not set
+CONFIG_CPU_FREQ=y
+# CONFIG_CPU_FREQ_PROC_INTF is not set
+# CONFIG_CPU_FREQ_DEFAULT_GOV_PERFORMANCE is not set
+CONFIG_CPU_FREQ_DEFAULT_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_PERFORMANCE=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=m
+CONFIG_CPU_FREQ_GOV_USERSPACE=m
+CONFIG_CPU_FREQ_GOV_ONDEMAND=m
+# CONFIG_CPU_FREQ_24_API is not set
+CONFIG_CPU_FREQ_TABLE=y
+CONFIG_DEBUG_STACKOVERFLOW=y
+CONFIG_DEBUG_STACK_USAGE=y
+# CONFIG_DEBUG_PAGEALLOC is not set
+# CONFIG_KPROBES is not set
+CONFIG_KEXEC=y
+CONFIG_NETDUMP=m
+# CONFIG_SCHEDSTATS is not set
+CONFIG_PCI_DIRECT=y
+CONFIG_PCI_MMCONFIG=y
+CONFIG_PCI_BIOS=y
+CONFIG_HOTPLUG_PCI=y
+# CONFIG_HOTPLUG_PCI_FAKE is not set
+CONFIG_HOTPLUG_PCI_COMPAQ=m
+# CONFIG_HOTPLUG_PCI_COMPAQ_NVRAM is not set
+CONFIG_HOTPLUG_PCI_IBM=m
+CONFIG_HOTPLUG_PCI_ACPI=m 
+CONFIG_HOTPLUG_PCI_ACPI_IBM=m
+# CONFIG_HOTPLUG_PCI_CPCI is not set
+CONFIG_HOTPLUG_PCI_PCIE=m
+# CONFIG_HOTPLUG_PCI_PCIE_POLL_EVENT_MODE is not set
+CONFIG_HOTPLUG_PCI_SHPC=m
+# CONFIG_HOTPLUG_PCI_SHPC_POLL_EVENT_MODE is not set
+# CONFIG_HOTPLUG_PCI_SHPC_PHPRM_LEGACY is not set
+CONFIG_PM=y
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
+CONFIG_M686=y
+# CONFIG_NOHIGHMEM is not set
+CONFIG_HIGHMEM64G=y
+CONFIG_HOTPLUG_PCI=y
+CONFIG_HOTPLUG_PCI_COMPAQ=m
+CONFIG_HOTPLUG_PCI_IBM=m
+# CONFIG_HIGHMEM64G is not set
+# CONFIG_EWRK3 is not set
+CONFIG_NR_CPUS=32
+# CONFIG_X86_PC is not set
+CONFIG_X86_GENERICARCH=y
diff --git a/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-i686.config b/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-i686.config
new file mode 100644 (file)
index 0000000..8d66567
--- /dev/null
@@ -0,0 +1,2735 @@
+#
+# Automatically generated make config: don't edit
+#
+CONFIG_MMU=y
+# CONFIG_SMP is not set
+# CONFIG_HOTPLUG_CPU is not set
+CONFIG_LOCALVERSION=""
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_CLEAN_COMPILE=y
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+
+#
+# General setup
+#
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+CONFIG_BSD_PROCESS_ACCT=y
+# CONFIG_BSD_PROCESS_ACCT_V3 is not set
+CONFIG_SYSCTL=y
+CONFIG_LOG_BUF_SHIFT=17
+# CONFIG_IKCONFIG is not set
+# CONFIG_EMBEDDED is not set
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_ALL is not set
+CONFIG_KALLSYMS_EXTRA_PASS=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+# CONFIG_PREEMPT is not set
+CONFIG_PREEMPT_VOLUNTARY=y
+CONFIG_POSIX_MQUEUE=y
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+CONFIG_MODVERSIONS=y
+CONFIG_KMOD=y
+CONFIG_MODULE_SIG=y
+# CONFIG_MODULE_SIG_FORCE is not set
+
+#
+# Bus options (PCI, PCMCIA, EISA, MCA, ISA)
+#
+CONFIG_PCI=y
+CONFIG_PCI_MSI=y
+CONFIG_PCI_LEGACY_PROC=y
+# CONFIG_PCI_NAMES is not set
+CONFIG_ISA=y
+# CONFIG_EISA is not set
+# CONFIG_MCA is not set
+# CONFIG_SCx200 is not set
+CONFIG_HOTPLUG=y
+
+#
+# PCMCIA/CardBus support
+#
+CONFIG_PCMCIA=m
+# CONFIG_PCMCIA_DEBUG is not set
+CONFIG_YENTA=y
+CONFIG_CARDBUS=y
+# CONFIG_I82092 is not set
+CONFIG_I82365=m
+CONFIG_PD6729=m
+CONFIG_TCIC=m
+CONFIG_PCMCIA_PROBE=y
+
+#
+# Executable file formats
+#
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_AOUT is not set
+CONFIG_BINFMT_MISC=y
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_FW_LOADER=y
+
+#
+# Memory Technology Devices (MTD)
+#
+CONFIG_MTD=m
+# CONFIG_MTD_DEBUG is not set
+CONFIG_MTD_PARTITIONS=m
+CONFIG_MTD_CONCAT=m
+CONFIG_MTD_REDBOOT_PARTS=m
+CONFIG_MTD_CMDLINE_PARTS=y
+CONFIG_MTD_PARTITIONS=y
+#
+# User Modules And Translation Layers
+#
+CONFIG_MTD_CHAR=m
+CONFIG_MTD_BLOCK=m
+CONFIG_MTD_BLOCK_RO=m
+CONFIG_FTL=m
+CONFIG_NFTL=m
+CONFIG_NFTL_RW=y
+# CONFIG_INFTL is not set
+
+#
+# RAM/ROM/Flash chip drivers
+#
+CONFIG_MTD_CFI=m
+CONFIG_MTD_JEDECPROBE=m
+CONFIG_MTD_GEN_PROBE=m
+# CONFIG_MTD_CFI_ADV_OPTIONS is not set
+CONFIG_MTD_CFI_INTELEXT=m
+CONFIG_MTD_CFI_AMDSTD=m
+CONFIG_MTD_CFI_STAA=m
+CONFIG_MTD_RAM=m
+CONFIG_MTD_ROM=m
+CONFIG_MTD_ABSENT=m
+# CONFIG_MTD_OBSOLETE_CHIPS is not set
+
+#
+# Mapping drivers for chip access
+#
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PHYSMAP is not set
+# CONFIG_MTD_PNC2000 is not set
+CONFIG_MTD_SC520CDP=m
+CONFIG_MTD_NETSC520=m
+CONFIG_MTD_SBC_GXX=m
+CONFIG_MTD_ELAN_104NC=m
+CONFIG_MTD_SCx200_DOCFLASH=m
+# CONFIG_MTD_AMD76XROM is not set
+# CONFIG_MTD_SCB2_FLASH is not set
+# CONFIG_MTD_NETtel is not set
+# CONFIG_MTD_DILNETPC is not set
+# CONFIG_MTD_L440GX is not set
+# CONFIG_MTD_PCI is not set
+
+#
+# Self-contained MTD device drivers
+#
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_PMC551_BUGFIX is not set
+# CONFIG_MTD_PMC551_DEBUG is not set
+# CONFIG_MTD_SLRAM is not set
+CONFIG_MTD_MTDRAM=m
+CONFIG_MTDRAM_TOTAL_SIZE=4096
+CONFIG_MTDRAM_ERASE_SIZE=128
+# CONFIG_MTD_BLKMTD is not set
+
+#
+# Disk-On-Chip Device Drivers
+#
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+CONFIG_MTD_DOCPROBE=m
+# CONFIG_MTD_DOCPROBE_ADVANCED is not set
+CONFIG_MTD_DOCPROBE_ADDRESS=0
+
+#
+# NAND Flash Device Drivers
+#
+CONFIG_MTD_NAND=m
+# CONFIG_MTD_NAND_VERIFY_WRITE is not set
+CONFIG_MTD_NAND_IDS=m
+
+# CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
+# CONFIG_MTD_REDBOOT_PARTS_READONLY is not set
+CONFIG_MTD_CFI_AMDSTD_RETRY=3
+# CONFIG_MTD_ICHXROM is not set
+# CONFIG_MTD_PHRAM is not set
+# CONFIG_MTD_NAND_DISKONCHIP is not set
+# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set
+
+
+#
+# Parallel port support
+#
+CONFIG_PARPORT=m
+CONFIG_PARPORT_PC=m
+CONFIG_PARPORT_PC_CML1=m
+CONFIG_PARPORT_SERIAL=m
+# CONFIG_PARPORT_PC_FIFO is not set
+# CONFIG_PARPORT_PC_SUPERIO is not set
+CONFIG_PARPORT_PC_PCMCIA=m
+# CONFIG_PARPORT_OTHER is not set
+CONFIG_PARPORT_1284=y
+
+#
+# Plug and Play support
+#
+CONFIG_PNP=y
+# CONFIG_PNP_DEBUG is not set
+
+#
+# Protocols
+#
+# CONFIG_ISAPNP is not set
+# CONFIG_PNPBIOS is not set
+
+#
+# Block devices
+#
+CONFIG_BLK_DEV_FD=m
+# CONFIG_BLK_DEV_XD is not set
+# CONFIG_PARIDE is not set
+CONFIG_BLK_CPQ_DA=m
+CONFIG_BLK_CPQ_CISS_DA=m
+CONFIG_CISS_SCSI_TAPE=y
+CONFIG_BLK_DEV_DAC960=m
+# CONFIG_BLK_DEV_UMEM is not set
+CONFIG_BLK_DEV_LOOP=m
+CONFIG_BLK_DEV_CRYPTOLOOP=m
+CONFIG_BLK_DEV_NBD=m
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=16384
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_BLK_DEV_ATIIXP=y
+CONFIG_BLK_DEV_DELKIN=y
+CONFIG_BLK_DEV_IT8212=y
+CONFIG_LBD=y
+# CONFIG_DCSSBLK is not set
+
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_IDE_GENERIC=y
+# CONFIG_HPT34X_AUTODMA is not set
+
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_HD_IDE is not set
+CONFIG_BLK_DEV_IDEDISK=y
+CONFIG_IDEDISK_MULTI_MODE=y
+CONFIG_BLK_DEV_IDECS=m
+CONFIG_BLK_DEV_IDECD=y
+# CONFIG_BLK_DEV_IDETAPE is not set
+CONFIG_BLK_DEV_IDEFLOPPY=y
+CONFIG_BLK_DEV_IDESCSI=m
+# CONFIG_IDE_TASK_IOCTL is not set
+# CONFIG_IDE_TASKFILE_IO is not set
+# CONFIG_BLK_DEV_IDE_SATA is not set
+
+#
+# IDE chipset support/bugfixes
+#
+# CONFIG_BLK_DEV_CMD640 is not set
+# CONFIG_BLK_DEV_CMD640_ENHANCED is not set
+CONFIG_BLK_DEV_IDEPNP=y
+CONFIG_BLK_DEV_IDEPCI=y
+CONFIG_IDEPCI_SHARE_IRQ=y
+# CONFIG_BLK_DEV_OFFBOARD is not set
+CONFIG_BLK_DEV_GENERIC=y
+# CONFIG_BLK_DEV_OPTI621 is not set
+CONFIG_BLK_DEV_RZ1000=y
+CONFIG_BLK_DEV_IDEDMA_PCI=y
+# CONFIG_BLK_DEV_IDEDMA_FORCED is not set
+CONFIG_IDEDMA_PCI_AUTO=y
+# CONFIG_IDEDMA_ONLYDISK is not set
+CONFIG_BLK_DEV_AEC62XX=y
+CONFIG_BLK_DEV_ALI15X3=y
+# CONFIG_WDC_ALI15X3 is not set
+CONFIG_BLK_DEV_AMD74XX=y
+CONFIG_BLK_DEV_CMD64X=y
+CONFIG_BLK_DEV_TRIFLEX=y
+CONFIG_BLK_DEV_CY82C693=y
+CONFIG_BLK_DEV_CS5520=y
+CONFIG_BLK_DEV_CS5530=y
+CONFIG_BLK_DEV_HPT34X=y
+CONFIG_BLK_DEV_HPT366=y
+# CONFIG_BLK_DEV_SC1200 is not set
+CONFIG_BLK_DEV_PIIX=y
+# CONFIG_BLK_DEV_NS87415 is not set
+CONFIG_BLK_DEV_PDC202XX_OLD=y
+# CONFIG_PDC202XX_BURST is not set
+CONFIG_BLK_DEV_PDC202XX_NEW=y
+CONFIG_PDC202XX_FORCE=y
+CONFIG_BLK_DEV_SVWKS=y
+CONFIG_BLK_DEV_SIIMAGE=y
+CONFIG_BLK_DEV_SIS5513=y
+CONFIG_BLK_DEV_SLC90E66=y
+# CONFIG_BLK_DEV_TRM290 is not set
+CONFIG_BLK_DEV_VIA82CXXX=y
+# CONFIG_IDE_CHIPSETS is not set
+CONFIG_BLK_DEV_IDEDMA=y
+# CONFIG_IDEDMA_IVB is not set
+CONFIG_IDEDMA_AUTO=y
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+CONFIG_SCSI=m
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=m
+CONFIG_CHR_DEV_ST=m
+CONFIG_CHR_DEV_OSST=m
+CONFIG_BLK_DEV_SR=m
+CONFIG_BLK_DEV_SR_VENDOR=y
+CONFIG_CHR_DEV_SG=m
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SPI_ATTRS=y
+CONFIG_SCSI_FC_ATTRS=y
+
+#
+# SCSI low-level drivers
+#
+CONFIG_BLK_DEV_3W_XXXX_RAID=m
+CONFIG_SCSI_3W_9XXX=m
+# CONFIG_SCSI_7000FASST is not set
+CONFIG_SCSI_ACARD=m
+CONFIG_SCSI_AHA152X=m
+# CONFIG_SCSI_AHA1542 is not set
+CONFIG_SCSI_AACRAID=m
+CONFIG_SCSI_AIC7XXX=m
+CONFIG_AIC7XXX_CMDS_PER_DEVICE=4
+CONFIG_AIC7XXX_RESET_DELAY_MS=15000
+# CONFIG_AIC7XXX_PROBE_EISA_VL is not set
+# CONFIG_AIC7XXX_BUILD_FIRMWARE is not set
+# CONFIG_AIC7XXX_DEBUG_ENABLE is not set
+CONFIG_AIC7XXX_DEBUG_MASK=0
+# CONFIG_AIC7XXX_REG_PRETTY_PRINT is not set
+CONFIG_SCSI_AIC7XXX_OLD=m
+CONFIG_SCSI_AIC79XX=m
+CONFIG_AIC79XX_CMDS_PER_DEVICE=4
+CONFIG_AIC79XX_RESET_DELAY_MS=15000
+# CONFIG_AIC79XX_BUILD_FIRMWARE is not set
+# CONFIG_AIC79XX_ENABLE_RD_STRM is not set
+# CONFIG_AIC79XX_DEBUG_ENABLE is not set
+CONFIG_AIC79XX_DEBUG_MASK=0
+# CONFIG_AIC79XX_REG_PRETTY_PRINT is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_IN2000 is not set
+CONFIG_MEGARAID_NEWGEN=y
+CONFIG_MEGARAID_MM=m
+CONFIG_MEGARAID_MAILBOX=m
+CONFIG_SCSI_SATA=y
+CONFIG_SCSI_SATA_SVW=m
+CONFIG_SCSI_ATA_PIIX=m
+CONFIG_SCSI_SATA_PROMISE=m
+CONFIG_SCSI_SATA_VIA=m
+CONFIG_BLK_DEV_SX8=m
+CONFIG_SCSI_SATA_VITESSE=m
+CONFIG_SCSI_SATA_SIL=m
+CONFIG_SCSI_SATA_SIS=m
+CONFIG_SCSI_SATA_SX4=m
+CONFIG_SCSI_SATA_NV=m
+CONFIG_SCSI_SATA_AHCI=m
+
+# CONFIG_SCSI_BUSLOGIC is not set
+CONFIG_SCSI_INITIO=m
+# CONFIG_SCSI_OMIT_FLASHPOINT is not set
+# CONFIG_SCSI_CPQFCTS is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_DTC3280 is not set
+# CONFIG_SCSI_EATA is not set
+# CONFIG_SCSI_EATA_PIO is not set
+CONFIG_SCSI_FUTURE_DOMAIN=m
+CONFIG_SCSI_GDTH=m
+# CONFIG_SCSI_GENERIC_NCR5380 is not set
+# CONFIG_SCSI_GENERIC_NCR5380_MMIO is not set
+CONFIG_SCSI_IPS=m
+# CONFIG_SCSI_INIA100 is not set
+CONFIG_SCSI_PPA=m
+CONFIG_SCSI_IMM=m
+# CONFIG_SCSI_IZIP_EPP16 is not set
+# CONFIG_SCSI_IZIP_SLOW_CTR is not set
+# CONFIG_SCSI_NCR53C406A is not set
+CONFIG_SCSI_SYM53C8XX_2=m
+CONFIG_SCSI_SYM53C8XX_DMA_ADDRESSING_MODE=1
+CONFIG_SCSI_SYM53C8XX_DEFAULT_TAGS=16
+CONFIG_SCSI_SYM53C8XX_MAX_TAGS=64
+# CONFIG_SCSI_SYM53C8XX_IOMAPPED is not set
+# CONFIG_SCSI_PAS16 is not set
+# CONFIG_SCSI_PSI240I is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_SCSI_QLOGIC_FC is not set
+# CONFIG_SCSI_QLOGIC_FC_FIRMWARE is not set
+CONFIG_SCSI_QLOGIC_1280=m
+# CONFIG_SCSI_SYM53C416 is not set
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_T128 is not set
+# CONFIG_SCSI_U14_34F is not set
+# CONFIG_SCSI_ULTRASTOR is not set
+# CONFIG_SCSI_NSP32 is not set
+# CONFIG_SCSI_DEBUG is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_SCSI_QLA2XXX=m
+CONFIG_SCSI_QLA21XX=m
+CONFIG_SCSI_QLA22XX=m
+CONFIG_SCSI_QLA2300=m
+CONFIG_SCSI_QLA2322=m
+CONFIG_SCSI_QLA6312=m
+CONFIG_SCSI_QLA6322=m
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_DPT_I2O is not set
+
+CONFIG_SCSI_LPFC=m
+
+#
+# PCMCIA SCSI adapter support
+#
+# CONFIG_PCMCIA_AHA152X is not set
+CONFIG_PCMCIA_FDOMAIN=m
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+
+
+#
+# Old CD-ROM drivers (not SCSI, not IDE)
+#
+# CONFIG_CD_NO_IDESCSI is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+CONFIG_MD=y
+CONFIG_BLK_DEV_MD=y
+CONFIG_MD_LINEAR=m
+CONFIG_MD_RAID0=m
+CONFIG_MD_RAID1=m
+CONFIG_MD_RAID5=m
+CONFIG_MD_RAID6=m
+CONFIG_MD_RAID10=m
+CONFIG_MD_MULTIPATH=m
+CONFIG_BLK_DEV_DM=m
+CONFIG_DM_SNAPSHOT=m
+CONFIG_DM_MIRROR=m
+CONFIG_DM_ZERO=m
+CONFIG_DM_CRYPT=m
+
+#
+# Fusion MPT device support
+#
+CONFIG_FUSION=m
+CONFIG_FUSION_MAX_SGE=40
+CONFIG_FUSION_CTL=m
+CONFIG_FUSION_LAN=m
+
+#
+# IEEE 1394 (FireWire) support (EXPERIMENTAL)
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# Subsystem Options
+#
+# CONFIG_IEEE1394_VERBOSEDEBUG is not set
+CONFIG_IEEE1394_OUI_DB=y
+
+#
+# Device Drivers
+#
+# CONFIG_IEEE1394_PCILYNX is not set
+CONFIG_IEEE1394_OHCI1394=m
+
+#
+# Protocol Drivers
+#
+CONFIG_IEEE1394_VIDEO1394=m
+CONFIG_IEEE1394_SBP2=m
+# CONFIG_IEEE1394_SBP2_PHYS_DMA is not set
+# CONFIG_IEEE1394_ETH1394 is not set
+CONFIG_IEEE1394_DV1394=m
+CONFIG_IEEE1394_RAWIO=m
+CONFIG_IEEE1394_CMP=m
+CONFIG_IEEE1394_AMDTP=m
+# CONFIG_IEEE1394_EXTRA_CONFIG_ROMS is not set
+
+#
+# I2O device support
+#
+CONFIG_I2O=m
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+CONFIG_PACKET=y
+CONFIG_PACKET_MMAP=y
+CONFIG_NETLINK_DEV=y
+CONFIG_UNIX=y
+CONFIG_NET_KEY=m
+CONFIG_INET=y
+CONFIG_INET_TUNNEL=m
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_FWMARK=y
+CONFIG_IP_ROUTE_MULTIPATH=y
+CONFIG_IP_ROUTE_VERBOSE=y
+# CONFIG_IP_PNP is not set
+CONFIG_NET_IPIP=m
+CONFIG_NET_IPGRE=m
+CONFIG_NET_IPGRE_BROADCAST=y
+CONFIG_IP_MROUTE=y
+CONFIG_IP_PIMSM_V1=y
+CONFIG_IP_PIMSM_V2=y
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+CONFIG_INET_AH=m
+CONFIG_INET_ESP=m
+CONFIG_INET_IPCOMP=m
+CONFIG_NETCONSOLE=m
+# CONFIG_NETPOLL_RX is not set
+CONFIG_NETPOLL_TRAP=y
+CONFIG_NET_POLL_CONTROLLER=y
+CONFIG_NETDUMP=m
+CONFIG_DISKDUMP=m
+CONFIG_SCSI_DUMP=m
+CONFIG_SD_IOSTATS=y
+
+#
+# IP: Virtual Server Configuration
+#
+CONFIG_IP_VS=m
+# CONFIG_IP_VS_DEBUG is not set
+CONFIG_IP_VS_TAB_BITS=12
+CONFIG_IP_VS_PROTO_TCP=y
+CONFIG_IP_VS_PROTO_UDP=y
+CONFIG_IP_VS_PROTO_ESP=y
+CONFIG_IP_VS_PROTO_AH=y
+CONFIG_IP_VS_RR=m
+CONFIG_IP_VS_WRR=m
+CONFIG_IP_VS_LC=m
+CONFIG_IP_VS_WLC=m
+CONFIG_IP_VS_LBLC=m
+CONFIG_IP_VS_LBLCR=m
+CONFIG_IP_VS_DH=m
+CONFIG_IP_VS_SH=m
+CONFIG_IP_VS_SED=m
+CONFIG_IP_VS_NQ=m
+CONFIG_IP_VS_FTP=m
+
+
+CONFIG_IPV6=m
+CONFIG_IPV6_PRIVACY=y
+CONFIG_INET6_AH=m
+CONFIG_INET6_ESP=m
+CONFIG_INET6_IPCOMP=m
+CONFIG_IPV6_TUNNEL=m
+# CONFIG_DECNET is not set
+CONFIG_BRIDGE=m
+CONFIG_NETFILTER=y
+# CONFIG_NETFILTER_DEBUG is not set
+CONFIG_BRIDGE_NETFILTER=y
+
+#
+# IP: Netfilter Configuration
+#
+CONFIG_IP_NF_CONNTRACK=m
+CONFIG_IP_NF_FTP=m
+CONFIG_IP_NF_IRC=m
+CONFIG_IP_NF_TFTP=m
+CONFIG_IP_NF_AMANDA=m
+CONFIG_IP_NF_QUEUE=m
+CONFIG_IP_NF_RAW=m
+CONFIG_IP_NF_IPTABLES=m
+CONFIG_IP_NF_MATCH_COMMENT=m
+CONFIG_IP_NF_MATCH_LIMIT=m
+CONFIG_IP_NF_MATCH_IPRANGE=m
+CONFIG_IP_NF_MATCH_MAC=m
+CONFIG_IP_NF_MATCH_PKTTYPE=m
+CONFIG_IP_NF_MATCH_MARK=m
+CONFIG_IP_NF_MATCH_MULTIPORT=m
+CONFIG_IP_NF_MATCH_TOS=m
+CONFIG_IP_NF_MATCH_RECENT=m
+CONFIG_IP_NF_MATCH_ECN=m
+CONFIG_IP_NF_MATCH_DSCP=m
+CONFIG_IP_NF_MATCH_AH_ESP=m
+CONFIG_IP_NF_MATCH_LENGTH=m
+CONFIG_IP_NF_MATCH_TTL=m
+CONFIG_IP_NF_MATCH_TCPMSS=m
+CONFIG_IP_NF_MATCH_HELPER=m
+CONFIG_IP_NF_MATCH_STATE=m
+CONFIG_IP_NF_MATCH_CONNTRACK=m
+CONFIG_IP_NF_MATCH_OWNER=m
+CONFIG_IP_NF_MATCH_PHYSDEV=m
+CONFIG_IP_NF_MATCH_ADDRTYPE=m
+CONFIG_IP_NF_MATCH_REALM=m
+CONFIG_IP_NF_MATCH_SCTP=m
+CONFIG_IP_NF_FILTER=m
+CONFIG_IP_NF_TARGET_REJECT=m
+CONFIG_IP_NF_NAT=m
+CONFIG_IP_NF_NAT_NEEDED=y
+CONFIG_IP_NF_TARGET_MASQUERADE=m
+CONFIG_IP_NF_TARGET_REDIRECT=m
+CONFIG_IP_NF_TARGET_NETMAP=m
+CONFIG_IP_NF_TARGET_SAME=m
+CONFIG_IP_NF_TARGET_NOTRACK=m
+CONFIG_IP_NF_NAT_LOCAL=y
+CONFIG_IP_NF_NAT_SNMP_BASIC=m
+CONFIG_IP_NF_NAT_IRC=m
+CONFIG_IP_NF_NAT_FTP=m
+CONFIG_IP_NF_NAT_TFTP=m
+CONFIG_IP_NF_NAT_AMANDA=m
+CONFIG_IP_NF_MANGLE=m
+CONFIG_IP_NF_TARGET_TOS=m
+CONFIG_IP_NF_TARGET_ECN=m
+CONFIG_IP_NF_TARGET_DSCP=m
+CONFIG_IP_NF_TARGET_MARK=m
+CONFIG_IP_NF_TARGET_CLASSIFY=m
+CONFIG_IP_NF_TARGET_LOG=m
+CONFIG_IP_NF_TARGET_ULOG=m
+CONFIG_IP_NF_TARGET_TCPMSS=m
+CONFIG_IP_NF_ARPTABLES=m
+CONFIG_IP_NF_ARPFILTER=m
+CONFIG_IP_NF_ARP_MANGLE=m
+CONFIG_IP_NF_CT_ACCT=y
+CONFIG_IP_NF_CT_PROTO_SCTP=m
+# CONFIG_IP_NF_COMPAT_IPCHAINS is not set
+# CONFIG_IP_NF_COMPAT_IPFWADM is not set
+
+#
+# IPv6: Netfilter Configuration
+#
+# CONFIG_IP6_NF_QUEUE is not set
+CONFIG_IP6_NF_IPTABLES=m
+CONFIG_IP6_NF_MATCH_LIMIT=m
+CONFIG_IP6_NF_MATCH_MAC=m
+CONFIG_IP6_NF_MATCH_RT=m
+CONFIG_IP6_NF_MATCH_OPTS=m
+CONFIG_IP6_NF_MATCH_FRAG=m
+CONFIG_IP6_NF_MATCH_HL=m
+CONFIG_IP6_NF_MATCH_MULTIPORT=m
+CONFIG_IP6_NF_MATCH_OWNER=m
+CONFIG_IP6_NF_MATCH_MARK=m
+CONFIG_IP6_NF_MATCH_IPV6HEADER=m
+CONFIG_IP6_NF_MATCH_AHESP=m
+CONFIG_IP6_NF_MATCH_LENGTH=m
+CONFIG_IP6_NF_MATCH_EUI64=m
+CONFIG_IP6_NF_MATCH_PHYSDEV=m
+CONFIG_IP6_NF_FILTER=m
+CONFIG_IP6_NF_TARGET_LOG=m
+CONFIG_IP6_NF_MANGLE=m
+CONFIG_IP6_NF_TARGET_MARK=m
+CONFIG_IP6_NF_RAW=m
+
+
+#
+# Bridge: Netfilter Configuration
+#
+CONFIG_BRIDGE_NF_EBTABLES=m
+CONFIG_BRIDGE_EBT_BROUTE=m
+CONFIG_BRIDGE_EBT_T_FILTER=m
+CONFIG_BRIDGE_EBT_T_NAT=m
+CONFIG_BRIDGE_EBT_802_3=m
+CONFIG_BRIDGE_EBT_AMONG=m
+CONFIG_BRIDGE_EBT_ARP=m
+CONFIG_BRIDGE_EBT_IP=m
+CONFIG_BRIDGE_EBT_LIMIT=m
+CONFIG_BRIDGE_EBT_MARK=m
+CONFIG_BRIDGE_EBT_PKTTYPE=m
+CONFIG_BRIDGE_EBT_STP=m
+CONFIG_BRIDGE_EBT_VLAN=m
+CONFIG_BRIDGE_EBT_ARPREPLY=m
+CONFIG_BRIDGE_EBT_DNAT=m
+CONFIG_BRIDGE_EBT_MARK_T=m
+CONFIG_BRIDGE_EBT_REDIRECT=m
+CONFIG_BRIDGE_EBT_SNAT=m
+CONFIG_BRIDGE_EBT_LOG=m
+CONFIG_XFRM=y
+CONFIG_XFRM_USER=y
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+CONFIG_IP_SCTP=m
+# CONFIG_SCTP_DBG_MSG is not set
+# CONFIG_SCTP_DBG_OBJCNT is not set
+# CONFIG_SCTP_HMAC_NONE is not set
+# CONFIG_SCTP_HMAC_SHA1 is not set
+CONFIG_SCTP_HMAC_MD5=y
+CONFIG_ATM=m
+CONFIG_VLAN_8021Q=m
+CONFIG_LLC=m
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_IPX_INTERN is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+CONFIG_COPS_DAYNA=y
+CONFIG_COPS_TANGENT=y
+# CONFIG_IPDDP is not set
+CONFIG_IPDDP_ENCAP=y
+CONFIG_IPDDP_DECAP=y
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+CONFIG_NET_DIVERT=y
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_NET_HW_FLOWCONTROL is not set
+
+#
+# QoS and/or fair queueing
+#
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_CBQ=m
+CONFIG_NET_SCH_HTB=m
+CONFIG_NET_SCH_PRIO=m
+CONFIG_NET_SCH_RED=m
+CONFIG_NET_SCH_SFQ=m
+CONFIG_NET_SCH_TEQL=m
+CONFIG_NET_SCH_TBF=m
+CONFIG_NET_SCH_GRED=m
+CONFIG_NET_SCH_DSMARK=m
+CONFIG_NET_SCH_INGRESS=m
+CONFIG_NET_SCH_HFSC=m
+CONFIG_NET_SCH_NETEM=m
+CONFIG_NET_QOS=y
+CONFIG_NET_ESTIMATOR=y
+CONFIG_NET_CLS=y
+CONFIG_NET_CLS_TCINDEX=m
+CONFIG_NET_CLS_ROUTE4=m
+CONFIG_NET_CLS_ROUTE=y
+CONFIG_NET_CLS_FW=m
+CONFIG_NET_CLS_U32=m
+CONFIG_NET_CLS_RSVP=m
+CONFIG_NET_CLS_RSVP6=m
+CONFIG_NET_CLS_POLICE=y
+# CONFIG_NET_ACT_POLICE is not set
+CONFIG_CLS_U32_PERF=y
+CONFIG_NET_CLS_IND=y
+# CONFIG_NET_CLS_ACT is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+CONFIG_NETDEVICES=y
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+CONFIG_DUMMY=m
+CONFIG_BONDING=m
+# CONFIG_EQUALIZER is not set
+CONFIG_TUN=m
+CONFIG_ETHERTAP=m
+# CONFIG_NET_SB1000 is not set
+
+#
+# ATM
+# 
+CONFIG_ATM_CLIP=m
+CONFIG_ATM_LANE=m
+CONFIG_ATM_BR2684=m
+CONFIG_NET_SCH_ATM=m
+CONFIG_ATM_TCP=m
+CONFIG_ATM_LANAI=m
+CONFIG_ATM_ENI=m
+CONFIG_ATM_FIRESTREAM=m
+# CONFIG_ATM_ZATM is not set
+CONFIG_ATM_IDT77252=m
+CONFIG_ATM_AMBASSADOR=m
+CONFIG_ATM_HORIZON=m
+CONFIG_ATM_FORE200E_MAYBE=m
+CONFIG_ATM_HE=m
+CONFIG_PPPOATM=m
+CONFIG_ATM_NICSTAR=m
+# CONFIG_ATM_IA is not set
+
+
+# CONFIG_ATM_CLIP_NO_ICMP is not set
+# CONFIG_ATM_MPOA is not set
+# CONFIG_ATM_BR2684_IPFILTER is not set
+# CONFIG_ATM_ENI_DEBUG is not set
+# CONFIG_ATM_ENI_TUNE_BURST is not set
+# CONFIG_ATM_ZATM_DEBUG is not set
+# CONFIG_ATM_IDT77252_DEBUG is not set
+# CONFIG_ATM_IDT77252_RCV_ALL is not set
+# CONFIG_ATM_AMBASSADOR_DEBUG is not set
+# CONFIG_ATM_HORIZON_DEBUG is not set
+# CONFIG_ATM_FORE200E_PCA is not set
+# CONFIG_ATM_HE_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_IDT77105 is not set
+# CONFIG_ATM_IA_DEBUG is not set
+
+
+
+
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=m
+CONFIG_HAPPYMEAL=m
+CONFIG_SUNGEM=m
+CONFIG_NET_VENDOR_3COM=y
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+CONFIG_VORTEX=m
+CONFIG_TYPHOON=m
+# CONFIG_LANCE is not set
+CONFIG_NET_VENDOR_SMC=y
+# CONFIG_WD80x3 is not set
+# CONFIG_ULTRA is not set
+CONFIG_SMC9194=m
+CONFIG_NET_VENDOR_RACAL=y
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+
+#
+# Tulip family network device support
+#
+CONFIG_NET_TULIP=y
+CONFIG_DE2104X=m
+CONFIG_TULIP=m
+# CONFIG_TULIP_NAPI is not set
+
+# CONFIG_TULIP_MWI is not set
+CONFIG_TULIP_MMIO=y
+# CONFIG_NI5010 is not set
+# CONFIG_PCMCIA_XIRTULIP is not set
+CONFIG_DE4X5=m
+CONFIG_WINBOND_840=m
+CONFIG_DM9102=m
+CONFIG_PCMCIA_XIRCOM=m
+# CONFIG_AT1700 is not set
+# CONFIG_DEPCA is not set
+CONFIG_HP100=m
+# CONFIG_NET_ISA is not set
+CONFIG_EWRK3=m
+CONFIG_E2100=m
+CONFIG_EEXPRESS=m
+CONFIG_EEXPRESS_PRO=m
+CONFIG_HPLAN_PLUS=m
+CONFIG_HPLAN=m
+CONFIG_LP486E=m
+CONFIG_ETH16I=m
+CONFIG_NE2000=m
+CONFIG_ZNET=m
+CONFIG_SEEQ8005=m
+CONFIG_LNE390=m
+CONFIG_NE3210=m
+CONFIG_ES3210=m
+CONFIG_NET_PCI=y
+CONFIG_PCNET32=m
+CONFIG_AMD8111_ETH=m
+CONFIG_AMD8111E_NAPI=y
+CONFIG_ADAPTEC_STARFIRE=m
+CONFIG_ADAPTEC_STARFIRE_NAPI=y
+# CONFIG_AC3200 is not set
+CONFIG_APRICOT=m
+CONFIG_B44=m
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+CONFIG_EEPRO100=m
+# CONFIG_EEPRO100_PIO is not set
+CONFIG_E100=m
+CONFIG_E100_NAPI=y
+CONFIG_FEALNX=m
+CONFIG_FORCEDETH=m
+CONFIG_NATSEMI=m
+CONFIG_NE2K_PCI=m
+CONFIG_8139CP=m
+CONFIG_8139TOO=m
+CONFIG_8139TOO_PIO=y
+# CONFIG_8139TOO_TUNE_TWISTER is not set
+CONFIG_8139TOO_8129=y
+# CONFIG_8139_OLD_RX_RESET is not set
+CONFIG_SIS900=m
+CONFIG_EPIC100=m
+# CONFIG_SUNDANCE is not set
+# CONFIG_SUNDANCE_MMIO is not set
+CONFIG_TLAN=m
+CONFIG_VIA_RHINE=m
+CONFIG_VIA_RHINE_MMIO=y
+CONFIG_VIA_VELOCITY=m
+CONFIG_NET_POCKET=y
+# CONFIG_ATP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+CONFIG_ACENIC=m
+# CONFIG_ACENIC_OMIT_TIGON_I is not set
+CONFIG_DL2K=m
+CONFIG_E1000=m
+CONFIG_E1000_NAPI=y
+CONFIG_NS83820=m
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+CONFIG_R8169=m
+CONFIG_R8169_NAPI=y
+CONFIG_SK98LIN=m
+CONFIG_TIGON3=m
+
+#
+# Ethernet (10000 Mbit)
+#
+CONFIG_IXGB=m
+CONFIG_IXGB_NAPI=y
+CONFIG_S2IO=m
+CONFIG_S2IO_NAPI=y
+CONFIG_FDDI=y
+# CONFIG_DEFXX is not set
+# CONFIG_SKFP is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PLIP is not set
+CONFIG_PPP=m
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_ASYNC=m
+CONFIG_PPP_SYNC_TTY=m
+CONFIG_PPP_DEFLATE=m
+CONFIG_IPPP_FILTER=y
+# CONFIG_PPP_BSDCOMP is not set
+CONFIG_PPPOE=m
+# CONFIG_SLIP is not set
+
+#
+# Wireless LAN (non-hamradio)
+#
+CONFIG_NET_RADIO=y
+
+#
+# Obsolete Wireless cards support (pre-802.11)
+#
+# CONFIG_STRIP is not set
+# CONFIG_ARLAN is not set
+CONFIG_WAVELAN=m
+CONFIG_PCMCIA_WAVELAN=m
+CONFIG_PCMCIA_NETWAVE=m
+
+#
+# Wireless 802.11 Frequency Hopping cards support
+#
+# CONFIG_PCMCIA_RAYCS is not set
+
+#
+# Wireless 802.11b ISA/PCI cards support
+#
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
+CONFIG_AIRO=m
+CONFIG_HERMES=m
+CONFIG_PLX_HERMES=m
+CONFIG_TMD_HERMES=m
+CONFIG_PCI_HERMES=m
+CONFIG_ATMEL=m
+CONFIG_PCI_ATMEL=m
+CONFIG_PRISM54=m
+
+#
+# Wireless 802.11b Pcmcia/Cardbus cards support
+#
+CONFIG_PCMCIA_HERMES=m
+CONFIG_AIRO_CS=m
+CONFIG_PCMCIA_ATMEL=m
+CONFIG_PCMCIA_WL3501=m
+CONFIG_NET_WIRELESS=y
+
+#
+# Token Ring devices
+#
+CONFIG_TR=y
+CONFIG_IBMOL=m
+CONFIG_3C359=m
+CONFIG_TMS380TR=m
+CONFIG_TMSPCI=m
+CONFIG_ABYSS=m
+CONFIG_IBMTR=m
+CONFIG_IBMLS=m
+CONFIG_SKISA=m
+CONFIG_PROTEON=m
+CONFIG_SMCTR=m
+CONFIG_PCMCIA_IBMTR=m
+
+
+CONFIG_NET_FC=y
+# CONFIG_SHAPER is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+
+#
+# PCMCIA network device support
+#
+CONFIG_NET_PCMCIA=y
+CONFIG_PCMCIA_3C589=m
+CONFIG_PCMCIA_3C574=m
+CONFIG_PCMCIA_FMVJ18X=m
+CONFIG_PCMCIA_PCNET=m
+CONFIG_PCMCIA_NMCLAN=m
+CONFIG_PCMCIA_SMC91C92=m
+CONFIG_PCMCIA_XIRC2PS=m
+CONFIG_PCMCIA_AXNET=m
+
+#
+# Amateur Radio support
+#
+# CONFIG_HAMRADIO is not set
+
+#
+# IrDA (infrared) support
+#
+# CONFIG_IRDA is not set
+# CONFIG_IRDA is not set
+# CONFIG_IRDA_DEBUG is not set
+CONFIG_IRLAN=m
+CONFIG_IRNET=m
+CONFIG_IRCOMM=m
+# CONFIG_IRDA_ULTRA is not set
+CONFIG_IRDA_CACHE_LAST_LSAP=y
+CONFIG_IRDA_FAST_RR=y
+CONFIG_IRTTY_SIR=m
+CONFIG_DONGLE=y
+CONFIG_ESI_DONGLE=m
+CONFIG_ACTISYS_DONGLE=m
+CONFIG_TEKRAM_DONGLE=m
+CONFIG_IRPORT_SIR=m
+# CONFIG_DONGLE_OLD is not set
+CONFIG_LITELINK_DONGLE=m
+CONFIG_MA600_DONGLE=m
+CONFIG_GIRBIL_DONGLE=m
+CONFIG_MCP2120_DONGLE=m
+CONFIG_OLD_BELKIN_DONGLE=m
+CONFIG_ACT200L_DONGLE=m
+
+CONFIG_USB_IRDA=m
+CONFIG_NSC_FIR=m
+CONFIG_SIGMATEL_FIR=m
+# CONFIG_WINBOND_FIR is not set
+# CONFIG_TOSHIBA_FIR is not set
+# CONFIG_SMC_IRCC_FIR is not set
+# CONFIG_ALI_FIR is not set
+# CONFIG_VLSI_FIR is not set
+# CONFIG_VIA_FIR is not set
+
+
+
+#
+# Bluetooth support
+#
+CONFIG_BT=m
+CONFIG_BT_L2CAP=m
+CONFIG_BT_SCO=m
+CONFIG_BT_CMTP=m
+CONFIG_BT_RFCOMM=m
+CONFIG_BT_RFCOMM_TTY=y
+CONFIG_BT_BNEP=m
+CONFIG_BT_BNEP_MC_FILTER=y
+CONFIG_BT_BNEP_PROTO_FILTER=y
+CONFIG_BT_HIDP=m
+
+#
+# Bluetooth device drivers
+#
+CONFIG_BT_HCIUSB=m
+CONFIG_BT_HCIUART=m
+CONFIG_BT_HCIUART_H4=y
+CONFIG_BT_HCIUART_BCSP=y
+CONFIG_BT_HCIUART_BCSP_TXCRC=y
+CONFIG_BT_HCIDTL1=m
+CONFIG_BT_HCIBT3C=m
+CONFIG_BT_HCIBLUECARD=m
+CONFIG_BT_HCIBTUART=m
+CONFIG_BT_HCIVHCI=m
+CONFIG_BT_HCIUSB_SCO=y
+CONFIG_BT_HCIBCM203X=m
+CONFIG_BT_HCIBFUSB=m
+CONFIG_USB_BLUETOOTH_TTY=m
+
+#
+# ISDN subsystem
+#
+
+CONFIG_ISDN=m
+CONFIG_ISDN_I4L=m
+CONFIG_ISDN_DRV_AVMB1_B1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCI=m
+CONFIG_ISDN_DRV_AVMB1_T1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCMCIA=m
+CONFIG_ISDN_DRV_AVMB1_T1PCI=m
+CONFIG_ISDN_DRV_AVMB1_C4=m
+
+CONFIG_ISDN_PPP=y
+CONFIG_ISDN_PPP_VJ=y
+CONFIG_ISDN_MPP=y
+# CONFIG_ISDN_PPP_BSDCOMP is not set
+CONFIG_ISDN_TTY_FAX=y
+CONFIG_DE_AOC=y
+
+CONFIG_ISDN_AUDIO=y
+
+CONFIG_ISDN_DRV_HISAX=m
+CONFIG_ISDN_DRV_ICN=m
+CONFIG_ISDN_DRV_PCBIT=m
+CONFIG_ISDN_DRV_SC=m
+CONFIG_ISDN_DRV_ACT2000=m
+CONFIG_ISDN_DRV_TPAM=m
+CONFIG_ISDN_DRV_AVMB1_B1PCIV4=y
+CONFIG_ISDN_DRV_AVMB1_AVM_CS=m
+
+CONFIG_ISDN_CAPI_CAPIDRV=m
+
+CONFIG_HISAX_EURO=y
+CONFIG_HISAX_1TR6=y
+CONFIG_HISAX_NI1=y
+CONFIG_HISAX_MAX_CARDS=8
+CONFIG_HISAX_16_0=y
+CONFIG_HISAX_16_3=y
+CONFIG_HISAX_TELESPCI=y
+CONFIG_HISAX_S0BOX=y
+CONFIG_HISAX_AVM_A1=y
+CONFIG_HISAX_FRITZPCI=y
+CONFIG_HISAX_AVM_A1_PCMCIA=y
+CONFIG_HISAX_ELSA=y
+CONFIG_HISAX_IX1MICROR2=y
+CONFIG_HISAX_DIEHLDIVA=y
+CONFIG_HISAX_ASUSCOM=y
+CONFIG_HISAX_TELEINT=y
+CONFIG_HISAX_HFCS=y
+CONFIG_HISAX_SEDLBAUER=y
+CONFIG_HISAX_SPORTSTER=y
+CONFIG_HISAX_MIC=y
+CONFIG_HISAX_NETJET=y
+CONFIG_HISAX_NETJET_U=y
+CONFIG_HISAX_NICCY=y
+CONFIG_HISAX_ISURF=y
+CONFIG_HISAX_HSTSAPHIR=y
+CONFIG_HISAX_BKM_A4T=y
+CONFIG_HISAX_SCT_QUADRO=y
+CONFIG_HISAX_GAZEL=y
+CONFIG_HISAX_HFC_PCI=y
+CONFIG_HISAX_W6692=y
+CONFIG_HISAX_HFC_SX=y
+CONFIG_HISAX_ENTERNOW_PCI=y
+# CONFIG_HISAX_DEBUG is not set
+CONFIG_HISAX_AVM_A1_CS=m
+CONFIG_HISAX_ST5481=m
+CONFIG_HISAX_HFCUSB=m
+CONFIG_HISAX_FRITZ_PCIPNP=m
+CONFIG_HISAX_NO_SENDCOMPLETE=y
+CONFIG_HISAX_NO_LLC=y
+CONFIG_HISAX_NO_KEYPAD=y
+CONFIG_HISAX_SEDLBAUER_CS=m
+CONFIG_HISAX_ELSA_CS=m
+CONFIG_HISAX_TELES_CS=m
+
+CONFIG_ISDN_DRV_LOOP=m
+CONFIG_HYSDN=m
+CONFIG_HYSDN_CAPI=y
+
+
+#
+# CAPI subsystem
+#
+CONFIG_ISDN_CAPI=m
+CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON=y
+CONFIG_ISDN_CAPI_MIDDLEWARE=y
+CONFIG_ISDN_CAPI_CAPI20=m
+CONFIG_ISDN_CAPI_CAPIFS_BOOL=y
+CONFIG_ISDN_CAPI_CAPIFS=m
+
+#
+# CAPI hardware drivers
+#
+
+#
+# Active AVM cards
+#
+CONFIG_CAPI_AVM=y
+
+#
+# Active Eicon DIVA Server cards
+#
+CONFIG_CAPI_EICON=y
+CONFIG_ISDN_DIVAS=m
+CONFIG_ISDN_DIVAS_BRIPCI=y
+CONFIG_ISDN_DIVAS_PRIPCI=y
+CONFIG_ISDN_DIVAS_DIVACAPI=m
+CONFIG_ISDN_DIVAS_USERIDI=m
+CONFIG_ISDN_DIVAS_MAINT=m
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+CONFIG_INPUT_JOYDEV=m
+# CONFIG_INPUT_TSDEV is not set
+CONFIG_INPUT_EVDEV=y
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input I/O drivers
+#
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=m
+CONFIG_GAMEPORT_NS558=m
+CONFIG_GAMEPORT_L4=m
+CONFIG_GAMEPORT_EMU10K1=m
+CONFIG_GAMEPORT_VORTEX=m
+CONFIG_GAMEPORT_FM801=m
+CONFIG_GAMEPORT_CS461x=m
+CONFIG_SERIO=y
+CONFIG_SERIO_I8042=y
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_RAW is not set
+
+# CONFIG_SERIO_CT82C710 is not set
+# CONFIG_SERIO_PARKBD is not set
+# CONFIG_SERIO_PCIPS2 is not set
+
+#
+# Input Device Drivers
+#
+CONFIG_INPUT_KEYBOARD=y
+CONFIG_KEYBOARD_ATKBD=y
+# CONFIG_KEYBOARD_SUNKBD is not set
+# CONFIG_KEYBOARD_XTKBD is not set
+# CONFIG_KEYBOARD_NEWTON is not set
+# CONFIG_KEYBOARD_LKKBD is not set
+CONFIG_INPUT_MOUSE=y
+CONFIG_MOUSE_PS2=y
+CONFIG_MOUSE_SERIAL=m
+CONFIG_MOUSE_INPORT=m
+CONFIG_MOUSE_ATIXL=y
+CONFIG_MOUSE_LOGIBM=m
+CONFIG_MOUSE_PC110PAD=m
+CONFIG_MOUSE_VSXXXAA=m
+CONFIG_INPUT_JOYSTICK=y
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+CONFIG_JOYSTICK_JOYDUMP=m
+CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_GUNZE=m
+CONFIG_INPUT_MISC=y
+CONFIG_INPUT_PCSPKR=m
+CONFIG_INPUT_UINPUT=m 
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+CONFIG_SERIAL_NONSTANDARD=y
+# CONFIG_ROCKETPORT is not set
+CONFIG_SYNCLINK=m
+CONFIG_SYNCLINKMP=m
+CONFIG_N_HDLC=m
+CONFIG_STALDRV=y
+# CONFIG_FTAPE is not set
+CONFIG_IBM_ASM=m
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_CS=m
+# CONFIG_SERIAL_8250_ACPI is not set
+CONFIG_SERIAL_8250_NR_UARTS=4
+CONFIG_SERIAL_8250_EXTENDED=y
+# CONFIG_SERIAL_8250_MANY_PORTS is not set
+CONFIG_SERIAL_8250_SHARE_IRQ=y
+CONFIG_SERIAL_8250_DETECT_IRQ=y
+CONFIG_SERIAL_8250_MULTIPORT=y
+CONFIG_SERIAL_8250_RSA=y
+# CONFIG_COMPUTONE is not set
+# CONFIG_CYCLADES is not set
+# CONFIG_DIGIEPCA is not set
+# CONFIG_DIGI is not set
+# CONFIG_ESPSERIAL is not set
+# CONFIG_MOXA_INTELLIO is not set
+# CONFIG_MOXA_SMARTIO is not set
+# CONFIG_ISI is not set
+# CONFIG_RISCOM8 is not set
+# CONFIG_SPECIALIX is not set
+# CONFIG_SX is not set
+# CONFIG_RIO is not set
+# CONFIG_STALLION is not set
+# CONFIG_ISTALLION is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+# CONFIG_LEGACY_PTYS is not set
+CONFIG_PRINTER=m
+CONFIG_LP_CONSOLE=y
+CONFIG_PPDEV=m
+# CONFIG_TIPAR is not set
+
+#
+# I2C support
+#
+CONFIG_I2C=m
+CONFIG_I2C_CHARDEV=m
+
+#
+# I2C Algorithms
+#
+# CONFIG_I2C_DEBUG_ALGO is not set
+CONFIG_I2C_ALGOBIT=m
+CONFIG_I2C_ALGOPCF=m
+
+#
+# I2C Hardware Bus support
+#
+CONFIG_I2C_ALI1535=m
+CONFIG_I2C_ALI15X3=m
+CONFIG_I2C_AMD756=m
+CONFIG_I2C_AMD8111=m
+CONFIG_I2C_I801=m
+CONFIG_I2C_I810=m
+CONFIG_I2C_ISA=m
+CONFIG_I2C_NFORCE2=m
+CONFIG_I2C_PIIX4=m
+CONFIG_I2C_PROSAVAGE=m
+CONFIG_I2C_SAVAGE4=m
+# CONFIG_SCx200_ACB is not set
+CONFIG_I2C_SIS5595=m
+CONFIG_I2C_SIS630=m
+CONFIG_I2C_SIS96X=m
+CONFIG_I2C_VIA=m
+CONFIG_I2C_VIAPRO=m
+CONFIG_I2C_VOODOO3=m
+# CONFIG_I2C_ELEKTOR is not set
+CONFIG_I2C_PARPORT=m
+CONFIG_I2C_PARPORT_LIGHT=m
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+# CONFIG_I2C_PARPORT is not set
+CONFIG_I2C_ALI1563=m
+# CONFIG_I2C_PARPORT_LIGHT is not set
+CONFIG_I2C_ALGOPCA=m
+# CONFIG_I2C_PCA_ISA is not set
+
+
+#
+# I2C Hardware Sensors Chip support
+#
+CONFIG_I2C_SENSOR=m
+CONFIG_SENSORS_ADM1021=m
+CONFIG_SENSORS_EEPROM=m
+CONFIG_SENSORS_IT87=m
+CONFIG_SENSORS_LM75=m
+CONFIG_SENSORS_LM78=m
+CONFIG_SENSORS_LM80=m
+CONFIG_SENSORS_LM83=m
+CONFIG_SENSORS_LM85=m
+CONFIG_SENSORS_VIA686A=m
+CONFIG_SENSORS_W83781D=m
+CONFIG_SENSORS_ASB100=m
+CONFIG_SENSORS_LM90=m
+CONFIG_SENSORS_W83L785TS=m
+CONFIG_SENSORS_FSCHER=m
+CONFIG_SENSORS_GL518SM=m
+CONFIG_SENSORS_DS1621=m
+CONFIG_SENSORS_W83627HF=m
+CONFIG_SENSORS_PCF8574=m
+CONFIG_SENSORS_PCF8591=m
+CONFIG_SENSORS_RTC8564=m
+CONFIG_SENSORS_MAX1619=m
+CONFIG_SENSORS_ADM1025=m
+CONFIG_SENSORS_ADM1031=m
+CONFIG_SENSORS_LM77=m
+CONFIG_SENSORS_SMSC47M1=m
+
+# CONFIG_W1 is not set
+
+#
+# Mice
+#
+CONFIG_CRASH=m
+
+#
+# IPMI
+#
+CONFIG_IPMI_HANDLER=m
+# CONFIG_IPMI_PANIC_EVENT is not set
+CONFIG_IPMI_DEVICE_INTERFACE=m
+CONFIG_IPMI_WATCHDOG=m
+CONFIG_IPMI_SI=m
+CONFIG_IPMI_POWEROFF=m
+
+#
+# Watchdog Cards
+#
+CONFIG_WATCHDOG=y
+# CONFIG_WATCHDOG_NOWAYOUT is not set
+CONFIG_SOFT_WATCHDOG=m
+CONFIG_WDT=m
+# CONFIG_WDT_501 is not set
+CONFIG_WDTPCI=m
+CONFIG_WDT_501_PCI=y
+CONFIG_PCWATCHDOG=m
+CONFIG_ACQUIRE_WDT=m
+CONFIG_ADVANTECH_WDT=m
+CONFIG_EUROTECH_WDT=m
+CONFIG_IB700_WDT=m
+CONFIG_I8XX_TCO=m
+# CONFIG_MIXCOMWD is not set
+# CONFIG_SCx200_WDT is not set
+# CONFIG_60XX_WDT is not set
+CONFIG_W83877F_WDT=m
+CONFIG_W83627HF_WDT=m
+CONFIG_MACHZ_WDT=m
+CONFIG_SC520_WDT=m
+CONFIG_ALIM7101_WDT=m
+CONFIG_ALIM1535_WDT=m
+CONFIG_SC1200_WDT=m
+CONFIG_WAFER_WDT=m
+CONFIG_CPU5_WDT=m
+CONFIG_PCIPCWATCHDOG=m
+CONFIG_USBPCWATCHDOG=m
+
+
+CONFIG_HW_RANDOM=m
+CONFIG_NVRAM=m
+CONFIG_RTC=y
+CONFIG_DTLK=m
+# CONFIG_R3964 is not set
+# CONFIG_APPLICOM is not set
+CONFIG_SONYPI=m
+
+#
+# Ftape, the floppy tape device driver
+#
+CONFIG_AGP=y
+CONFIG_AGP_ALI=y
+CONFIG_AGP_ATI=y
+CONFIG_AGP_AMD=y
+CONFIG_AGP_AMD64=y
+CONFIG_AGP_INTEL=y
+CONFIG_AGP_INTEL_MCH=y
+CONFIG_AGP_NVIDIA=y
+CONFIG_AGP_SIS=y
+CONFIG_AGP_SWORKS=y
+CONFIG_AGP_VIA=y
+CONFIG_AGP_EFFICEON=y
+CONFIG_DRM=y
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+CONFIG_DRM_R128=m
+CONFIG_DRM_RADEON=m
+CONFIG_DRM_I810=m
+CONFIG_DRM_I830=m
+CONFIG_DRM_MGA=m
+# CONFIG_DRM_SIS is not set
+CONFIG_DRM_I915=m
+
+
+
+#
+# PCMCIA character devices
+#
+CONFIG_SYNCLINK_CS=m
+
+
+
+# CONFIG_MWAVE is not set
+CONFIG_RAW_DRIVER=y
+CONFIG_MAX_RAW_DEVS=8192
+CONFIG_HANGCHECK_TIMER=m
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Video For Linux
+#
+
+#
+# Video Adapters
+#
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+CONFIG_VIDEO_OVCAMCHIP=m
+
+
+#
+# Radio Adapters
+#
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+CONFIG_DVB_CORE=m
+
+#
+# Supported Frontend Modules
+#
+CONFIG_DVB_STV0299=m
+# CONFIG_DVB_SP887X is not set
+# CONFIG_DVB_ALPS_TDLB7 is not set
+CONFIG_DVB_ALPS_TDMB7=m
+CONFIG_DVB_ATMEL_AT76C651=m
+CONFIG_DVB_CX24110=m
+CONFIG_DVB_GRUNDIG_29504_491=m
+CONFIG_DVB_GRUNDIG_29504_401=m
+CONFIG_DVB_MT312=m
+CONFIG_DVB_VES1820=m
+CONFIG_DVB_VES1X93=m
+CONFIG_DVB_TWINHAN_DST=m
+CONFIG_DVB_TTUSB_DEC=m
+CONFIG_DVB_BT8XX=m
+# CONFIG_DVB_TDA1004X is not set
+CONFIG_DVB_NXT6000=m
+
+#
+# Supported SAA7146 based PCI Adapters
+#
+CONFIG_DVB_AV7110=m
+CONFIG_DVB_AV7110_OSD=y
+# CONFIG_DVB_AV7110_FIRMWARE is not set
+CONFIG_DVB_BUDGET=m
+CONFIG_DVB_BUDGET_CI=m
+CONFIG_DVB_BUDGET_AV=m
+CONFIG_DVB_BUDGET_PATCH=m
+
+#
+# Supported USB Adapters
+#
+CONFIG_DVB_TTUSB_BUDGET=m
+
+#
+# Supported FlexCopII (B2C2) Adapters
+#
+CONFIG_DVB_B2C2_SKYSTAR=m
+CONFIG_VIDEO_SAA7146=m
+CONFIG_VIDEO_SAA7146_VV=m
+CONFIG_VIDEO_VIDEOBUF=m
+CONFIG_VIDEO_TUNER=m
+CONFIG_VIDEO_BUF=m
+CONFIG_VIDEO_BTCX=m
+
+#
+# Graphics support
+#
+CONFIG_FB=y
+# CONFIG_FB_CYBER2000 is not set
+# CONFIG_FB_IMSTT is not set
+CONFIG_FB_VGA16=m
+CONFIG_FB_VESA=y
+CONFIG_VIDEO_SELECT=y
+# CONFIG_FB_HGA is not set
+CONFIG_FB_RIVA=m
+# CONFIG_FB_RIVA_DEBUG is not set
+# CONFIG_FB_RIVA_I2C is not set
+CONFIG_FB_I810=m
+CONFIG_FB_I810_GTF=y
+# CONFIG_FB_MATROX is not set
+CONFIG_FB_MATROX_MILLENIUM=y
+CONFIG_FB_MATROX_MYSTIQUE=y
+CONFIG_FB_MATROX_G450=y
+CONFIG_FB_MATROX_G100=y
+CONFIG_FB_MATROX_I2C=m
+CONFIG_FB_MATROX_MAVEN=m
+CONFIG_FB_MATROX_MULTIHEAD=y
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_RADEON_DEBUG is not set
+# CONFIG_FB_RADEON_OLD is not set
+CONFIG_FB_RADEON_I2C=y
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_ATY is not set
+CONFIG_FB_ATY_CT=y
+CONFIG_FB_ATY_GX=y
+# CONFIG_FB_ATY_XL_INIT is not set
+# CONFIG_FB_SIS is not set
+CONFIG_FB_SIS_300=y
+CONFIG_FB_SIS_315=y
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VIRTUAL is not set
+CONFIG_FB_KYRO=m
+# CONFIG_FB_PM2 is not set
+# CONFIG_FB_PM2_FIFO_DISCONNECT is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+CONFIG_FB_CIRRUS=m
+
+#
+# Console display driver support
+#
+CONFIG_VGA_CONSOLE=y
+CONFIG_MDA_CONSOLE=m
+CONFIG_DUMMY_CONSOLE=y
+CONFIG_FRAMEBUFFER_CONSOLE=y
+# CONFIG_FONTS is not set
+
+
+#
+# Logo configuration
+#
+CONFIG_LOGO=y
+# CONFIG_LOGO_LINUX_MONO is not set
+# CONFIG_LOGO_LINUX_VGA16 is not set
+CONFIG_LOGO_LINUX_CLUT224=y
+
+#
+# Sound
+#
+CONFIG_SOUND=m
+
+#
+# Advanced Linux Sound Architecture
+#
+CONFIG_SND=m
+CONFIG_SND_SEQUENCER=m
+CONFIG_SND_SEQ_DUMMY=m
+CONFIG_SND_OSSEMUL=y
+CONFIG_SND_MIXER_OSS=m
+CONFIG_SND_PCM_OSS=m
+CONFIG_SND_SEQUENCER_OSS=y
+CONFIG_SND_RTCTIMER=m
+# CONFIG_SND_VERBOSE_PRINTK is not set
+# CONFIG_SND_DEBUG is not set
+CONFIG_SND_BIT32_EMUL=y
+
+#
+# Generic devices
+#
+CONFIG_SND_DUMMY=m
+CONFIG_SND_VIRMIDI=m
+CONFIG_SND_MTPAV=m
+# CONFIG_SND_SERIAL_U16550 is not set
+CONFIG_SND_MPU401=m
+
+#
+# ISA devices
+#
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+
+#
+# PCI devices
+#
+CONFIG_SND_ALI5451=m
+CONFIG_SND_AZT3328=m
+CONFIG_SND_CS46XX=m
+CONFIG_SND_CS46XX_NEW_DSP=y
+CONFIG_SND_CS4281=m
+CONFIG_SND_EMU10K1=m
+CONFIG_SND_KORG1212=m
+CONFIG_SND_NM256=m
+CONFIG_SND_RME32=m
+CONFIG_SND_RME96=m
+CONFIG_SND_RME9652=m
+CONFIG_SND_HDSP=m
+CONFIG_SND_TRIDENT=m
+CONFIG_SND_YMFPCI=m
+CONFIG_SND_ALS4000=m
+CONFIG_SND_CMIPCI=m
+CONFIG_SND_ENS1370=m
+CONFIG_SND_ENS1371=m
+CONFIG_SND_ES1938=m
+CONFIG_SND_ES1968=m
+CONFIG_SND_MAESTRO3=m
+CONFIG_SND_FM801=m
+CONFIG_SND_ICE1712=m
+CONFIG_SND_ICE1724=m
+CONFIG_SND_INTEL8X0=m
+CONFIG_SND_SONICVIBES=m
+CONFIG_SND_VIA82XX=m
+CONFIG_SND_VX222=m
+CONFIG_SND_BT87X=m
+CONFIG_SND_ATIIXP=m
+CONFIG_SND_ATIIXP_MODEM=m
+CONFIG_SND_AU8810=m
+CONFIG_SND_AU8820=m
+CONFIG_SND_AU8830=m
+CONFIG_SND_MIXART=m
+CONFIG_SND_FM801_TEA575X=m
+CONFIG_SND_INTEL8X0M=m
+CONFIG_SND_PDAUDIOCF=m
+
+
+#
+# ALSA USB devices
+#
+CONFIG_SND_USB_AUDIO=m
+CONFIG_SND_USB_USX2Y=m
+
+#
+# PCMCIA devices
+#
+# CONFIG_SND_VXPOCKET is not set
+# CONFIG_SND_VXP440 is not set
+
+#
+# Open Sound System
+#
+# CONFIG_SOUND_PRIME is not set
+# CONFIG_SOUND_BT878 is not set
+# CONFIG_SOUND_CMPCI is not set
+
+#
+# USB support
+#
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+CONFIG_USB_DEVICEFS=y
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+CONFIG_USB_SUSPEND=y
+
+#
+# USB Host Controller Drivers
+#
+CONFIG_USB_EHCI_HCD=m
+CONFIG_USB_EHCI_SPLIT_ISO=y
+CONFIG_USB_EHCI_ROOT_HUB_TT=y
+CONFIG_USB_OHCI_HCD=m
+CONFIG_USB_UHCI_HCD=m
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_AUDIO is not set
+
+#
+# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem
+#
+CONFIG_USB_MIDI=m
+CONFIG_USB_ACM=m
+CONFIG_USB_PRINTER=m
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_USB_STORAGE=m
+# CONFIG_USB_STORAGE_DEBUG is not set
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_DPCM=y
+CONFIG_USB_STORAGE_HP8200e=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_RW_DETECT=y
+
+#
+# USB Human Interface Devices (HID)
+#
+CONFIG_USB_HID=y
+CONFIG_USB_HIDINPUT=y
+CONFIG_HID_FF=y
+CONFIG_HID_PID=y
+CONFIG_LOGITECH_FF=y
+CONFIG_THRUSTMASTER_FF=y
+CONFIG_USB_HIDDEV=y
+
+#
+# USB HID Boot Protocol drivers
+#
+# CONFIG_USB_KBD is not set
+# CONFIG_USB_MOUSE is not set
+CONFIG_USB_AIPTEK=m
+CONFIG_USB_WACOM=m
+CONFIG_USB_KBTAB=m
+CONFIG_USB_POWERMATE=m
+CONFIG_USB_XPAD=m
+
+#
+# USB Imaging devices
+#
+CONFIG_USB_MDC800=m
+CONFIG_USB_MICROTEK=m
+CONFIG_USB_HPUSBSCSI=m
+
+#
+# USB Multimedia devices
+#
+CONFIG_USB_DABUSB=m
+CONFIG_USB_VICAM=m
+CONFIG_USB_DSBR=m
+CONFIG_USB_IBMCAM=m
+CONFIG_USB_KONICAWC=m
+CONFIG_USB_OV511=m
+CONFIG_USB_SE401=m
+CONFIG_USB_STV680=m
+CONFIG_USB_SN9C102=m
+
+#
+# USB Network adaptors
+#
+CONFIG_USB_CATC=m
+CONFIG_USB_KAWETH=m
+CONFIG_USB_PEGASUS=m
+CONFIG_USB_RTL8150=m
+CONFIG_USB_USBNET=m
+CONFIG_USB_SPEEDTOUCH=m
+
+#
+# USB Host-to-Host Cables
+#
+CONFIG_USB_AN2720=y
+CONFIG_USB_BELKIN=y
+CONFIG_USB_GENESYS=y
+CONFIG_USB_NET1080=y
+CONFIG_USB_PL2301=y
+
+#
+# Intelligent USB Devices/Gadgets
+#
+CONFIG_USB_ARMLINUX=y
+CONFIG_USB_EPSON2888=y
+CONFIG_USB_ZAURUS=y
+CONFIG_USB_CDCETHER=y
+
+#
+# USB Network Adapters
+#
+CONFIG_USB_AX8817X=y
+
+#
+# USB port drivers
+#
+CONFIG_USB_USS720=m
+
+#
+# USB Serial Converter support
+#
+CONFIG_USB_SERIAL=m
+CONFIG_USB_SERIAL_GENERIC=y
+CONFIG_USB_SERIAL_BELKIN=m
+CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m
+CONFIG_USB_SERIAL_EMPEG=m
+CONFIG_USB_SERIAL_FTDI_SIO=m
+CONFIG_USB_SERIAL_VISOR=m
+CONFIG_USB_SERIAL_IPAQ=m
+CONFIG_USB_SERIAL_IR=m
+CONFIG_USB_SERIAL_EDGEPORT=m
+CONFIG_USB_SERIAL_EDGEPORT_TI=m
+CONFIG_USB_SERIAL_KEYSPAN_PDA=m
+CONFIG_USB_SERIAL_KEYSPAN=m
+CONFIG_USB_SERIAL_KEYSPAN_MPR=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XA=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XB=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19=y
+CONFIG_USB_SERIAL_KEYSPAN_USA18X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QW=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QI=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y
+CONFIG_USB_SERIAL_KLSI=m
+CONFIG_USB_SERIAL_KOBIL_SCT=m
+CONFIG_USB_SERIAL_MCT_U232=m
+CONFIG_USB_SERIAL_PL2303=m
+CONFIG_USB_SERIAL_SAFE=m
+CONFIG_USB_SERIAL_SAFE_PADDED=y
+CONFIG_USB_SERIAL_CYBERJACK=m
+CONFIG_USB_SERIAL_XIRCOM=m
+CONFIG_USB_SERIAL_OMNINET=m
+CONFIG_USB_SERIAL_WHITEHEAT=m
+CONFIG_USB_EZUSB=y
+CONFIG_USB_EMI62=m
+CONFIG_USB_LED=m
+CONFIG_USB_G_SERIAL=m
+
+
+#
+# USB Miscellaneous drivers
+#
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_TIGL is not set
+CONFIG_USB_AUERSWALD=m
+CONFIG_USB_RIO500=m
+CONFIG_USB_LCD=m
+CONFIG_USB_TEST=m
+# CONFIG_USB_GADGET is not set
+# CONFIG_USB_GADGET_PXA2XX is not set
+# CONFIG_USB_GADGET_GOKU is not set
+# CONFIG_USB_GADGET_SA1100 is not set
+CONFIG_USB_ZERO=m
+CONFIG_USB_ETH=m
+CONFIG_USB_GADGETFS=m
+CONFIG_USB_W9968CF=m
+CONFIG_USB_PWC=m
+CONFIG_USB_LEGOTOWER=m
+CONFIG_USB_FILE_STORAGE=m
+# CONFIG_USB_FILE_STORAGE_TEST is not set
+CONFIG_USB_MTOUCH=m
+CONFIG_USB_ATI_REMOTE=m
+CONFIG_USB_ALI_M5632=y
+# CONFIG_USB_CYTHERM is not set
+CONFIG_USB_EGALAX=m
+CONFIG_USB_PHIDGETSERVO=m
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT2_FS_POSIX_ACL=y
+CONFIG_EXT2_FS_SECURITY=y
+CONFIG_EXT3_FS=m
+CONFIG_EXT3_FS_XATTR=y
+CONFIG_EXT3_FS_POSIX_ACL=y
+CONFIG_EXT3_FS_SECURITY=y
+CONFIG_JBD=m
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_REISERFS_CHECK is not set
+CONFIG_REISERFS_PROC_INFO=y
+CONFIG_REISERFS_FS_XATTR=y
+CONFIG_REISERFS_FS_POSIX_ACL=y
+CONFIG_REISERFS_FS_SECURITY=y
+# CONFIG_JFS_FS is not set
+# CONFIG_JFS_DEBUG is not set
+# CONFIG_JFS_STATISTICS is not set
+CONFIG_JFS_POSIX_ACL=y
+# CONFIG_XFS_FS is not set
+# CONFIG_XFS_RT is not set
+CONFIG_XFS_QUOTA=y
+CONFIG_XFS_POSIX_ACL=y
+CONFIG_XFS_SECURITY=y
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_QUOTA=y
+# CONFIG_QFMT_V1 is not set
+CONFIG_QFMT_V2=y
+CONFIG_QUOTACTL=y
+# CONFIG_AUTOFS_FS is not set
+CONFIG_AUTOFS4_FS=m
+
+#
+# CD-ROM/DVD Filesystems
+#
+CONFIG_ISO9660_FS=y
+CONFIG_JOLIET=y
+CONFIG_ZISOFS=y
+CONFIG_ZISOFS_FS=y
+CONFIG_UDF_FS=m
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=m
+CONFIG_MSDOS_FS=m
+CONFIG_VFAT_FS=m
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="ascii"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+# CONFIG_DEVFS_FS is not set
+CONFIG_DEVPTS_FS_XATTR=y
+CONFIG_DEVPTS_FS_SECURITY=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_XATTR=y
+CONFIG_TMPFS_SECURITY=y
+CONFIG_HUGETLBFS=y
+CONFIG_HUGETLB_PAGE=y
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not seta
+# CONFIG_AFFS_FS is not set
+# uses sleepon and needs a major update
+CONFIG_HFS_FS=m
+CONFIG_HFSPLUS_FS=m
+# CONFIG_BEFS_FS is not set
+# CONFIG_BEFS_DEBUG is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_JFFS_FS is not set
+CONFIG_JFFS2_FS=m
+CONFIG_JFFS2_FS_DEBUG=0
+CONFIG_JFFS2_FS_NAND=y
+CONFIG_CRAMFS=m
+CONFIG_VXFS_FS=m
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_QNX4FS_RW is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_UFS_FS_WRITE is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=m
+CONFIG_NFS_V3=y
+CONFIG_NFS_V4=y
+CONFIG_NFS_DIRECTIO=y
+CONFIG_NFSD=m
+CONFIG_NFSD_V3=y
+CONFIG_NFSD_V4=y
+CONFIG_NFSD_TCP=y
+CONFIG_LOCKD=m
+CONFIG_LOCKD_V4=y
+CONFIG_EXPORTFS=m
+CONFIG_SUNRPC=m
+CONFIG_SUNRPC_GSS=m
+CONFIG_RPCSEC_GSS_KRB5=m
+CONFIG_RPCSEC_GSS_SPKM3=m
+CONFIG_SMB_FS=m
+# CONFIG_SMB_NLS_DEFAULT is not set
+CONFIG_CIFS=m
+# CONFIG_CIFS_STATS is not set
+CONFIG_CIFS_XATTR=y
+CONFIG_CIFS_POSIX=y
+# CONFIG_NCP_FS is not set
+CONFIG_NCPFS_PACKET_SIGNING=y
+CONFIG_NCPFS_IOCTL_LOCKING=y
+CONFIG_NCPFS_STRONG=y
+CONFIG_NCPFS_NFS_NS=y
+CONFIG_NCPFS_OS2_NS=y
+CONFIG_NCPFS_SMALLDOS=y
+CONFIG_NCPFS_NLS=y
+CONFIG_NCPFS_EXTRAS=y
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+# CONFIG_RXRPC is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_ACORN_PARTITION is not set
+CONFIG_OSF_PARTITION=y
+# CONFIG_AMIGA_PARTITION is not set
+# CONFIG_ATARI_PARTITION is not set
+CONFIG_MAC_PARTITION=y
+CONFIG_MSDOS_PARTITION=y
+CONFIG_BSD_DISKLABEL=y
+CONFIG_MINIX_SUBPARTITION=y
+CONFIG_SOLARIS_X86_PARTITION=y
+CONFIG_UNIXWARE_DISKLABEL=y
+# CONFIG_LDM_PARTITION is not set
+CONFIG_SGI_PARTITION=y
+# CONFIG_ULTRIX_PARTITION is not set
+CONFIG_SUN_PARTITION=y
+CONFIG_EFI_PARTITION=y
+CONFIG_NLS=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS_DEFAULT="utf8"
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_CODEPAGE_737=m
+CONFIG_NLS_CODEPAGE_775=m
+CONFIG_NLS_CODEPAGE_850=m
+CONFIG_NLS_CODEPAGE_852=m
+CONFIG_NLS_CODEPAGE_855=m
+CONFIG_NLS_CODEPAGE_857=m
+CONFIG_NLS_CODEPAGE_860=m
+CONFIG_NLS_CODEPAGE_861=m
+CONFIG_NLS_CODEPAGE_862=m
+CONFIG_NLS_CODEPAGE_863=m
+CONFIG_NLS_CODEPAGE_864=m
+CONFIG_NLS_CODEPAGE_865=m
+CONFIG_NLS_CODEPAGE_866=m
+CONFIG_NLS_CODEPAGE_869=m
+CONFIG_NLS_CODEPAGE_936=m
+CONFIG_NLS_CODEPAGE_950=m
+CONFIG_NLS_CODEPAGE_932=m
+CONFIG_NLS_CODEPAGE_949=m
+CONFIG_NLS_CODEPAGE_874=m
+CONFIG_NLS_ISO8859_8=m
+CONFIG_NLS_CODEPAGE_1250=m
+CONFIG_NLS_CODEPAGE_1251=m
+CONFIG_NLS_ISO8859_1=m
+CONFIG_NLS_ISO8859_2=m
+CONFIG_NLS_ISO8859_3=m
+CONFIG_NLS_ISO8859_4=m
+CONFIG_NLS_ISO8859_5=m
+CONFIG_NLS_ISO8859_6=m
+CONFIG_NLS_ISO8859_7=m
+CONFIG_NLS_ISO8859_9=m
+CONFIG_NLS_ISO8859_13=m
+CONFIG_NLS_ISO8859_14=m
+CONFIG_NLS_ISO8859_15=m
+CONFIG_NLS_KOI8_R=m
+CONFIG_NLS_KOI8_U=m
+CONFIG_NLS_UTF8=m
+CONFIG_NLS_ASCII=y
+
+#
+# Profiling support
+#
+# CONFIG_PROFILING is not set
+# CONFIG_OPROFILE is not set
+
+#
+# Tux
+#
+CONFIG_TUX=m
+CONFIG_TUX_EXTCGI=y
+# CONFIG_TUX_EXTENDED_LOG is not set
+# CONFIG_TUX_DEBUG is not set
+
+
+#
+# Kernel hacking
+#
+CONFIG_DEBUG_KERNEL=y
+# CONFIG_DEBUG_SLAB is not set
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_HIGHMEM=y
+# CONFIG_DEBUG_INFO is not set
+CONFIG_DEBUG_SPINLOCK_SLEEP=y
+# CONFIG_FRAME_POINTER is not set
+CONFIG_CC_OPTIMIZE_FOR_SIZE=y
+# CONFIG_DEBUG_DRIVER is not set
+
+#
+# Security options
+#
+CONFIG_SECURITY=y
+CONFIG_SECURITY_NETWORK=y
+CONFIG_SECURITY_CAPABILITIES=y
+# CONFIG_SECURITY_ROOTPLUG is not set
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM=y
+CONFIG_SECURITY_SELINUX_DISABLE=y
+CONFIG_SECURITY_SELINUX_DEVELOP=y
+CONFIG_SECURITY_SELINUX_AVC_STATS=y
+# CONFIG_SECURITY_SELINUX_MLS is not set
+CONFIG_SECURITY_SELINUX_BOOTPARAM_VALUE=1
+CONFIG_AUDIT=y
+CONFIG_AUDITSYSCALL=y
+
+#
+# Cryptographic options
+#
+CONFIG_CRYPTO=y
+CONFIG_CRYPTO_HMAC=y
+CONFIG_CRYPTO_NULL=m
+CONFIG_CRYPTO_MD4=m
+CONFIG_CRYPTO_MD5=m
+CONFIG_CRYPTO_SHA1=y
+CONFIG_CRYPTO_SHA256=m
+CONFIG_CRYPTO_SHA512=m
+CONFIG_CRYPTO_DES=m
+CONFIG_CRYPTO_BLOWFISH=m
+CONFIG_CRYPTO_TWOFISH=m
+CONFIG_CRYPTO_SERPENT=m
+CONFIG_CRYPTO_AES=m
+CONFIG_CRYPTO_CAST5=m
+CONFIG_CRYPTO_CAST6=m
+CONFIG_CRYPTO_DEFLATE=m
+CONFIG_CRYPTO_ARC4=m
+CONFIG_CRYPTO_MICHAEL_MIC=m
+# CONFIG_CRYPTO_TEST is not set
+CONFIG_LIBCRC32C=m
+CONFIG_CRYPTO_CRC32C=m
+CONFIG_CRYPTO_SIGNATURE_DSA=y
+CONFIG_CRYPTO_MPILIB=y
+CONFIG_CRYPTO_TEA=m
+CONFIG_CRYPTO_KHAZAD=m
+CONFIG_CRYPTO_WP512=m
+
+#
+# Library routines
+#
+CONFIG_CRC32=m
+CONFIG_CRC_CCITT=m
+
+CONFIG_ZLIB_INFLATE=y
+CONFIG_ZLIB_DEFLATE=m
+CONFIG_PC=y
+# CONFIG_SCSI_BUSLOGIC is not set
+# CONFIG_SCSI_INIA100 is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+# CONFIG_IPX is not set
+# CONFIG_IPDDP is not set
+# CONFIG_IRDA is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_ISAPNP is not set
+# CONFIG_PCMCIA_AHA152X is not set
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_IEEE1394 is not set
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_WD80x3 is not set
+# CONFIG_IRDA is not set
+# CONFIG_GAMEPORT is not set
+# CONFIG_DVB is not set
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+# CONFIG_REISERFS_FS is not set
+# CONFIG_XFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_ROMFS_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_BINFMT_AOUT is not set
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+# CONFIG_DRM_SIS is not set
+# CONFIG_BLK_DEV_UMEM is not set
+# CONFIG_MWAVE is not set
+# CONFIG_ROCKETPORT is not set
+# CONFIG_R3964 is not set
+# CONFIG_TIPAR is not set
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+# CONFIG_VIDEO_DEV is not set
+# CONFIG_PLIP is not set
+# CONFIG_FB_MATROX is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_HGA is not set
+# CONFIG_FB_ATY is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_AHA1542 is not set
+CONFIG_SCSI_FUTURE_DOMAIN=m
+# CONFIG_SCSI_IN2000 is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_I82092 is not set
+# CONFIG_YELLOWFIN is not set
+# CONFIG_SUNDANCE is not set
+# CONFIG_ULTRA is not set
+# CONFIG_SKFP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+# CONFIG_AC3200 is not set
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+# CONFIG_LANCE is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+# CONFIG_HAMACHI is not set
+CONFIG_HP100=m
+# CONFIG_EQUALIZER is not set
+# CONFIG_NET_SB1000 is not set
+# CONFIG_DEPCA is not set
+# CONFIG_ATP is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_INFTL is not set
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PCI is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_AUDIT=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_JFS_FS is not set
+# CONFIG_I2C_PCA_ISA is not set
+CONFIG_RAW_DRIVER=y
+# CONFIG_MTD_SCB2_FLASH is not set
+CONFIG_UID16=y
+CONFIG_X86_PC=y
+# CONFIG_X86_ELAN is not set
+# CONFIG_X86_VOYAGER is not set
+# CONFIG_X86_NUMAQ is not set
+# CONFIG_X86_SUMMIT is not set
+# CONFIG_X86_BIGSMP is not set
+# CONFIG_X86_VISWS is not set
+# CONFIG_X86_GENERICARCH is not set
+# CONFIG_X86_ES7000 is not set
+# CONFIG_M386 is not set
+# CONFIG_M486 is not set
+# CONFIG_M586 is not set
+# CONFIG_M586TSC is not set
+# CONFIG_M586MMX is not set
+CONFIG_M686=y
+# CONFIG_MPENTIUMII is not set
+# CONFIG_MPENTIUMIII is not set
+# CONFIG_MPENTIUMM is not set
+# CONFIG_MPENTIUM4 is not set
+# CONFIG_MK6 is not set
+# CONFIG_MK7 is not set
+# CONFIG_MK8 is not set
+# CONFIG_MCRUSOE is not set
+# CONFIG_MWINCHIPC6 is not set
+# CONFIG_MWINCHIP2 is not set
+# CONFIG_MWINCHIP3D is not set
+# CONFIG_MCYRIXIII is not set
+# CONFIG_MVIAC3_2 is not set
+CONFIG_X86_GENERIC=y
+CONFIG_X86_CMPXCHG=y
+CONFIG_X86_XADD=y
+CONFIG_X86_L1_CACHE_SHIFT=7
+CONFIG_RWSEM_XCHGADD_ALGORITHM=y
+CONFIG_X86_PPRO_FENCE=y
+CONFIG_X86_WP_WORKS_OK=y
+CONFIG_X86_INVLPG=y
+CONFIG_X86_BSWAP=y
+CONFIG_X86_POPAD_OK=y
+CONFIG_X86_GOOD_APIC=y
+CONFIG_X86_INTEL_USERCOPY=y
+CONFIG_X86_USE_PPRO_CHECKSUM=y
+# CONFIG_HPET is not set
+CONFIG_HPET_TIMER=y
+CONFIG_HPET_EMULATE_RTC=y
+CONFIG_NR_CPUS=8
+CONFIG_X86_LOCAL_APIC=y
+CONFIG_X86_IO_APIC=y
+CONFIG_X86_TSC=y
+CONFIG_X86_MCE=y
+# CONFIG_X86_MCE_NONFATAL is not set
+CONFIG_X86_MCE_P4THERMAL=y
+CONFIG_TOSHIBA=m
+CONFIG_I8K=m
+CONFIG_SONYPI=m
+CONFIG_MICROCODE=m
+CONFIG_X86_MSR=m
+CONFIG_X86_CPUID=m
+CONFIG_EDD=m
+# CONFIG_NUMA is not set
+# CONFIG_NOHIGHMEM is not set
+CONFIG_HIGHMEM4G=y
+# CONFIG_HIGHMEM64G is not set
+CONFIG_HIGHMEM=y
+CONFIG_HIGHPTE=y
+# CONFIG_MATH_EMULATION is not set
+CONFIG_MTRR=y
+CONFIG_HAVE_DEC_LOCK=y
+# CONFIG_X86_UP_APIC is not set
+CONFIG_X86_PM_TIMER=y
+# CONFIG_X86_4G is not set
+# CONFIG_EFI is not set
+CONFIG_REGPARM=y
+# CONFIG_PCI_GOBIOS is not set
+# CONFIG_PCI_GODIRECT is not set
+# CONFIG_PCI_GOMMCONFIG is not set
+CONFIG_PCI_GOANY=y
+CONFIG_MDA_CONSOLE=m
+CONFIG_SYNCLINK_CS=m
+CONFIG_SYNCLINK=m
+CONFIG_SYNCLINKMP=m
+CONFIG_HP100=m
+CONFIG_PCMCIA_FDOMAIN=m
+CONFIG_SCSI_FUTURE_DOMAIN=m
+CONFIG_CRASH=m
+CONFIG_CAPI_EICON=y
+CONFIG_I2O=m
+CONFIG_I2O_BLOCK=m
+CONFIG_I2O_SCSI=m
+CONFIG_I2O_PROC=m
+CONFIG_I2O_CONFIG=y
+CONFIG_APM=y
+# CONFIG_APM_IGNORE_USER_SUSPEND is not set
+# CONFIG_APM_DO_ENABLE is not set
+CONFIG_APM_CPU_IDLE=y
+# CONFIG_APM_DISPLAY_BLANK is not set
+CONFIG_APM_RTC_IS_GMT=y
+# CONFIG_APM_ALLOW_INTS is not set
+# CONFIG_APM_REAL_MODE_POWER_OFF is not set
+CONFIG_X86_FIND_SMP_CONFIG=y
+CONFIG_X86_MPPARSE=y
+CONFIG_ACPI=y
+CONFIG_ACPI_BOOT=y
+CONFIG_ACPI_INTERPRETER=y
+CONFIG_ACPI_SLEEP=y
+CONFIG_ACPI_AC=m
+CONFIG_ACPI_BATTERY=m
+CONFIG_ACPI_BUTTON=m
+CONFIG_ACPI_FAN=y
+CONFIG_ACPI_PROCESSOR=y
+CONFIG_ACPI_THERMAL=y
+CONFIG_ACPI_ASUS=m
+CONFIG_ACPI_TOSHIBA=m
+# CONFIG_ACPI_DEBUG is not set
+CONFIG_ACPI_BUS=y
+CONFIG_ACPI_EC=y
+CONFIG_ACPI_POWER=y
+CONFIG_ACPI_PCI=y
+CONFIG_ACPI_SYSTEM=y
+CONFIG_ACPI_NUMA=y
+CONFIG_ACPI_BLACKLIST_YEAR=2001
+CONFIG_X86_ACPI_CPUFREQ=y
+# CONFIG_X86_ACPI_CPUFREQ_PROC_INTF is not set
+CONFIG_X86_POWERNOW_K6=m
+CONFIG_X86_POWERNOW_K7=y
+CONFIG_X86_POWERNOW_K8=m
+# CONFIG_X86_GX_SUSPMOD is not set
+# CONFIG_X86_SPEEDSTEP_CENTRINO is not set
+CONFIG_X86_SPEEDSTEP_ICH=y
+CONFIG_X86_SPEEDSTEP_SMI=m
+CONFIG_X86_SPEEDSTEP_LIB=y
+# CONFIG_X86_SPEEDSTEP_RELAXED_CAP_CHECK is not set
+CONFIG_X86_P4_CLOCKMOD=m
+CONFIG_X86_LONGRUN=y
+CONFIG_X86_LONGHAUL=y
+CONFIG_X86_SMP=y
+CONFIG_X86_HT=y
+CONFIG_X86_BIOS_REBOOT=y
+CONFIG_X86_TRAMPOLINE=y
+CONFIG_TUX=m
+CONFIG_NVRAM=m
+CONFIG_IBM_ASM=m
+CONFIG_CRYPTO_AES_586=m
+CONFIG_GENERIC_ISA_DMA=y
+CONFIG_SCHED_SMT=y
+# CONFIG_IRQBALANCE is not set
+# CONFIG_SOFTWARE_SUSPEND is not set
+# CONFIG_PM_DEBUG is not set
+CONFIG_CPU_FREQ=y
+# CONFIG_CPU_FREQ_PROC_INTF is not set
+# CONFIG_CPU_FREQ_DEFAULT_GOV_PERFORMANCE is not set
+CONFIG_CPU_FREQ_DEFAULT_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_PERFORMANCE=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=m
+CONFIG_CPU_FREQ_GOV_USERSPACE=m
+CONFIG_CPU_FREQ_GOV_ONDEMAND=m
+# CONFIG_CPU_FREQ_24_API is not set
+CONFIG_CPU_FREQ_TABLE=y
+CONFIG_DEBUG_STACKOVERFLOW=y
+CONFIG_DEBUG_STACK_USAGE=y
+# CONFIG_DEBUG_PAGEALLOC is not set
+# CONFIG_KPROBES is not set
+CONFIG_KEXEC=y
+CONFIG_NETDUMP=m
+# CONFIG_SCHEDSTATS is not set
+CONFIG_PCI_DIRECT=y
+CONFIG_PCI_MMCONFIG=y
+CONFIG_PCI_BIOS=y
+CONFIG_HOTPLUG_PCI=y
+# CONFIG_HOTPLUG_PCI_FAKE is not set
+CONFIG_HOTPLUG_PCI_COMPAQ=m
+# CONFIG_HOTPLUG_PCI_COMPAQ_NVRAM is not set
+CONFIG_HOTPLUG_PCI_IBM=m
+CONFIG_HOTPLUG_PCI_ACPI=m 
+CONFIG_HOTPLUG_PCI_ACPI_IBM=m
+# CONFIG_HOTPLUG_PCI_CPCI is not set
+CONFIG_HOTPLUG_PCI_PCIE=m
+# CONFIG_HOTPLUG_PCI_PCIE_POLL_EVENT_MODE is not set
+CONFIG_HOTPLUG_PCI_SHPC=m
+# CONFIG_HOTPLUG_PCI_SHPC_POLL_EVENT_MODE is not set
+# CONFIG_HOTPLUG_PCI_SHPC_PHPRM_LEGACY is not set
+CONFIG_PM=y
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
+CONFIG_M686=y
+# CONFIG_NOHIGHMEM is not set
+# CONFIG_SMP is not set
+CONFIG_HIGHMEM4G=y
+# CONFIG_HIGHMEM64G is not set
+# CONFIG_PROFILING is not set
+# CONFIG_OPROFILE is not set
diff --git a/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-ia64-smp.config b/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-ia64-smp.config
new file mode 100644 (file)
index 0000000..611ce45
--- /dev/null
@@ -0,0 +1,1908 @@
+#
+# Automatically generated make config: don't edit
+# Linux kernel version: 2.6.9-5.0.3.EL_lustre-b1_4_rhel4.200503031449smp
+# Thu Mar  3 14:52:42 2005
+#
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_CLEAN_COMPILE=y
+
+#
+# General setup
+#
+CONFIG_LOCALVERSION=""
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+CONFIG_POSIX_MQUEUE=y
+CONFIG_BSD_PROCESS_ACCT=y
+# CONFIG_BSD_PROCESS_ACCT_V3 is not set
+CONFIG_SYSCTL=y
+CONFIG_AUDIT=y
+CONFIG_AUDITSYSCALL=y
+CONFIG_LOG_BUF_SHIFT=17
+CONFIG_HOTPLUG=y
+# CONFIG_IKCONFIG is not set
+# CONFIG_EMBEDDED is not set
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_ALL is not set
+CONFIG_KALLSYMS_EXTRA_PASS=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+CONFIG_IOSCHED_CFQ=y
+# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
+CONFIG_SHMEM=y
+# CONFIG_TINY_SHMEM is not set
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+CONFIG_MODVERSIONS=y
+CONFIG_MODULE_SIG=y
+# CONFIG_MODULE_SIG_FORCE is not set
+CONFIG_KMOD=y
+CONFIG_STOP_MACHINE=y
+
+#
+# Processor type and features
+#
+CONFIG_IA64=y
+CONFIG_64BIT=y
+CONFIG_MMU=y
+CONFIG_RWSEM_XCHGADD_ALGORITHM=y
+CONFIG_TIME_INTERPOLATION=y
+CONFIG_EFI=y
+CONFIG_GENERIC_IOMAP=y
+CONFIG_IA64_GENERIC=y
+# CONFIG_IA64_DIG is not set
+# CONFIG_IA64_HP_ZX1 is not set
+# CONFIG_IA64_SGI_SN2 is not set
+# CONFIG_IA64_HP_SIM is not set
+# CONFIG_ITANIUM is not set
+CONFIG_MCKINLEY=y
+# CONFIG_IA64_PAGE_SIZE_4KB is not set
+# CONFIG_IA64_PAGE_SIZE_8KB is not set
+CONFIG_IA64_PAGE_SIZE_16KB=y
+# CONFIG_IA64_PAGE_SIZE_64KB is not set
+CONFIG_IA64_L1_CACHE_SHIFT=7
+CONFIG_NUMA=y
+CONFIG_VIRTUAL_MEM_MAP=y
+CONFIG_DISCONTIGMEM=y
+CONFIG_IA64_CYCLONE=y
+CONFIG_IOSAPIC=y
+CONFIG_FORCE_MAX_ZONEORDER=18
+CONFIG_SMP=y
+CONFIG_NR_CPUS=64
+# CONFIG_HOTPLUG_CPU is not set
+# CONFIG_PREEMPT is not set
+CONFIG_HAVE_DEC_LOCK=y
+# CONFIG_IA32_SUPPORT is not set
+CONFIG_IA64_MCA_RECOVERY=m
+CONFIG_PERFMON=y
+CONFIG_IA64_PALINFO=y
+
+#
+# Firmware Drivers
+#
+CONFIG_EFI_VARS=y
+CONFIG_EFI_PCDP=y
+CONFIG_BINFMT_ELF=y
+CONFIG_BINFMT_MISC=y
+
+#
+# Power management and ACPI
+#
+CONFIG_PM=y
+CONFIG_ACPI=y
+
+#
+# ACPI (Advanced Configuration and Power Interface) Support
+#
+CONFIG_ACPI_BOOT=y
+CONFIG_ACPI_INTERPRETER=y
+CONFIG_ACPI_BUTTON=m
+CONFIG_ACPI_FAN=y
+CONFIG_ACPI_PROCESSOR=y
+CONFIG_ACPI_THERMAL=y
+CONFIG_ACPI_NUMA=y
+CONFIG_ACPI_BLACKLIST_YEAR=2001
+# CONFIG_ACPI_DEBUG is not set
+CONFIG_ACPI_BUS=y
+CONFIG_ACPI_POWER=y
+CONFIG_ACPI_PCI=y
+CONFIG_ACPI_SYSTEM=y
+
+#
+# Bus options (PCI, PCMCIA)
+#
+CONFIG_PCI=y
+CONFIG_PCI_DOMAINS=y
+CONFIG_PCI_MSI=y
+CONFIG_PCI_LEGACY_PROC=y
+# CONFIG_PCI_NAMES is not set
+
+#
+# PCI Hotplug Support
+#
+CONFIG_HOTPLUG_PCI=y
+# CONFIG_HOTPLUG_PCI_FAKE is not set
+CONFIG_HOTPLUG_PCI_ACPI=m
+CONFIG_HOTPLUG_PCI_ACPI_IBM=m
+# CONFIG_HOTPLUG_PCI_CPCI is not set
+CONFIG_HOTPLUG_PCI_PCIE=m
+# CONFIG_HOTPLUG_PCI_PCIE_POLL_EVENT_MODE is not set
+CONFIG_HOTPLUG_PCI_SHPC=m
+# CONFIG_HOTPLUG_PCI_SHPC_POLL_EVENT_MODE is not set
+
+#
+# PCMCIA/CardBus support
+#
+CONFIG_PCMCIA=m
+# CONFIG_PCMCIA_DEBUG is not set
+CONFIG_YENTA=m
+CONFIG_CARDBUS=y
+CONFIG_PD6729=m
+# CONFIG_I82092 is not set
+CONFIG_TCIC=m
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+CONFIG_FW_LOADER=y
+# CONFIG_DEBUG_DRIVER is not set
+
+#
+# Memory Technology Devices (MTD)
+#
+# CONFIG_MTD is not set
+
+#
+# Parallel port support
+#
+CONFIG_PARPORT=m
+CONFIG_PARPORT_PC=m
+CONFIG_PARPORT_PC_CML1=m
+CONFIG_PARPORT_SERIAL=m
+# CONFIG_PARPORT_PC_FIFO is not set
+# CONFIG_PARPORT_PC_SUPERIO is not set
+CONFIG_PARPORT_PC_PCMCIA=m
+# CONFIG_PARPORT_OTHER is not set
+CONFIG_PARPORT_1284=y
+
+#
+# Plug and Play support
+#
+
+#
+# Block devices
+#
+# CONFIG_PARIDE is not set
+CONFIG_BLK_CPQ_DA=m
+CONFIG_BLK_CPQ_CISS_DA=m
+CONFIG_CISS_SCSI_TAPE=y
+CONFIG_BLK_DEV_DAC960=m
+# CONFIG_BLK_DEV_UMEM is not set
+CONFIG_BLK_DEV_LOOP=m
+CONFIG_BLK_DEV_CRYPTOLOOP=m
+CONFIG_BLK_DEV_NBD=m
+CONFIG_BLK_DEV_SX8=m
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=16384
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_DISKDUMP=m
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_IDE_SATA is not set
+CONFIG_BLK_DEV_IDEDISK=y
+CONFIG_IDEDISK_MULTI_MODE=y
+CONFIG_BLK_DEV_IDECS=m
+CONFIG_BLK_DEV_DELKIN=m
+CONFIG_BLK_DEV_IDECD=y
+# CONFIG_BLK_DEV_IDETAPE is not set
+CONFIG_BLK_DEV_IDEFLOPPY=y
+CONFIG_BLK_DEV_IDESCSI=m
+# CONFIG_IDE_TASK_IOCTL is not set
+# CONFIG_IDE_TASKFILE_IO is not set
+
+#
+# IDE chipset support/bugfixes
+#
+CONFIG_IDE_GENERIC=y
+CONFIG_BLK_DEV_IDEPCI=y
+CONFIG_IDEPCI_SHARE_IRQ=y
+# CONFIG_BLK_DEV_OFFBOARD is not set
+CONFIG_BLK_DEV_GENERIC=y
+# CONFIG_BLK_DEV_OPTI621 is not set
+CONFIG_BLK_DEV_IDEDMA_PCI=y
+# CONFIG_BLK_DEV_IDEDMA_FORCED is not set
+CONFIG_IDEDMA_PCI_AUTO=y
+# CONFIG_IDEDMA_ONLYDISK is not set
+CONFIG_BLK_DEV_AEC62XX=y
+CONFIG_BLK_DEV_ALI15X3=y
+# CONFIG_WDC_ALI15X3 is not set
+CONFIG_BLK_DEV_AMD74XX=y
+CONFIG_BLK_DEV_CMD64X=y
+CONFIG_BLK_DEV_TRIFLEX=y
+CONFIG_BLK_DEV_CY82C693=y
+CONFIG_BLK_DEV_CS5520=y
+CONFIG_BLK_DEV_CS5530=y
+CONFIG_BLK_DEV_HPT34X=y
+# CONFIG_HPT34X_AUTODMA is not set
+CONFIG_BLK_DEV_HPT366=y
+# CONFIG_BLK_DEV_SC1200 is not set
+CONFIG_BLK_DEV_PIIX=y
+CONFIG_BLK_DEV_IT8212=y
+# CONFIG_BLK_DEV_NS87415 is not set
+CONFIG_BLK_DEV_PDC202XX_OLD=y
+# CONFIG_PDC202XX_BURST is not set
+CONFIG_BLK_DEV_PDC202XX_NEW=y
+CONFIG_PDC202XX_FORCE=y
+CONFIG_BLK_DEV_SVWKS=y
+CONFIG_BLK_DEV_SGIIOC4=m
+CONFIG_BLK_DEV_SIIMAGE=y
+CONFIG_BLK_DEV_SLC90E66=y
+# CONFIG_BLK_DEV_TRM290 is not set
+CONFIG_BLK_DEV_VIA82CXXX=y
+# CONFIG_IDE_ARM is not set
+CONFIG_BLK_DEV_IDEDMA=y
+# CONFIG_IDEDMA_IVB is not set
+CONFIG_IDEDMA_AUTO=y
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+CONFIG_SCSI=m
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=m
+CONFIG_SCSI_DUMP=m
+CONFIG_SD_IOSTATS=y
+CONFIG_CHR_DEV_ST=m
+CONFIG_CHR_DEV_OSST=m
+CONFIG_BLK_DEV_SR=m
+CONFIG_BLK_DEV_SR_VENDOR=y
+CONFIG_CHR_DEV_SG=m
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+
+#
+# SCSI Transport Attributes
+#
+CONFIG_SCSI_SPI_ATTRS=m
+CONFIG_SCSI_FC_ATTRS=m
+
+#
+# SCSI low-level drivers
+#
+CONFIG_BLK_DEV_3W_XXXX_RAID=m
+CONFIG_SCSI_3W_9XXX=m
+CONFIG_SCSI_ACARD=m
+CONFIG_SCSI_AACRAID=m
+CONFIG_SCSI_AIC7XXX=m
+CONFIG_AIC7XXX_CMDS_PER_DEVICE=4
+CONFIG_AIC7XXX_RESET_DELAY_MS=15000
+# CONFIG_AIC7XXX_DEBUG_ENABLE is not set
+CONFIG_AIC7XXX_DEBUG_MASK=0
+# CONFIG_AIC7XXX_REG_PRETTY_PRINT is not set
+CONFIG_SCSI_AIC7XXX_OLD=m
+CONFIG_SCSI_AIC79XX=m
+CONFIG_AIC79XX_CMDS_PER_DEVICE=4
+CONFIG_AIC79XX_RESET_DELAY_MS=15000
+# CONFIG_AIC79XX_ENABLE_RD_STRM is not set
+# CONFIG_AIC79XX_DEBUG_ENABLE is not set
+CONFIG_AIC79XX_DEBUG_MASK=0
+# CONFIG_AIC79XX_REG_PRETTY_PRINT is not set
+CONFIG_MEGARAID_NEWGEN=y
+CONFIG_MEGARAID_MM=m
+CONFIG_MEGARAID_MAILBOX=m
+CONFIG_SCSI_SATA=y
+CONFIG_SCSI_SATA_AHCI=m
+CONFIG_SCSI_SATA_SVW=m
+CONFIG_SCSI_ATA_PIIX=m
+CONFIG_SCSI_SATA_NV=m
+CONFIG_SCSI_SATA_PROMISE=m
+CONFIG_SCSI_SATA_SX4=m
+CONFIG_SCSI_SATA_SIL=m
+CONFIG_SCSI_SATA_SIS=m
+CONFIG_SCSI_SATA_VIA=m
+CONFIG_SCSI_SATA_VITESSE=m
+# CONFIG_SCSI_BUSLOGIC is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_EATA is not set
+# CONFIG_SCSI_EATA_PIO is not set
+CONFIG_SCSI_LPFC=m
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+CONFIG_SCSI_GDTH=m
+CONFIG_SCSI_IPS=m
+CONFIG_SCSI_INITIO=m
+# CONFIG_SCSI_INIA100 is not set
+CONFIG_SCSI_PPA=m
+CONFIG_SCSI_IMM=m
+# CONFIG_SCSI_IZIP_EPP16 is not set
+# CONFIG_SCSI_IZIP_SLOW_CTR is not set
+CONFIG_SCSI_SYM53C8XX_2=m
+CONFIG_SCSI_SYM53C8XX_DMA_ADDRESSING_MODE=1
+CONFIG_SCSI_SYM53C8XX_DEFAULT_TAGS=16
+CONFIG_SCSI_SYM53C8XX_MAX_TAGS=64
+# CONFIG_SCSI_SYM53C8XX_IOMAPPED is not set
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_SCSI_QLOGIC_FC is not set
+CONFIG_SCSI_QLOGIC_1280=m
+CONFIG_SCSI_QLA2XXX=m
+CONFIG_SCSI_QLA21XX=m
+CONFIG_SCSI_QLA22XX=m
+CONFIG_SCSI_QLA2300=m
+CONFIG_SCSI_QLA2322=m
+CONFIG_SCSI_QLA6312=m
+CONFIG_SCSI_QLA6322=m
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_DC390T is not set
+# CONFIG_SCSI_DEBUG is not set
+
+#
+# PCMCIA SCSI adapter support
+#
+# CONFIG_PCMCIA_FDOMAIN is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+CONFIG_MD=y
+CONFIG_BLK_DEV_MD=y
+CONFIG_MD_LINEAR=m
+CONFIG_MD_RAID0=m
+CONFIG_MD_RAID1=m
+CONFIG_MD_RAID10=m
+CONFIG_MD_RAID5=m
+CONFIG_MD_RAID6=m
+CONFIG_MD_MULTIPATH=m
+CONFIG_BLK_DEV_DM=m
+CONFIG_DM_CRYPT=m
+CONFIG_DM_SNAPSHOT=m
+CONFIG_DM_MIRROR=m
+CONFIG_DM_ZERO=m
+
+#
+# Fusion MPT device support
+#
+CONFIG_FUSION=m
+CONFIG_FUSION_MAX_SGE=40
+CONFIG_FUSION_CTL=m
+CONFIG_FUSION_LAN=m
+
+#
+# IEEE 1394 (FireWire) support
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# I2O device support
+#
+# CONFIG_I2O is not set
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+CONFIG_PACKET=y
+CONFIG_PACKET_MMAP=y
+CONFIG_NETLINK_DEV=y
+CONFIG_UNIX=y
+CONFIG_NET_KEY=m
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_FWMARK=y
+CONFIG_IP_ROUTE_MULTIPATH=y
+CONFIG_IP_ROUTE_VERBOSE=y
+# CONFIG_IP_PNP is not set
+CONFIG_NET_IPIP=m
+CONFIG_NET_IPGRE=m
+CONFIG_NET_IPGRE_BROADCAST=y
+CONFIG_IP_MROUTE=y
+CONFIG_IP_PIMSM_V1=y
+CONFIG_IP_PIMSM_V2=y
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+CONFIG_INET_AH=m
+CONFIG_INET_ESP=m
+CONFIG_INET_IPCOMP=m
+CONFIG_INET_TUNNEL=m
+
+#
+# IP: Virtual Server Configuration
+#
+CONFIG_IP_VS=m
+# CONFIG_IP_VS_DEBUG is not set
+CONFIG_IP_VS_TAB_BITS=12
+
+#
+# IPVS transport protocol load balancing support
+#
+CONFIG_IP_VS_PROTO_TCP=y
+CONFIG_IP_VS_PROTO_UDP=y
+CONFIG_IP_VS_PROTO_ESP=y
+CONFIG_IP_VS_PROTO_AH=y
+
+#
+# IPVS scheduler
+#
+CONFIG_IP_VS_RR=m
+CONFIG_IP_VS_WRR=m
+CONFIG_IP_VS_LC=m
+CONFIG_IP_VS_WLC=m
+CONFIG_IP_VS_LBLC=m
+CONFIG_IP_VS_LBLCR=m
+CONFIG_IP_VS_DH=m
+CONFIG_IP_VS_SH=m
+CONFIG_IP_VS_SED=m
+CONFIG_IP_VS_NQ=m
+
+#
+# IPVS application helper
+#
+CONFIG_IP_VS_FTP=m
+CONFIG_IPV6=m
+CONFIG_IPV6_PRIVACY=y
+CONFIG_INET6_AH=m
+CONFIG_INET6_ESP=m
+CONFIG_INET6_IPCOMP=m
+CONFIG_INET6_TUNNEL=m
+CONFIG_IPV6_TUNNEL=m
+CONFIG_NETFILTER=y
+# CONFIG_NETFILTER_DEBUG is not set
+CONFIG_BRIDGE_NETFILTER=y
+
+#
+# IP: Netfilter Configuration
+#
+CONFIG_IP_NF_CONNTRACK=m
+CONFIG_IP_NF_CT_ACCT=y
+CONFIG_IP_NF_CT_PROTO_SCTP=m
+CONFIG_IP_NF_FTP=m
+CONFIG_IP_NF_IRC=m
+CONFIG_IP_NF_TFTP=m
+CONFIG_IP_NF_AMANDA=m
+CONFIG_IP_NF_QUEUE=m
+CONFIG_IP_NF_IPTABLES=m
+CONFIG_IP_NF_MATCH_LIMIT=m
+CONFIG_IP_NF_MATCH_IPRANGE=m
+CONFIG_IP_NF_MATCH_MAC=m
+CONFIG_IP_NF_MATCH_PKTTYPE=m
+CONFIG_IP_NF_MATCH_MARK=m
+CONFIG_IP_NF_MATCH_MULTIPORT=m
+CONFIG_IP_NF_MATCH_TOS=m
+CONFIG_IP_NF_MATCH_RECENT=m
+CONFIG_IP_NF_MATCH_ECN=m
+CONFIG_IP_NF_MATCH_DSCP=m
+CONFIG_IP_NF_MATCH_AH_ESP=m
+CONFIG_IP_NF_MATCH_LENGTH=m
+CONFIG_IP_NF_MATCH_TTL=m
+CONFIG_IP_NF_MATCH_TCPMSS=m
+CONFIG_IP_NF_MATCH_HELPER=m
+CONFIG_IP_NF_MATCH_STATE=m
+CONFIG_IP_NF_MATCH_CONNTRACK=m
+CONFIG_IP_NF_MATCH_OWNER=m
+CONFIG_IP_NF_MATCH_PHYSDEV=m
+CONFIG_IP_NF_MATCH_ADDRTYPE=m
+CONFIG_IP_NF_MATCH_REALM=m
+CONFIG_IP_NF_MATCH_SCTP=m
+CONFIG_IP_NF_MATCH_COMMENT=m
+CONFIG_IP_NF_FILTER=m
+CONFIG_IP_NF_TARGET_REJECT=m
+CONFIG_IP_NF_TARGET_LOG=m
+CONFIG_IP_NF_TARGET_ULOG=m
+CONFIG_IP_NF_TARGET_TCPMSS=m
+CONFIG_IP_NF_NAT=m
+CONFIG_IP_NF_NAT_NEEDED=y
+CONFIG_IP_NF_TARGET_MASQUERADE=m
+CONFIG_IP_NF_TARGET_REDIRECT=m
+CONFIG_IP_NF_TARGET_NETMAP=m
+CONFIG_IP_NF_TARGET_SAME=m
+CONFIG_IP_NF_NAT_LOCAL=y
+CONFIG_IP_NF_NAT_SNMP_BASIC=m
+CONFIG_IP_NF_NAT_IRC=m
+CONFIG_IP_NF_NAT_FTP=m
+CONFIG_IP_NF_NAT_TFTP=m
+CONFIG_IP_NF_NAT_AMANDA=m
+CONFIG_IP_NF_MANGLE=m
+CONFIG_IP_NF_TARGET_TOS=m
+CONFIG_IP_NF_TARGET_ECN=m
+CONFIG_IP_NF_TARGET_DSCP=m
+CONFIG_IP_NF_TARGET_MARK=m
+CONFIG_IP_NF_TARGET_CLASSIFY=m
+CONFIG_IP_NF_RAW=m
+CONFIG_IP_NF_TARGET_NOTRACK=m
+CONFIG_IP_NF_ARPTABLES=m
+CONFIG_IP_NF_ARPFILTER=m
+CONFIG_IP_NF_ARP_MANGLE=m
+# CONFIG_IP_NF_COMPAT_IPCHAINS is not set
+# CONFIG_IP_NF_COMPAT_IPFWADM is not set
+
+#
+# IPv6: Netfilter Configuration
+#
+# CONFIG_IP6_NF_QUEUE is not set
+CONFIG_IP6_NF_IPTABLES=m
+CONFIG_IP6_NF_MATCH_LIMIT=m
+CONFIG_IP6_NF_MATCH_MAC=m
+CONFIG_IP6_NF_MATCH_RT=m
+CONFIG_IP6_NF_MATCH_OPTS=m
+CONFIG_IP6_NF_MATCH_FRAG=m
+CONFIG_IP6_NF_MATCH_HL=m
+CONFIG_IP6_NF_MATCH_MULTIPORT=m
+CONFIG_IP6_NF_MATCH_OWNER=m
+CONFIG_IP6_NF_MATCH_MARK=m
+CONFIG_IP6_NF_MATCH_IPV6HEADER=m
+CONFIG_IP6_NF_MATCH_AHESP=m
+CONFIG_IP6_NF_MATCH_LENGTH=m
+CONFIG_IP6_NF_MATCH_EUI64=m
+CONFIG_IP6_NF_MATCH_PHYSDEV=m
+CONFIG_IP6_NF_FILTER=m
+CONFIG_IP6_NF_TARGET_LOG=m
+CONFIG_IP6_NF_MANGLE=m
+CONFIG_IP6_NF_TARGET_MARK=m
+CONFIG_IP6_NF_RAW=m
+
+#
+# Bridge: Netfilter Configuration
+#
+CONFIG_BRIDGE_NF_EBTABLES=m
+CONFIG_BRIDGE_EBT_BROUTE=m
+CONFIG_BRIDGE_EBT_T_FILTER=m
+CONFIG_BRIDGE_EBT_T_NAT=m
+CONFIG_BRIDGE_EBT_802_3=m
+CONFIG_BRIDGE_EBT_AMONG=m
+CONFIG_BRIDGE_EBT_ARP=m
+CONFIG_BRIDGE_EBT_IP=m
+CONFIG_BRIDGE_EBT_LIMIT=m
+CONFIG_BRIDGE_EBT_MARK=m
+CONFIG_BRIDGE_EBT_PKTTYPE=m
+CONFIG_BRIDGE_EBT_STP=m
+CONFIG_BRIDGE_EBT_VLAN=m
+CONFIG_BRIDGE_EBT_ARPREPLY=m
+CONFIG_BRIDGE_EBT_DNAT=m
+CONFIG_BRIDGE_EBT_MARK_T=m
+CONFIG_BRIDGE_EBT_REDIRECT=m
+CONFIG_BRIDGE_EBT_SNAT=m
+CONFIG_BRIDGE_EBT_LOG=m
+CONFIG_XFRM=y
+CONFIG_XFRM_USER=y
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+CONFIG_IP_SCTP=m
+# CONFIG_SCTP_DBG_MSG is not set
+# CONFIG_SCTP_DBG_OBJCNT is not set
+# CONFIG_SCTP_HMAC_NONE is not set
+# CONFIG_SCTP_HMAC_SHA1 is not set
+CONFIG_SCTP_HMAC_MD5=y
+CONFIG_ATM=m
+CONFIG_ATM_CLIP=m
+# CONFIG_ATM_CLIP_NO_ICMP is not set
+CONFIG_ATM_LANE=m
+# CONFIG_ATM_MPOA is not set
+CONFIG_ATM_BR2684=m
+# CONFIG_ATM_BR2684_IPFILTER is not set
+CONFIG_BRIDGE=m
+CONFIG_VLAN_8021Q=m
+# CONFIG_DECNET is not set
+CONFIG_LLC=y
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_ATALK is not set
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+CONFIG_NET_DIVERT=y
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+
+#
+# QoS and/or fair queueing
+#
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_CLK_JIFFIES=y
+# CONFIG_NET_SCH_CLK_GETTIMEOFDAY is not set
+# CONFIG_NET_SCH_CLK_CPU is not set
+CONFIG_NET_SCH_CBQ=m
+CONFIG_NET_SCH_HTB=m
+CONFIG_NET_SCH_HFSC=m
+CONFIG_NET_SCH_ATM=m
+CONFIG_NET_SCH_PRIO=m
+CONFIG_NET_SCH_RED=m
+CONFIG_NET_SCH_SFQ=m
+CONFIG_NET_SCH_TEQL=m
+CONFIG_NET_SCH_TBF=m
+CONFIG_NET_SCH_GRED=m
+CONFIG_NET_SCH_DSMARK=m
+CONFIG_NET_SCH_NETEM=m
+CONFIG_NET_SCH_INGRESS=m
+CONFIG_NET_QOS=y
+CONFIG_NET_ESTIMATOR=y
+CONFIG_NET_CLS=y
+CONFIG_NET_CLS_TCINDEX=m
+CONFIG_NET_CLS_ROUTE4=m
+CONFIG_NET_CLS_ROUTE=y
+CONFIG_NET_CLS_FW=m
+CONFIG_NET_CLS_U32=m
+CONFIG_CLS_U32_PERF=y
+CONFIG_NET_CLS_IND=y
+CONFIG_NET_CLS_RSVP=m
+CONFIG_NET_CLS_RSVP6=m
+# CONFIG_NET_CLS_ACT is not set
+CONFIG_NET_CLS_POLICE=y
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+CONFIG_NETPOLL=y
+# CONFIG_NETPOLL_RX is not set
+CONFIG_NETPOLL_TRAP=y
+CONFIG_NET_POLL_CONTROLLER=y
+# CONFIG_HAMRADIO is not set
+# CONFIG_IRDA is not set
+CONFIG_BT=m
+CONFIG_BT_L2CAP=m
+CONFIG_BT_SCO=m
+CONFIG_BT_RFCOMM=m
+CONFIG_BT_RFCOMM_TTY=y
+CONFIG_BT_BNEP=m
+CONFIG_BT_BNEP_MC_FILTER=y
+CONFIG_BT_BNEP_PROTO_FILTER=y
+CONFIG_BT_CMTP=m
+CONFIG_BT_HIDP=m
+
+#
+# Bluetooth device drivers
+#
+CONFIG_BT_HCIUSB=m
+CONFIG_BT_HCIUSB_SCO=y
+CONFIG_BT_HCIUART=m
+CONFIG_BT_HCIUART_H4=y
+CONFIG_BT_HCIUART_BCSP=y
+CONFIG_BT_HCIUART_BCSP_TXCRC=y
+CONFIG_BT_HCIBCM203X=m
+CONFIG_BT_HCIBFUSB=m
+CONFIG_BT_HCIDTL1=m
+CONFIG_BT_HCIBT3C=m
+CONFIG_BT_HCIBLUECARD=m
+CONFIG_BT_HCIBTUART=m
+CONFIG_BT_HCIVHCI=m
+CONFIG_TUX=m
+
+#
+# TUX options
+#
+CONFIG_TUX_EXTCGI=y
+# CONFIG_TUX_EXTENDED_LOG is not set
+# CONFIG_TUX_DEBUG is not set
+CONFIG_NETDEVICES=y
+CONFIG_DUMMY=m
+CONFIG_BONDING=m
+# CONFIG_EQUALIZER is not set
+CONFIG_TUN=m
+CONFIG_ETHERTAP=m
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=m
+CONFIG_HAPPYMEAL=m
+CONFIG_SUNGEM=m
+CONFIG_NET_VENDOR_3COM=y
+CONFIG_VORTEX=m
+CONFIG_TYPHOON=m
+
+#
+# Tulip family network device support
+#
+CONFIG_NET_TULIP=y
+CONFIG_DE2104X=m
+CONFIG_TULIP=m
+# CONFIG_TULIP_MWI is not set
+CONFIG_TULIP_MMIO=y
+# CONFIG_TULIP_NAPI is not set
+CONFIG_DE4X5=m
+CONFIG_WINBOND_840=m
+CONFIG_DM9102=m
+CONFIG_PCMCIA_XIRCOM=m
+# CONFIG_HP100 is not set
+CONFIG_NET_PCI=y
+CONFIG_PCNET32=m
+CONFIG_AMD8111_ETH=m
+CONFIG_AMD8111E_NAPI=y
+CONFIG_ADAPTEC_STARFIRE=m
+CONFIG_ADAPTEC_STARFIRE_NAPI=y
+CONFIG_B44=m
+CONFIG_FORCEDETH=m
+# CONFIG_DGRS is not set
+CONFIG_EEPRO100=m
+# CONFIG_EEPRO100_PIO is not set
+CONFIG_E100=m
+CONFIG_E100_NAPI=y
+CONFIG_FEALNX=m
+CONFIG_NATSEMI=m
+CONFIG_NE2K_PCI=m
+CONFIG_8139CP=m
+CONFIG_8139TOO=m
+CONFIG_8139TOO_PIO=y
+# CONFIG_8139TOO_TUNE_TWISTER is not set
+CONFIG_8139TOO_8129=y
+# CONFIG_8139_OLD_RX_RESET is not set
+CONFIG_SIS900=m
+CONFIG_EPIC100=m
+# CONFIG_SUNDANCE is not set
+CONFIG_VIA_RHINE=m
+CONFIG_VIA_RHINE_MMIO=y
+
+#
+# Ethernet (1000 Mbit)
+#
+CONFIG_ACENIC=m
+# CONFIG_ACENIC_OMIT_TIGON_I is not set
+CONFIG_DL2K=m
+CONFIG_E1000=m
+CONFIG_E1000_NAPI=y
+CONFIG_NS83820=m
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+CONFIG_R8169=m
+CONFIG_R8169_NAPI=y
+CONFIG_SK98LIN=m
+CONFIG_VIA_VELOCITY=m
+CONFIG_TIGON3=m
+
+#
+# Ethernet (10000 Mbit)
+#
+CONFIG_IXGB=m
+CONFIG_IXGB_NAPI=y
+CONFIG_S2IO=m
+CONFIG_S2IO_NAPI=y
+
+#
+# Token Ring devices
+#
+CONFIG_TR=y
+CONFIG_IBMOL=m
+CONFIG_3C359=m
+CONFIG_TMS380TR=m
+CONFIG_TMSPCI=m
+CONFIG_ABYSS=m
+
+#
+# Wireless LAN (non-hamradio)
+#
+CONFIG_NET_RADIO=y
+
+#
+# Obsolete Wireless cards support (pre-802.11)
+#
+# CONFIG_STRIP is not set
+CONFIG_PCMCIA_WAVELAN=m
+CONFIG_PCMCIA_NETWAVE=m
+
+#
+# Wireless 802.11 Frequency Hopping cards support
+#
+# CONFIG_PCMCIA_RAYCS is not set
+
+#
+# Wireless 802.11b ISA/PCI cards support
+#
+# CONFIG_IEEE80211 is not set
+CONFIG_HERMES=m
+CONFIG_PLX_HERMES=m
+CONFIG_TMD_HERMES=m
+CONFIG_PCI_HERMES=m
+CONFIG_ATMEL=m
+CONFIG_PCI_ATMEL=m
+
+#
+# Wireless 802.11b Pcmcia/Cardbus cards support
+#
+CONFIG_PCMCIA_HERMES=m
+CONFIG_AIRO_CS=m
+CONFIG_PCMCIA_ATMEL=m
+CONFIG_PCMCIA_WL3501=m
+
+#
+# Prism GT/Duette 802.11(a/b/g) PCI/Cardbus support
+#
+CONFIG_PRISM54=m
+CONFIG_NET_WIRELESS=y
+
+#
+# PCMCIA network device support
+#
+CONFIG_NET_PCMCIA=y
+CONFIG_PCMCIA_3C589=m
+CONFIG_PCMCIA_3C574=m
+CONFIG_PCMCIA_FMVJ18X=m
+CONFIG_PCMCIA_PCNET=m
+CONFIG_PCMCIA_NMCLAN=m
+CONFIG_PCMCIA_SMC91C92=m
+CONFIG_PCMCIA_XIRC2PS=m
+CONFIG_PCMCIA_AXNET=m
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+
+#
+# ATM drivers
+#
+CONFIG_ATM_TCP=m
+CONFIG_ATM_LANAI=m
+CONFIG_ATM_ENI=m
+# CONFIG_ATM_ENI_DEBUG is not set
+# CONFIG_ATM_ENI_TUNE_BURST is not set
+CONFIG_ATM_FIRESTREAM=m
+# CONFIG_ATM_ZATM is not set
+CONFIG_ATM_IDT77252=m
+# CONFIG_ATM_IDT77252_DEBUG is not set
+# CONFIG_ATM_IDT77252_RCV_ALL is not set
+CONFIG_ATM_IDT77252_USE_SUNI=y
+CONFIG_ATM_AMBASSADOR=m
+# CONFIG_ATM_AMBASSADOR_DEBUG is not set
+CONFIG_ATM_HORIZON=m
+# CONFIG_ATM_HORIZON_DEBUG is not set
+CONFIG_ATM_FORE200E_MAYBE=m
+# CONFIG_ATM_FORE200E_PCA is not set
+CONFIG_ATM_HE=m
+# CONFIG_ATM_HE_USE_SUNI is not set
+CONFIG_FDDI=y
+# CONFIG_DEFXX is not set
+# CONFIG_SKFP is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PLIP is not set
+CONFIG_PPP=m
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_ASYNC=m
+CONFIG_PPP_SYNC_TTY=m
+CONFIG_PPP_DEFLATE=m
+# CONFIG_PPP_BSDCOMP is not set
+CONFIG_PPPOE=m
+CONFIG_PPPOATM=m
+# CONFIG_SLIP is not set
+CONFIG_NET_FC=y
+# CONFIG_SHAPER is not set
+CONFIG_NETCONSOLE=m
+CONFIG_NETDUMP=m
+
+#
+# ISDN subsystem
+#
+CONFIG_ISDN=m
+
+#
+# Old ISDN4Linux
+#
+CONFIG_ISDN_I4L=m
+CONFIG_ISDN_PPP=y
+CONFIG_ISDN_PPP_VJ=y
+CONFIG_ISDN_MPP=y
+CONFIG_IPPP_FILTER=y
+# CONFIG_ISDN_PPP_BSDCOMP is not set
+CONFIG_ISDN_AUDIO=y
+CONFIG_ISDN_TTY_FAX=y
+
+#
+# ISDN feature submodules
+#
+
+#
+# ISDN4Linux hardware drivers
+#
+
+#
+# Passive cards
+#
+CONFIG_ISDN_DRV_HISAX=m
+
+#
+# D-channel protocol features
+#
+CONFIG_HISAX_EURO=y
+CONFIG_DE_AOC=y
+CONFIG_HISAX_NO_SENDCOMPLETE=y
+CONFIG_HISAX_NO_LLC=y
+CONFIG_HISAX_NO_KEYPAD=y
+CONFIG_HISAX_1TR6=y
+CONFIG_HISAX_NI1=y
+CONFIG_HISAX_MAX_CARDS=8
+
+#
+# HiSax supported cards
+#
+CONFIG_HISAX_16_3=y
+CONFIG_HISAX_TELESPCI=y
+CONFIG_HISAX_S0BOX=y
+CONFIG_HISAX_FRITZPCI=y
+CONFIG_HISAX_AVM_A1_PCMCIA=y
+CONFIG_HISAX_ELSA=y
+CONFIG_HISAX_DIEHLDIVA=y
+CONFIG_HISAX_SEDLBAUER=y
+CONFIG_HISAX_NETJET=y
+CONFIG_HISAX_NETJET_U=y
+CONFIG_HISAX_NICCY=y
+CONFIG_HISAX_BKM_A4T=y
+CONFIG_HISAX_SCT_QUADRO=y
+CONFIG_HISAX_GAZEL=y
+CONFIG_HISAX_HFC_PCI=y
+CONFIG_HISAX_W6692=y
+CONFIG_HISAX_HFC_SX=y
+CONFIG_HISAX_ENTERNOW_PCI=y
+# CONFIG_HISAX_DEBUG is not set
+
+#
+# HiSax PCMCIA card service modules
+#
+CONFIG_HISAX_SEDLBAUER_CS=m
+CONFIG_HISAX_ELSA_CS=m
+CONFIG_HISAX_AVM_A1_CS=m
+CONFIG_HISAX_TELES_CS=m
+
+#
+# HiSax sub driver modules
+#
+CONFIG_HISAX_ST5481=m
+CONFIG_HISAX_HFCUSB=m
+CONFIG_HISAX_FRITZ_PCIPNP=m
+CONFIG_HISAX_HDLC=y
+
+#
+# Active cards
+#
+CONFIG_ISDN_DRV_TPAM=m
+
+#
+# CAPI subsystem
+#
+CONFIG_ISDN_CAPI=m
+CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON=y
+CONFIG_ISDN_CAPI_MIDDLEWARE=y
+CONFIG_ISDN_CAPI_CAPI20=m
+CONFIG_ISDN_CAPI_CAPIFS_BOOL=y
+CONFIG_ISDN_CAPI_CAPIFS=m
+CONFIG_ISDN_CAPI_CAPIDRV=m
+
+#
+# CAPI hardware drivers
+#
+
+#
+# Active AVM cards
+#
+CONFIG_CAPI_AVM=y
+
+#
+# Active Eicon DIVA Server cards
+#
+# CONFIG_CAPI_EICON is not set
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+CONFIG_INPUT_JOYDEV=m
+# CONFIG_INPUT_TSDEV is not set
+CONFIG_INPUT_EVDEV=y
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input I/O drivers
+#
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+CONFIG_SERIO=y
+CONFIG_SERIO_I8042=y
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_CT82C710 is not set
+# CONFIG_SERIO_PARKBD is not set
+# CONFIG_SERIO_PCIPS2 is not set
+# CONFIG_SERIO_RAW is not set
+
+#
+# Input Device Drivers
+#
+CONFIG_INPUT_KEYBOARD=y
+CONFIG_KEYBOARD_ATKBD=y
+# CONFIG_KEYBOARD_SUNKBD is not set
+# CONFIG_KEYBOARD_LKKBD is not set
+# CONFIG_KEYBOARD_XTKBD is not set
+# CONFIG_KEYBOARD_NEWTON is not set
+CONFIG_INPUT_MOUSE=y
+CONFIG_MOUSE_PS2=y
+CONFIG_MOUSE_SERIAL=m
+CONFIG_MOUSE_VSXXXAA=m
+CONFIG_INPUT_JOYSTICK=y
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_GUNZE=m
+CONFIG_INPUT_MISC=y
+CONFIG_INPUT_UINPUT=m
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+CONFIG_SERIAL_NONSTANDARD=y
+# CONFIG_ROCKETPORT is not set
+# CONFIG_CYCLADES is not set
+# CONFIG_SYNCLINK is not set
+# CONFIG_SYNCLINKMP is not set
+CONFIG_N_HDLC=m
+CONFIG_STALDRV=y
+CONFIG_SGI_SNSC=y
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_CS=m
+CONFIG_SERIAL_8250_ACPI=y
+CONFIG_SERIAL_8250_NR_UARTS=20
+CONFIG_SERIAL_8250_EXTENDED=y
+CONFIG_SERIAL_8250_SHARE_IRQ=y
+CONFIG_SERIAL_8250_DETECT_IRQ=y
+CONFIG_SERIAL_8250_MULTIPORT=y
+CONFIG_SERIAL_8250_RSA=y
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_SERIAL_SGI_L1_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+# CONFIG_LEGACY_PTYS is not set
+# CONFIG_CRASH is not set
+CONFIG_PRINTER=m
+CONFIG_LP_CONSOLE=y
+CONFIG_PPDEV=m
+# CONFIG_TIPAR is not set
+
+#
+# IPMI
+#
+CONFIG_IPMI_HANDLER=m
+# CONFIG_IPMI_PANIC_EVENT is not set
+CONFIG_IPMI_DEVICE_INTERFACE=m
+CONFIG_IPMI_SI=m
+CONFIG_IPMI_WATCHDOG=m
+CONFIG_IPMI_POWEROFF=m
+
+#
+# Watchdog Cards
+#
+CONFIG_WATCHDOG=y
+# CONFIG_WATCHDOG_NOWAYOUT is not set
+
+#
+# Watchdog Device Drivers
+#
+CONFIG_SOFT_WATCHDOG=m
+CONFIG_I8XX_TCO=m
+
+#
+# PCI-based Watchdog Cards
+#
+CONFIG_PCIPCWATCHDOG=m
+CONFIG_WDTPCI=m
+CONFIG_WDT_501_PCI=y
+
+#
+# USB-based Watchdog Cards
+#
+CONFIG_USBPCWATCHDOG=m
+# CONFIG_HW_RANDOM is not set
+CONFIG_EFI_RTC=y
+CONFIG_DTLK=m
+# CONFIG_R3964 is not set
+# CONFIG_APPLICOM is not set
+
+#
+# Ftape, the floppy tape device driver
+#
+CONFIG_AGP=y
+CONFIG_AGP_I460=y
+CONFIG_AGP_HP_ZX1=y
+CONFIG_DRM=y
+# CONFIG_DRM_TDFX is not set
+CONFIG_DRM_R128=m
+CONFIG_DRM_RADEON=m
+CONFIG_DRM_MGA=m
+# CONFIG_DRM_SIS is not set
+
+#
+# PCMCIA character devices
+#
+# CONFIG_SYNCLINK_CS is not set
+CONFIG_RAW_DRIVER=y
+# CONFIG_HPET is not set
+CONFIG_MAX_RAW_DEVS=8192
+# CONFIG_MMTIMER is not set
+
+#
+# I2C support
+#
+CONFIG_I2C=m
+CONFIG_I2C_CHARDEV=m
+
+#
+# I2C Algorithms
+#
+CONFIG_I2C_ALGOBIT=m
+CONFIG_I2C_ALGOPCF=m
+CONFIG_I2C_ALGOPCA=m
+
+#
+# I2C Hardware Bus support
+#
+CONFIG_I2C_ALI1535=m
+CONFIG_I2C_ALI1563=m
+CONFIG_I2C_ALI15X3=m
+CONFIG_I2C_AMD756=m
+CONFIG_I2C_AMD8111=m
+CONFIG_I2C_I801=m
+CONFIG_I2C_I810=m
+CONFIG_I2C_ISA=m
+CONFIG_I2C_NFORCE2=m
+# CONFIG_I2C_PARPORT is not set
+# CONFIG_I2C_PARPORT_LIGHT is not set
+CONFIG_I2C_PROSAVAGE=m
+CONFIG_I2C_SAVAGE4=m
+# CONFIG_SCx200_ACB is not set
+CONFIG_I2C_SIS5595=m
+CONFIG_I2C_SIS630=m
+CONFIG_I2C_SIS96X=m
+CONFIG_I2C_VIA=m
+CONFIG_I2C_VIAPRO=m
+CONFIG_I2C_VOODOO3=m
+# CONFIG_I2C_PCA_ISA is not set
+
+#
+# Hardware Sensors Chip support
+#
+CONFIG_I2C_SENSOR=m
+CONFIG_SENSORS_ADM1021=m
+CONFIG_SENSORS_ADM1025=m
+CONFIG_SENSORS_ADM1031=m
+CONFIG_SENSORS_ASB100=m
+CONFIG_SENSORS_DS1621=m
+CONFIG_SENSORS_FSCHER=m
+CONFIG_SENSORS_GL518SM=m
+CONFIG_SENSORS_IT87=m
+CONFIG_SENSORS_LM75=m
+CONFIG_SENSORS_LM77=m
+CONFIG_SENSORS_LM78=m
+CONFIG_SENSORS_LM80=m
+CONFIG_SENSORS_LM83=m
+CONFIG_SENSORS_LM85=m
+CONFIG_SENSORS_LM90=m
+CONFIG_SENSORS_MAX1619=m
+CONFIG_SENSORS_SMSC47M1=m
+CONFIG_SENSORS_VIA686A=m
+CONFIG_SENSORS_W83781D=m
+CONFIG_SENSORS_W83L785TS=m
+CONFIG_SENSORS_W83627HF=m
+
+#
+# Other I2C Chip support
+#
+CONFIG_SENSORS_EEPROM=m
+CONFIG_SENSORS_PCF8574=m
+CONFIG_SENSORS_PCF8591=m
+CONFIG_SENSORS_RTC8564=m
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_ALGO is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
+#
+# Misc devices
+#
+
+#
+# Multimedia devices
+#
+CONFIG_VIDEO_DEV=m
+
+#
+# Video For Linux
+#
+
+#
+# Video Adapters
+#
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_SAA5246A is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+CONFIG_VIDEO_OVCAMCHIP=m
+
+#
+# Radio Adapters
+#
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+
+#
+# Graphics support
+#
+CONFIG_FB=y
+CONFIG_FB_MODE_HELPERS=y
+CONFIG_FB_CIRRUS=m
+# CONFIG_FB_PM2 is not set
+# CONFIG_FB_CYBER2000 is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_IMSTT is not set
+CONFIG_FB_RIVA=m
+# CONFIG_FB_RIVA_I2C is not set
+# CONFIG_FB_RIVA_DEBUG is not set
+# CONFIG_FB_MATROX is not set
+# CONFIG_FB_RADEON_OLD is not set
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_ATY is not set
+# CONFIG_FB_SIS is not set
+# CONFIG_FB_NEOMAGIC is not set
+CONFIG_FB_KYRO=m
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VIRTUAL is not set
+
+#
+# Console display driver support
+#
+CONFIG_VGA_CONSOLE=y
+CONFIG_DUMMY_CONSOLE=y
+CONFIG_FRAMEBUFFER_CONSOLE=y
+# CONFIG_FONTS is not set
+CONFIG_FONT_8x8=y
+CONFIG_FONT_8x16=y
+
+#
+# Logo configuration
+#
+CONFIG_LOGO=y
+# CONFIG_LOGO_LINUX_MONO is not set
+# CONFIG_LOGO_LINUX_VGA16 is not set
+CONFIG_LOGO_LINUX_CLUT224=y
+
+#
+# Sound
+#
+CONFIG_SOUND=m
+
+#
+# Advanced Linux Sound Architecture
+#
+CONFIG_SND=m
+CONFIG_SND_TIMER=m
+CONFIG_SND_PCM=m
+CONFIG_SND_HWDEP=m
+CONFIG_SND_RAWMIDI=m
+CONFIG_SND_SEQUENCER=m
+CONFIG_SND_SEQ_DUMMY=m
+CONFIG_SND_OSSEMUL=y
+CONFIG_SND_MIXER_OSS=m
+CONFIG_SND_PCM_OSS=m
+CONFIG_SND_SEQUENCER_OSS=y
+# CONFIG_SND_VERBOSE_PRINTK is not set
+# CONFIG_SND_DEBUG is not set
+
+#
+# Generic devices
+#
+CONFIG_SND_MPU401_UART=m
+CONFIG_SND_OPL3_LIB=m
+CONFIG_SND_VX_LIB=m
+CONFIG_SND_DUMMY=m
+CONFIG_SND_VIRMIDI=m
+CONFIG_SND_MTPAV=m
+# CONFIG_SND_SERIAL_U16550 is not set
+CONFIG_SND_MPU401=m
+
+#
+# PCI devices
+#
+CONFIG_SND_AC97_CODEC=m
+CONFIG_SND_ALI5451=m
+CONFIG_SND_ATIIXP=m
+CONFIG_SND_ATIIXP_MODEM=m
+CONFIG_SND_AU8810=m
+CONFIG_SND_AU8820=m
+CONFIG_SND_AU8830=m
+CONFIG_SND_AZT3328=m
+CONFIG_SND_BT87X=m
+CONFIG_SND_CS46XX=m
+CONFIG_SND_CS46XX_NEW_DSP=y
+CONFIG_SND_CS4281=m
+CONFIG_SND_EMU10K1=m
+CONFIG_SND_KORG1212=m
+CONFIG_SND_MIXART=m
+CONFIG_SND_NM256=m
+CONFIG_SND_RME32=m
+CONFIG_SND_RME96=m
+CONFIG_SND_RME9652=m
+CONFIG_SND_HDSP=m
+CONFIG_SND_TRIDENT=m
+CONFIG_SND_YMFPCI=m
+CONFIG_SND_ALS4000=m
+CONFIG_SND_CMIPCI=m
+CONFIG_SND_ENS1370=m
+CONFIG_SND_ENS1371=m
+CONFIG_SND_ES1938=m
+CONFIG_SND_ES1968=m
+CONFIG_SND_MAESTRO3=m
+CONFIG_SND_FM801=m
+CONFIG_SND_FM801_TEA575X=m
+CONFIG_SND_ICE1712=m
+CONFIG_SND_ICE1724=m
+CONFIG_SND_INTEL8X0=m
+CONFIG_SND_INTEL8X0M=m
+CONFIG_SND_SONICVIBES=m
+CONFIG_SND_VIA82XX=m
+CONFIG_SND_VX222=m
+
+#
+# ALSA USB devices
+#
+CONFIG_SND_USB_AUDIO=m
+CONFIG_SND_USB_USX2Y=m
+
+#
+# PCMCIA devices
+#
+
+#
+# Open Sound System
+#
+# CONFIG_SOUND_PRIME is not set
+
+#
+# USB support
+#
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+CONFIG_USB_DEVICEFS=y
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+CONFIG_USB_SUSPEND=y
+# CONFIG_USB_OTG is not set
+
+#
+# USB Host Controller Drivers
+#
+CONFIG_USB_EHCI_HCD=m
+CONFIG_USB_EHCI_SPLIT_ISO=y
+CONFIG_USB_EHCI_ROOT_HUB_TT=y
+CONFIG_USB_OHCI_HCD=m
+CONFIG_USB_UHCI_HCD=m
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_AUDIO is not set
+
+#
+# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem
+#
+CONFIG_USB_MIDI=m
+CONFIG_USB_ACM=m
+CONFIG_USB_PRINTER=m
+CONFIG_USB_STORAGE=m
+# CONFIG_USB_STORAGE_DEBUG is not set
+CONFIG_USB_STORAGE_RW_DETECT=y
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_DPCM=y
+CONFIG_USB_STORAGE_HP8200e=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+
+#
+# USB Human Interface Devices (HID)
+#
+CONFIG_USB_HID=y
+CONFIG_USB_HIDINPUT=y
+CONFIG_HID_FF=y
+CONFIG_HID_PID=y
+CONFIG_LOGITECH_FF=y
+CONFIG_THRUSTMASTER_FF=y
+CONFIG_USB_HIDDEV=y
+CONFIG_USB_AIPTEK=m
+CONFIG_USB_WACOM=m
+CONFIG_USB_KBTAB=m
+CONFIG_USB_POWERMATE=m
+CONFIG_USB_MTOUCH=m
+CONFIG_USB_EGALAX=m
+CONFIG_USB_XPAD=m
+CONFIG_USB_ATI_REMOTE=m
+
+#
+# USB Imaging devices
+#
+CONFIG_USB_MDC800=m
+CONFIG_USB_MICROTEK=m
+CONFIG_USB_HPUSBSCSI=m
+
+#
+# USB Multimedia devices
+#
+CONFIG_USB_DABUSB=m
+CONFIG_USB_VICAM=m
+CONFIG_USB_DSBR=m
+CONFIG_USB_IBMCAM=m
+CONFIG_USB_KONICAWC=m
+CONFIG_USB_OV511=m
+CONFIG_USB_SE401=m
+CONFIG_USB_SN9C102=m
+CONFIG_USB_STV680=m
+CONFIG_USB_W9968CF=m
+CONFIG_USB_PWC=m
+
+#
+# USB Network adaptors
+#
+CONFIG_USB_CATC=m
+CONFIG_USB_KAWETH=m
+CONFIG_USB_PEGASUS=m
+CONFIG_USB_RTL8150=m
+CONFIG_USB_USBNET=m
+
+#
+# USB Host-to-Host Cables
+#
+CONFIG_USB_ALI_M5632=y
+CONFIG_USB_AN2720=y
+CONFIG_USB_BELKIN=y
+CONFIG_USB_GENESYS=y
+CONFIG_USB_NET1080=y
+CONFIG_USB_PL2301=y
+
+#
+# Intelligent USB Devices/Gadgets
+#
+CONFIG_USB_ARMLINUX=y
+CONFIG_USB_EPSON2888=y
+CONFIG_USB_ZAURUS=y
+CONFIG_USB_CDCETHER=y
+
+#
+# USB Network Adapters
+#
+CONFIG_USB_AX8817X=y
+
+#
+# USB port drivers
+#
+CONFIG_USB_USS720=m
+
+#
+# USB Serial Converter support
+#
+CONFIG_USB_SERIAL=m
+CONFIG_USB_SERIAL_GENERIC=y
+CONFIG_USB_SERIAL_BELKIN=m
+CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m
+CONFIG_USB_SERIAL_EMPEG=m
+CONFIG_USB_SERIAL_FTDI_SIO=m
+CONFIG_USB_SERIAL_VISOR=m
+CONFIG_USB_SERIAL_IPAQ=m
+CONFIG_USB_SERIAL_IR=m
+CONFIG_USB_SERIAL_EDGEPORT=m
+CONFIG_USB_SERIAL_EDGEPORT_TI=m
+CONFIG_USB_SERIAL_KEYSPAN_PDA=m
+CONFIG_USB_SERIAL_KEYSPAN=m
+CONFIG_USB_SERIAL_KEYSPAN_MPR=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XA=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XB=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19=y
+CONFIG_USB_SERIAL_KEYSPAN_USA18X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QW=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QI=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y
+CONFIG_USB_SERIAL_KLSI=m
+CONFIG_USB_SERIAL_KOBIL_SCT=m
+CONFIG_USB_SERIAL_MCT_U232=m
+CONFIG_USB_SERIAL_PL2303=m
+CONFIG_USB_SERIAL_SAFE=m
+CONFIG_USB_SERIAL_SAFE_PADDED=y
+CONFIG_USB_SERIAL_CYBERJACK=m
+CONFIG_USB_SERIAL_XIRCOM=m
+CONFIG_USB_SERIAL_OMNINET=m
+CONFIG_USB_EZUSB=y
+
+#
+# USB Miscellaneous drivers
+#
+CONFIG_USB_EMI62=m
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_TIGL is not set
+CONFIG_USB_AUERSWALD=m
+CONFIG_USB_RIO500=m
+CONFIG_USB_LEGOTOWER=m
+CONFIG_USB_LCD=m
+CONFIG_USB_LED=m
+# CONFIG_USB_CYTHERM is not set
+CONFIG_USB_PHIDGETSERVO=m
+CONFIG_USB_TEST=m
+
+#
+# USB ATM/DSL drivers
+#
+CONFIG_USB_ATM=m
+CONFIG_USB_SPEEDTOUCH=m
+
+#
+# USB Gadget Support
+#
+# CONFIG_USB_GADGET is not set
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT2_FS_POSIX_ACL=y
+CONFIG_EXT2_FS_SECURITY=y
+CONFIG_EXT3_FS=m
+CONFIG_EXT3_FS_XATTR=y
+CONFIG_EXT3_FS_POSIX_ACL=y
+CONFIG_EXT3_FS_SECURITY=y
+CONFIG_JBD=m
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_JFS_FS is not set
+CONFIG_FS_POSIX_ACL=y
+# CONFIG_XFS_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_QUOTA=y
+# CONFIG_QFMT_V1 is not set
+CONFIG_QFMT_V2=y
+CONFIG_QUOTACTL=y
+# CONFIG_AUTOFS_FS is not set
+CONFIG_AUTOFS4_FS=m
+
+#
+# CD-ROM/DVD Filesystems
+#
+CONFIG_ISO9660_FS=y
+CONFIG_JOLIET=y
+CONFIG_ZISOFS=y
+CONFIG_ZISOFS_FS=y
+CONFIG_UDF_FS=m
+CONFIG_UDF_NLS=y
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=m
+CONFIG_MSDOS_FS=m
+CONFIG_VFAT_FS=m
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="ascii"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+CONFIG_SYSFS=y
+# CONFIG_DEVFS_FS is not set
+CONFIG_DEVPTS_FS_XATTR=y
+CONFIG_DEVPTS_FS_SECURITY=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_XATTR=y
+CONFIG_TMPFS_SECURITY=y
+CONFIG_HUGETLBFS=y
+CONFIG_HUGETLB_PAGE=y
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not set
+# CONFIG_AFFS_FS is not set
+CONFIG_HFS_FS=m
+CONFIG_HFSPLUS_FS=m
+# CONFIG_BEFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+CONFIG_CRAMFS=m
+CONFIG_VXFS_FS=m
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=m
+CONFIG_NFS_V3=y
+CONFIG_NFS_V4=y
+CONFIG_NFS_DIRECTIO=y
+CONFIG_NFSD=m
+CONFIG_NFSD_V3=y
+CONFIG_NFSD_V4=y
+CONFIG_NFSD_TCP=y
+CONFIG_LOCKD=m
+CONFIG_LOCKD_V4=y
+CONFIG_EXPORTFS=m
+CONFIG_SUNRPC=m
+CONFIG_SUNRPC_GSS=m
+CONFIG_RPCSEC_GSS_KRB5=m
+CONFIG_RPCSEC_GSS_SPKM3=m
+CONFIG_SMB_FS=m
+# CONFIG_SMB_NLS_DEFAULT is not set
+CONFIG_CIFS=m
+# CONFIG_CIFS_STATS is not set
+CONFIG_CIFS_XATTR=y
+CONFIG_CIFS_POSIX=y
+# CONFIG_NCP_FS is not set
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_ACORN_PARTITION is not set
+CONFIG_OSF_PARTITION=y
+# CONFIG_AMIGA_PARTITION is not set
+# CONFIG_ATARI_PARTITION is not set
+CONFIG_MAC_PARTITION=y
+CONFIG_MSDOS_PARTITION=y
+CONFIG_BSD_DISKLABEL=y
+CONFIG_MINIX_SUBPARTITION=y
+CONFIG_SOLARIS_X86_PARTITION=y
+CONFIG_UNIXWARE_DISKLABEL=y
+# CONFIG_LDM_PARTITION is not set
+CONFIG_SGI_PARTITION=y
+# CONFIG_ULTRIX_PARTITION is not set
+CONFIG_SUN_PARTITION=y
+CONFIG_EFI_PARTITION=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS=y
+CONFIG_NLS_DEFAULT="utf8"
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_CODEPAGE_737=m
+CONFIG_NLS_CODEPAGE_775=m
+CONFIG_NLS_CODEPAGE_850=m
+CONFIG_NLS_CODEPAGE_852=m
+CONFIG_NLS_CODEPAGE_855=m
+CONFIG_NLS_CODEPAGE_857=m
+CONFIG_NLS_CODEPAGE_860=m
+CONFIG_NLS_CODEPAGE_861=m
+CONFIG_NLS_CODEPAGE_862=m
+CONFIG_NLS_CODEPAGE_863=m
+CONFIG_NLS_CODEPAGE_864=m
+CONFIG_NLS_CODEPAGE_865=m
+CONFIG_NLS_CODEPAGE_866=m
+CONFIG_NLS_CODEPAGE_869=m
+CONFIG_NLS_CODEPAGE_936=m
+CONFIG_NLS_CODEPAGE_950=m
+CONFIG_NLS_CODEPAGE_932=m
+CONFIG_NLS_CODEPAGE_949=m
+CONFIG_NLS_CODEPAGE_874=m
+CONFIG_NLS_ISO8859_8=m
+CONFIG_NLS_CODEPAGE_1250=m
+CONFIG_NLS_CODEPAGE_1251=m
+CONFIG_NLS_ASCII=y
+CONFIG_NLS_ISO8859_1=m
+CONFIG_NLS_ISO8859_2=m
+CONFIG_NLS_ISO8859_3=m
+CONFIG_NLS_ISO8859_4=m
+CONFIG_NLS_ISO8859_5=m
+CONFIG_NLS_ISO8859_6=m
+CONFIG_NLS_ISO8859_7=m
+CONFIG_NLS_ISO8859_9=m
+CONFIG_NLS_ISO8859_13=m
+CONFIG_NLS_ISO8859_14=m
+CONFIG_NLS_ISO8859_15=m
+CONFIG_NLS_KOI8_R=m
+CONFIG_NLS_KOI8_U=m
+CONFIG_NLS_UTF8=m
+
+#
+# Library routines
+#
+CONFIG_CRC_CCITT=m
+CONFIG_CRC32=y
+CONFIG_LIBCRC32C=m
+CONFIG_ZLIB_INFLATE=y
+CONFIG_ZLIB_DEFLATE=m
+
+#
+# HP Simulator drivers
+#
+# CONFIG_HP_SIMETH is not set
+# CONFIG_HP_SIMSERIAL is not set
+# CONFIG_HP_SIMSCSI is not set
+
+#
+# Profiling support
+#
+CONFIG_PROFILING=y
+CONFIG_OPROFILE=m
+
+#
+# Kernel hacking
+#
+CONFIG_DEBUG_KERNEL=y
+CONFIG_MAGIC_SYSRQ=y
+# CONFIG_DEBUG_SLAB is not set
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_SPINLOCK_SLEEP=y
+# CONFIG_DEBUG_INFO is not set
+CONFIG_IA64_GRANULE_16MB=y
+# CONFIG_IA64_GRANULE_64MB is not set
+# CONFIG_IA64_PRINT_HAZARDS is not set
+# CONFIG_DISABLE_VHPT is not set
+# CONFIG_IA64_DEBUG_CMPXCHG is not set
+# CONFIG_IA64_DEBUG_IRQ is not set
+
+#
+# Security options
+#
+CONFIG_SECURITY=y
+CONFIG_SECURITY_NETWORK=y
+CONFIG_SECURITY_CAPABILITIES=y
+# CONFIG_SECURITY_ROOTPLUG is not set
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM_VALUE=1
+CONFIG_SECURITY_SELINUX_DISABLE=y
+CONFIG_SECURITY_SELINUX_DEVELOP=y
+CONFIG_SECURITY_SELINUX_AVC_STATS=y
+# CONFIG_SECURITY_SELINUX_MLS is not set
+
+#
+# Cryptographic options
+#
+CONFIG_CRYPTO=y
+CONFIG_CRYPTO_HMAC=y
+CONFIG_CRYPTO_NULL=m
+CONFIG_CRYPTO_MD4=m
+CONFIG_CRYPTO_MD5=m
+CONFIG_CRYPTO_SHA1=y
+CONFIG_CRYPTO_SHA256=m
+CONFIG_CRYPTO_SHA512=m
+CONFIG_CRYPTO_WP512=m
+CONFIG_CRYPTO_DES=m
+CONFIG_CRYPTO_BLOWFISH=m
+CONFIG_CRYPTO_TWOFISH=m
+CONFIG_CRYPTO_SERPENT=m
+CONFIG_CRYPTO_AES=m
+CONFIG_CRYPTO_CAST5=m
+CONFIG_CRYPTO_CAST6=m
+CONFIG_CRYPTO_TEA=m
+CONFIG_CRYPTO_ARC4=m
+CONFIG_CRYPTO_KHAZAD=m
+CONFIG_CRYPTO_DEFLATE=m
+CONFIG_CRYPTO_MICHAEL_MIC=m
+CONFIG_CRYPTO_CRC32C=m
+# CONFIG_CRYPTO_TEST is not set
+CONFIG_CRYPTO_SIGNATURE=y
+CONFIG_CRYPTO_SIGNATURE_DSA=y
+CONFIG_CRYPTO_MPILIB=y
diff --git a/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-ia64.config b/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-ia64.config
new file mode 100644 (file)
index 0000000..611ce45
--- /dev/null
@@ -0,0 +1,1908 @@
+#
+# Automatically generated make config: don't edit
+# Linux kernel version: 2.6.9-5.0.3.EL_lustre-b1_4_rhel4.200503031449smp
+# Thu Mar  3 14:52:42 2005
+#
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_CLEAN_COMPILE=y
+
+#
+# General setup
+#
+CONFIG_LOCALVERSION=""
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+CONFIG_POSIX_MQUEUE=y
+CONFIG_BSD_PROCESS_ACCT=y
+# CONFIG_BSD_PROCESS_ACCT_V3 is not set
+CONFIG_SYSCTL=y
+CONFIG_AUDIT=y
+CONFIG_AUDITSYSCALL=y
+CONFIG_LOG_BUF_SHIFT=17
+CONFIG_HOTPLUG=y
+# CONFIG_IKCONFIG is not set
+# CONFIG_EMBEDDED is not set
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_ALL is not set
+CONFIG_KALLSYMS_EXTRA_PASS=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+CONFIG_IOSCHED_CFQ=y
+# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
+CONFIG_SHMEM=y
+# CONFIG_TINY_SHMEM is not set
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+CONFIG_MODVERSIONS=y
+CONFIG_MODULE_SIG=y
+# CONFIG_MODULE_SIG_FORCE is not set
+CONFIG_KMOD=y
+CONFIG_STOP_MACHINE=y
+
+#
+# Processor type and features
+#
+CONFIG_IA64=y
+CONFIG_64BIT=y
+CONFIG_MMU=y
+CONFIG_RWSEM_XCHGADD_ALGORITHM=y
+CONFIG_TIME_INTERPOLATION=y
+CONFIG_EFI=y
+CONFIG_GENERIC_IOMAP=y
+CONFIG_IA64_GENERIC=y
+# CONFIG_IA64_DIG is not set
+# CONFIG_IA64_HP_ZX1 is not set
+# CONFIG_IA64_SGI_SN2 is not set
+# CONFIG_IA64_HP_SIM is not set
+# CONFIG_ITANIUM is not set
+CONFIG_MCKINLEY=y
+# CONFIG_IA64_PAGE_SIZE_4KB is not set
+# CONFIG_IA64_PAGE_SIZE_8KB is not set
+CONFIG_IA64_PAGE_SIZE_16KB=y
+# CONFIG_IA64_PAGE_SIZE_64KB is not set
+CONFIG_IA64_L1_CACHE_SHIFT=7
+CONFIG_NUMA=y
+CONFIG_VIRTUAL_MEM_MAP=y
+CONFIG_DISCONTIGMEM=y
+CONFIG_IA64_CYCLONE=y
+CONFIG_IOSAPIC=y
+CONFIG_FORCE_MAX_ZONEORDER=18
+CONFIG_SMP=y
+CONFIG_NR_CPUS=64
+# CONFIG_HOTPLUG_CPU is not set
+# CONFIG_PREEMPT is not set
+CONFIG_HAVE_DEC_LOCK=y
+# CONFIG_IA32_SUPPORT is not set
+CONFIG_IA64_MCA_RECOVERY=m
+CONFIG_PERFMON=y
+CONFIG_IA64_PALINFO=y
+
+#
+# Firmware Drivers
+#
+CONFIG_EFI_VARS=y
+CONFIG_EFI_PCDP=y
+CONFIG_BINFMT_ELF=y
+CONFIG_BINFMT_MISC=y
+
+#
+# Power management and ACPI
+#
+CONFIG_PM=y
+CONFIG_ACPI=y
+
+#
+# ACPI (Advanced Configuration and Power Interface) Support
+#
+CONFIG_ACPI_BOOT=y
+CONFIG_ACPI_INTERPRETER=y
+CONFIG_ACPI_BUTTON=m
+CONFIG_ACPI_FAN=y
+CONFIG_ACPI_PROCESSOR=y
+CONFIG_ACPI_THERMAL=y
+CONFIG_ACPI_NUMA=y
+CONFIG_ACPI_BLACKLIST_YEAR=2001
+# CONFIG_ACPI_DEBUG is not set
+CONFIG_ACPI_BUS=y
+CONFIG_ACPI_POWER=y
+CONFIG_ACPI_PCI=y
+CONFIG_ACPI_SYSTEM=y
+
+#
+# Bus options (PCI, PCMCIA)
+#
+CONFIG_PCI=y
+CONFIG_PCI_DOMAINS=y
+CONFIG_PCI_MSI=y
+CONFIG_PCI_LEGACY_PROC=y
+# CONFIG_PCI_NAMES is not set
+
+#
+# PCI Hotplug Support
+#
+CONFIG_HOTPLUG_PCI=y
+# CONFIG_HOTPLUG_PCI_FAKE is not set
+CONFIG_HOTPLUG_PCI_ACPI=m
+CONFIG_HOTPLUG_PCI_ACPI_IBM=m
+# CONFIG_HOTPLUG_PCI_CPCI is not set
+CONFIG_HOTPLUG_PCI_PCIE=m
+# CONFIG_HOTPLUG_PCI_PCIE_POLL_EVENT_MODE is not set
+CONFIG_HOTPLUG_PCI_SHPC=m
+# CONFIG_HOTPLUG_PCI_SHPC_POLL_EVENT_MODE is not set
+
+#
+# PCMCIA/CardBus support
+#
+CONFIG_PCMCIA=m
+# CONFIG_PCMCIA_DEBUG is not set
+CONFIG_YENTA=m
+CONFIG_CARDBUS=y
+CONFIG_PD6729=m
+# CONFIG_I82092 is not set
+CONFIG_TCIC=m
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+CONFIG_FW_LOADER=y
+# CONFIG_DEBUG_DRIVER is not set
+
+#
+# Memory Technology Devices (MTD)
+#
+# CONFIG_MTD is not set
+
+#
+# Parallel port support
+#
+CONFIG_PARPORT=m
+CONFIG_PARPORT_PC=m
+CONFIG_PARPORT_PC_CML1=m
+CONFIG_PARPORT_SERIAL=m
+# CONFIG_PARPORT_PC_FIFO is not set
+# CONFIG_PARPORT_PC_SUPERIO is not set
+CONFIG_PARPORT_PC_PCMCIA=m
+# CONFIG_PARPORT_OTHER is not set
+CONFIG_PARPORT_1284=y
+
+#
+# Plug and Play support
+#
+
+#
+# Block devices
+#
+# CONFIG_PARIDE is not set
+CONFIG_BLK_CPQ_DA=m
+CONFIG_BLK_CPQ_CISS_DA=m
+CONFIG_CISS_SCSI_TAPE=y
+CONFIG_BLK_DEV_DAC960=m
+# CONFIG_BLK_DEV_UMEM is not set
+CONFIG_BLK_DEV_LOOP=m
+CONFIG_BLK_DEV_CRYPTOLOOP=m
+CONFIG_BLK_DEV_NBD=m
+CONFIG_BLK_DEV_SX8=m
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=16384
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_DISKDUMP=m
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_IDE_SATA is not set
+CONFIG_BLK_DEV_IDEDISK=y
+CONFIG_IDEDISK_MULTI_MODE=y
+CONFIG_BLK_DEV_IDECS=m
+CONFIG_BLK_DEV_DELKIN=m
+CONFIG_BLK_DEV_IDECD=y
+# CONFIG_BLK_DEV_IDETAPE is not set
+CONFIG_BLK_DEV_IDEFLOPPY=y
+CONFIG_BLK_DEV_IDESCSI=m
+# CONFIG_IDE_TASK_IOCTL is not set
+# CONFIG_IDE_TASKFILE_IO is not set
+
+#
+# IDE chipset support/bugfixes
+#
+CONFIG_IDE_GENERIC=y
+CONFIG_BLK_DEV_IDEPCI=y
+CONFIG_IDEPCI_SHARE_IRQ=y
+# CONFIG_BLK_DEV_OFFBOARD is not set
+CONFIG_BLK_DEV_GENERIC=y
+# CONFIG_BLK_DEV_OPTI621 is not set
+CONFIG_BLK_DEV_IDEDMA_PCI=y
+# CONFIG_BLK_DEV_IDEDMA_FORCED is not set
+CONFIG_IDEDMA_PCI_AUTO=y
+# CONFIG_IDEDMA_ONLYDISK is not set
+CONFIG_BLK_DEV_AEC62XX=y
+CONFIG_BLK_DEV_ALI15X3=y
+# CONFIG_WDC_ALI15X3 is not set
+CONFIG_BLK_DEV_AMD74XX=y
+CONFIG_BLK_DEV_CMD64X=y
+CONFIG_BLK_DEV_TRIFLEX=y
+CONFIG_BLK_DEV_CY82C693=y
+CONFIG_BLK_DEV_CS5520=y
+CONFIG_BLK_DEV_CS5530=y
+CONFIG_BLK_DEV_HPT34X=y
+# CONFIG_HPT34X_AUTODMA is not set
+CONFIG_BLK_DEV_HPT366=y
+# CONFIG_BLK_DEV_SC1200 is not set
+CONFIG_BLK_DEV_PIIX=y
+CONFIG_BLK_DEV_IT8212=y
+# CONFIG_BLK_DEV_NS87415 is not set
+CONFIG_BLK_DEV_PDC202XX_OLD=y
+# CONFIG_PDC202XX_BURST is not set
+CONFIG_BLK_DEV_PDC202XX_NEW=y
+CONFIG_PDC202XX_FORCE=y
+CONFIG_BLK_DEV_SVWKS=y
+CONFIG_BLK_DEV_SGIIOC4=m
+CONFIG_BLK_DEV_SIIMAGE=y
+CONFIG_BLK_DEV_SLC90E66=y
+# CONFIG_BLK_DEV_TRM290 is not set
+CONFIG_BLK_DEV_VIA82CXXX=y
+# CONFIG_IDE_ARM is not set
+CONFIG_BLK_DEV_IDEDMA=y
+# CONFIG_IDEDMA_IVB is not set
+CONFIG_IDEDMA_AUTO=y
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+CONFIG_SCSI=m
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=m
+CONFIG_SCSI_DUMP=m
+CONFIG_SD_IOSTATS=y
+CONFIG_CHR_DEV_ST=m
+CONFIG_CHR_DEV_OSST=m
+CONFIG_BLK_DEV_SR=m
+CONFIG_BLK_DEV_SR_VENDOR=y
+CONFIG_CHR_DEV_SG=m
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+
+#
+# SCSI Transport Attributes
+#
+CONFIG_SCSI_SPI_ATTRS=m
+CONFIG_SCSI_FC_ATTRS=m
+
+#
+# SCSI low-level drivers
+#
+CONFIG_BLK_DEV_3W_XXXX_RAID=m
+CONFIG_SCSI_3W_9XXX=m
+CONFIG_SCSI_ACARD=m
+CONFIG_SCSI_AACRAID=m
+CONFIG_SCSI_AIC7XXX=m
+CONFIG_AIC7XXX_CMDS_PER_DEVICE=4
+CONFIG_AIC7XXX_RESET_DELAY_MS=15000
+# CONFIG_AIC7XXX_DEBUG_ENABLE is not set
+CONFIG_AIC7XXX_DEBUG_MASK=0
+# CONFIG_AIC7XXX_REG_PRETTY_PRINT is not set
+CONFIG_SCSI_AIC7XXX_OLD=m
+CONFIG_SCSI_AIC79XX=m
+CONFIG_AIC79XX_CMDS_PER_DEVICE=4
+CONFIG_AIC79XX_RESET_DELAY_MS=15000
+# CONFIG_AIC79XX_ENABLE_RD_STRM is not set
+# CONFIG_AIC79XX_DEBUG_ENABLE is not set
+CONFIG_AIC79XX_DEBUG_MASK=0
+# CONFIG_AIC79XX_REG_PRETTY_PRINT is not set
+CONFIG_MEGARAID_NEWGEN=y
+CONFIG_MEGARAID_MM=m
+CONFIG_MEGARAID_MAILBOX=m
+CONFIG_SCSI_SATA=y
+CONFIG_SCSI_SATA_AHCI=m
+CONFIG_SCSI_SATA_SVW=m
+CONFIG_SCSI_ATA_PIIX=m
+CONFIG_SCSI_SATA_NV=m
+CONFIG_SCSI_SATA_PROMISE=m
+CONFIG_SCSI_SATA_SX4=m
+CONFIG_SCSI_SATA_SIL=m
+CONFIG_SCSI_SATA_SIS=m
+CONFIG_SCSI_SATA_VIA=m
+CONFIG_SCSI_SATA_VITESSE=m
+# CONFIG_SCSI_BUSLOGIC is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_EATA is not set
+# CONFIG_SCSI_EATA_PIO is not set
+CONFIG_SCSI_LPFC=m
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+CONFIG_SCSI_GDTH=m
+CONFIG_SCSI_IPS=m
+CONFIG_SCSI_INITIO=m
+# CONFIG_SCSI_INIA100 is not set
+CONFIG_SCSI_PPA=m
+CONFIG_SCSI_IMM=m
+# CONFIG_SCSI_IZIP_EPP16 is not set
+# CONFIG_SCSI_IZIP_SLOW_CTR is not set
+CONFIG_SCSI_SYM53C8XX_2=m
+CONFIG_SCSI_SYM53C8XX_DMA_ADDRESSING_MODE=1
+CONFIG_SCSI_SYM53C8XX_DEFAULT_TAGS=16
+CONFIG_SCSI_SYM53C8XX_MAX_TAGS=64
+# CONFIG_SCSI_SYM53C8XX_IOMAPPED is not set
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_SCSI_QLOGIC_FC is not set
+CONFIG_SCSI_QLOGIC_1280=m
+CONFIG_SCSI_QLA2XXX=m
+CONFIG_SCSI_QLA21XX=m
+CONFIG_SCSI_QLA22XX=m
+CONFIG_SCSI_QLA2300=m
+CONFIG_SCSI_QLA2322=m
+CONFIG_SCSI_QLA6312=m
+CONFIG_SCSI_QLA6322=m
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_DC390T is not set
+# CONFIG_SCSI_DEBUG is not set
+
+#
+# PCMCIA SCSI adapter support
+#
+# CONFIG_PCMCIA_FDOMAIN is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+CONFIG_MD=y
+CONFIG_BLK_DEV_MD=y
+CONFIG_MD_LINEAR=m
+CONFIG_MD_RAID0=m
+CONFIG_MD_RAID1=m
+CONFIG_MD_RAID10=m
+CONFIG_MD_RAID5=m
+CONFIG_MD_RAID6=m
+CONFIG_MD_MULTIPATH=m
+CONFIG_BLK_DEV_DM=m
+CONFIG_DM_CRYPT=m
+CONFIG_DM_SNAPSHOT=m
+CONFIG_DM_MIRROR=m
+CONFIG_DM_ZERO=m
+
+#
+# Fusion MPT device support
+#
+CONFIG_FUSION=m
+CONFIG_FUSION_MAX_SGE=40
+CONFIG_FUSION_CTL=m
+CONFIG_FUSION_LAN=m
+
+#
+# IEEE 1394 (FireWire) support
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# I2O device support
+#
+# CONFIG_I2O is not set
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+CONFIG_PACKET=y
+CONFIG_PACKET_MMAP=y
+CONFIG_NETLINK_DEV=y
+CONFIG_UNIX=y
+CONFIG_NET_KEY=m
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_FWMARK=y
+CONFIG_IP_ROUTE_MULTIPATH=y
+CONFIG_IP_ROUTE_VERBOSE=y
+# CONFIG_IP_PNP is not set
+CONFIG_NET_IPIP=m
+CONFIG_NET_IPGRE=m
+CONFIG_NET_IPGRE_BROADCAST=y
+CONFIG_IP_MROUTE=y
+CONFIG_IP_PIMSM_V1=y
+CONFIG_IP_PIMSM_V2=y
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+CONFIG_INET_AH=m
+CONFIG_INET_ESP=m
+CONFIG_INET_IPCOMP=m
+CONFIG_INET_TUNNEL=m
+
+#
+# IP: Virtual Server Configuration
+#
+CONFIG_IP_VS=m
+# CONFIG_IP_VS_DEBUG is not set
+CONFIG_IP_VS_TAB_BITS=12
+
+#
+# IPVS transport protocol load balancing support
+#
+CONFIG_IP_VS_PROTO_TCP=y
+CONFIG_IP_VS_PROTO_UDP=y
+CONFIG_IP_VS_PROTO_ESP=y
+CONFIG_IP_VS_PROTO_AH=y
+
+#
+# IPVS scheduler
+#
+CONFIG_IP_VS_RR=m
+CONFIG_IP_VS_WRR=m
+CONFIG_IP_VS_LC=m
+CONFIG_IP_VS_WLC=m
+CONFIG_IP_VS_LBLC=m
+CONFIG_IP_VS_LBLCR=m
+CONFIG_IP_VS_DH=m
+CONFIG_IP_VS_SH=m
+CONFIG_IP_VS_SED=m
+CONFIG_IP_VS_NQ=m
+
+#
+# IPVS application helper
+#
+CONFIG_IP_VS_FTP=m
+CONFIG_IPV6=m
+CONFIG_IPV6_PRIVACY=y
+CONFIG_INET6_AH=m
+CONFIG_INET6_ESP=m
+CONFIG_INET6_IPCOMP=m
+CONFIG_INET6_TUNNEL=m
+CONFIG_IPV6_TUNNEL=m
+CONFIG_NETFILTER=y
+# CONFIG_NETFILTER_DEBUG is not set
+CONFIG_BRIDGE_NETFILTER=y
+
+#
+# IP: Netfilter Configuration
+#
+CONFIG_IP_NF_CONNTRACK=m
+CONFIG_IP_NF_CT_ACCT=y
+CONFIG_IP_NF_CT_PROTO_SCTP=m
+CONFIG_IP_NF_FTP=m
+CONFIG_IP_NF_IRC=m
+CONFIG_IP_NF_TFTP=m
+CONFIG_IP_NF_AMANDA=m
+CONFIG_IP_NF_QUEUE=m
+CONFIG_IP_NF_IPTABLES=m
+CONFIG_IP_NF_MATCH_LIMIT=m
+CONFIG_IP_NF_MATCH_IPRANGE=m
+CONFIG_IP_NF_MATCH_MAC=m
+CONFIG_IP_NF_MATCH_PKTTYPE=m
+CONFIG_IP_NF_MATCH_MARK=m
+CONFIG_IP_NF_MATCH_MULTIPORT=m
+CONFIG_IP_NF_MATCH_TOS=m
+CONFIG_IP_NF_MATCH_RECENT=m
+CONFIG_IP_NF_MATCH_ECN=m
+CONFIG_IP_NF_MATCH_DSCP=m
+CONFIG_IP_NF_MATCH_AH_ESP=m
+CONFIG_IP_NF_MATCH_LENGTH=m
+CONFIG_IP_NF_MATCH_TTL=m
+CONFIG_IP_NF_MATCH_TCPMSS=m
+CONFIG_IP_NF_MATCH_HELPER=m
+CONFIG_IP_NF_MATCH_STATE=m
+CONFIG_IP_NF_MATCH_CONNTRACK=m
+CONFIG_IP_NF_MATCH_OWNER=m
+CONFIG_IP_NF_MATCH_PHYSDEV=m
+CONFIG_IP_NF_MATCH_ADDRTYPE=m
+CONFIG_IP_NF_MATCH_REALM=m
+CONFIG_IP_NF_MATCH_SCTP=m
+CONFIG_IP_NF_MATCH_COMMENT=m
+CONFIG_IP_NF_FILTER=m
+CONFIG_IP_NF_TARGET_REJECT=m
+CONFIG_IP_NF_TARGET_LOG=m
+CONFIG_IP_NF_TARGET_ULOG=m
+CONFIG_IP_NF_TARGET_TCPMSS=m
+CONFIG_IP_NF_NAT=m
+CONFIG_IP_NF_NAT_NEEDED=y
+CONFIG_IP_NF_TARGET_MASQUERADE=m
+CONFIG_IP_NF_TARGET_REDIRECT=m
+CONFIG_IP_NF_TARGET_NETMAP=m
+CONFIG_IP_NF_TARGET_SAME=m
+CONFIG_IP_NF_NAT_LOCAL=y
+CONFIG_IP_NF_NAT_SNMP_BASIC=m
+CONFIG_IP_NF_NAT_IRC=m
+CONFIG_IP_NF_NAT_FTP=m
+CONFIG_IP_NF_NAT_TFTP=m
+CONFIG_IP_NF_NAT_AMANDA=m
+CONFIG_IP_NF_MANGLE=m
+CONFIG_IP_NF_TARGET_TOS=m
+CONFIG_IP_NF_TARGET_ECN=m
+CONFIG_IP_NF_TARGET_DSCP=m
+CONFIG_IP_NF_TARGET_MARK=m
+CONFIG_IP_NF_TARGET_CLASSIFY=m
+CONFIG_IP_NF_RAW=m
+CONFIG_IP_NF_TARGET_NOTRACK=m
+CONFIG_IP_NF_ARPTABLES=m
+CONFIG_IP_NF_ARPFILTER=m
+CONFIG_IP_NF_ARP_MANGLE=m
+# CONFIG_IP_NF_COMPAT_IPCHAINS is not set
+# CONFIG_IP_NF_COMPAT_IPFWADM is not set
+
+#
+# IPv6: Netfilter Configuration
+#
+# CONFIG_IP6_NF_QUEUE is not set
+CONFIG_IP6_NF_IPTABLES=m
+CONFIG_IP6_NF_MATCH_LIMIT=m
+CONFIG_IP6_NF_MATCH_MAC=m
+CONFIG_IP6_NF_MATCH_RT=m
+CONFIG_IP6_NF_MATCH_OPTS=m
+CONFIG_IP6_NF_MATCH_FRAG=m
+CONFIG_IP6_NF_MATCH_HL=m
+CONFIG_IP6_NF_MATCH_MULTIPORT=m
+CONFIG_IP6_NF_MATCH_OWNER=m
+CONFIG_IP6_NF_MATCH_MARK=m
+CONFIG_IP6_NF_MATCH_IPV6HEADER=m
+CONFIG_IP6_NF_MATCH_AHESP=m
+CONFIG_IP6_NF_MATCH_LENGTH=m
+CONFIG_IP6_NF_MATCH_EUI64=m
+CONFIG_IP6_NF_MATCH_PHYSDEV=m
+CONFIG_IP6_NF_FILTER=m
+CONFIG_IP6_NF_TARGET_LOG=m
+CONFIG_IP6_NF_MANGLE=m
+CONFIG_IP6_NF_TARGET_MARK=m
+CONFIG_IP6_NF_RAW=m
+
+#
+# Bridge: Netfilter Configuration
+#
+CONFIG_BRIDGE_NF_EBTABLES=m
+CONFIG_BRIDGE_EBT_BROUTE=m
+CONFIG_BRIDGE_EBT_T_FILTER=m
+CONFIG_BRIDGE_EBT_T_NAT=m
+CONFIG_BRIDGE_EBT_802_3=m
+CONFIG_BRIDGE_EBT_AMONG=m
+CONFIG_BRIDGE_EBT_ARP=m
+CONFIG_BRIDGE_EBT_IP=m
+CONFIG_BRIDGE_EBT_LIMIT=m
+CONFIG_BRIDGE_EBT_MARK=m
+CONFIG_BRIDGE_EBT_PKTTYPE=m
+CONFIG_BRIDGE_EBT_STP=m
+CONFIG_BRIDGE_EBT_VLAN=m
+CONFIG_BRIDGE_EBT_ARPREPLY=m
+CONFIG_BRIDGE_EBT_DNAT=m
+CONFIG_BRIDGE_EBT_MARK_T=m
+CONFIG_BRIDGE_EBT_REDIRECT=m
+CONFIG_BRIDGE_EBT_SNAT=m
+CONFIG_BRIDGE_EBT_LOG=m
+CONFIG_XFRM=y
+CONFIG_XFRM_USER=y
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+CONFIG_IP_SCTP=m
+# CONFIG_SCTP_DBG_MSG is not set
+# CONFIG_SCTP_DBG_OBJCNT is not set
+# CONFIG_SCTP_HMAC_NONE is not set
+# CONFIG_SCTP_HMAC_SHA1 is not set
+CONFIG_SCTP_HMAC_MD5=y
+CONFIG_ATM=m
+CONFIG_ATM_CLIP=m
+# CONFIG_ATM_CLIP_NO_ICMP is not set
+CONFIG_ATM_LANE=m
+# CONFIG_ATM_MPOA is not set
+CONFIG_ATM_BR2684=m
+# CONFIG_ATM_BR2684_IPFILTER is not set
+CONFIG_BRIDGE=m
+CONFIG_VLAN_8021Q=m
+# CONFIG_DECNET is not set
+CONFIG_LLC=y
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_ATALK is not set
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+CONFIG_NET_DIVERT=y
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+
+#
+# QoS and/or fair queueing
+#
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_CLK_JIFFIES=y
+# CONFIG_NET_SCH_CLK_GETTIMEOFDAY is not set
+# CONFIG_NET_SCH_CLK_CPU is not set
+CONFIG_NET_SCH_CBQ=m
+CONFIG_NET_SCH_HTB=m
+CONFIG_NET_SCH_HFSC=m
+CONFIG_NET_SCH_ATM=m
+CONFIG_NET_SCH_PRIO=m
+CONFIG_NET_SCH_RED=m
+CONFIG_NET_SCH_SFQ=m
+CONFIG_NET_SCH_TEQL=m
+CONFIG_NET_SCH_TBF=m
+CONFIG_NET_SCH_GRED=m
+CONFIG_NET_SCH_DSMARK=m
+CONFIG_NET_SCH_NETEM=m
+CONFIG_NET_SCH_INGRESS=m
+CONFIG_NET_QOS=y
+CONFIG_NET_ESTIMATOR=y
+CONFIG_NET_CLS=y
+CONFIG_NET_CLS_TCINDEX=m
+CONFIG_NET_CLS_ROUTE4=m
+CONFIG_NET_CLS_ROUTE=y
+CONFIG_NET_CLS_FW=m
+CONFIG_NET_CLS_U32=m
+CONFIG_CLS_U32_PERF=y
+CONFIG_NET_CLS_IND=y
+CONFIG_NET_CLS_RSVP=m
+CONFIG_NET_CLS_RSVP6=m
+# CONFIG_NET_CLS_ACT is not set
+CONFIG_NET_CLS_POLICE=y
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+CONFIG_NETPOLL=y
+# CONFIG_NETPOLL_RX is not set
+CONFIG_NETPOLL_TRAP=y
+CONFIG_NET_POLL_CONTROLLER=y
+# CONFIG_HAMRADIO is not set
+# CONFIG_IRDA is not set
+CONFIG_BT=m
+CONFIG_BT_L2CAP=m
+CONFIG_BT_SCO=m
+CONFIG_BT_RFCOMM=m
+CONFIG_BT_RFCOMM_TTY=y
+CONFIG_BT_BNEP=m
+CONFIG_BT_BNEP_MC_FILTER=y
+CONFIG_BT_BNEP_PROTO_FILTER=y
+CONFIG_BT_CMTP=m
+CONFIG_BT_HIDP=m
+
+#
+# Bluetooth device drivers
+#
+CONFIG_BT_HCIUSB=m
+CONFIG_BT_HCIUSB_SCO=y
+CONFIG_BT_HCIUART=m
+CONFIG_BT_HCIUART_H4=y
+CONFIG_BT_HCIUART_BCSP=y
+CONFIG_BT_HCIUART_BCSP_TXCRC=y
+CONFIG_BT_HCIBCM203X=m
+CONFIG_BT_HCIBFUSB=m
+CONFIG_BT_HCIDTL1=m
+CONFIG_BT_HCIBT3C=m
+CONFIG_BT_HCIBLUECARD=m
+CONFIG_BT_HCIBTUART=m
+CONFIG_BT_HCIVHCI=m
+CONFIG_TUX=m
+
+#
+# TUX options
+#
+CONFIG_TUX_EXTCGI=y
+# CONFIG_TUX_EXTENDED_LOG is not set
+# CONFIG_TUX_DEBUG is not set
+CONFIG_NETDEVICES=y
+CONFIG_DUMMY=m
+CONFIG_BONDING=m
+# CONFIG_EQUALIZER is not set
+CONFIG_TUN=m
+CONFIG_ETHERTAP=m
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=m
+CONFIG_HAPPYMEAL=m
+CONFIG_SUNGEM=m
+CONFIG_NET_VENDOR_3COM=y
+CONFIG_VORTEX=m
+CONFIG_TYPHOON=m
+
+#
+# Tulip family network device support
+#
+CONFIG_NET_TULIP=y
+CONFIG_DE2104X=m
+CONFIG_TULIP=m
+# CONFIG_TULIP_MWI is not set
+CONFIG_TULIP_MMIO=y
+# CONFIG_TULIP_NAPI is not set
+CONFIG_DE4X5=m
+CONFIG_WINBOND_840=m
+CONFIG_DM9102=m
+CONFIG_PCMCIA_XIRCOM=m
+# CONFIG_HP100 is not set
+CONFIG_NET_PCI=y
+CONFIG_PCNET32=m
+CONFIG_AMD8111_ETH=m
+CONFIG_AMD8111E_NAPI=y
+CONFIG_ADAPTEC_STARFIRE=m
+CONFIG_ADAPTEC_STARFIRE_NAPI=y
+CONFIG_B44=m
+CONFIG_FORCEDETH=m
+# CONFIG_DGRS is not set
+CONFIG_EEPRO100=m
+# CONFIG_EEPRO100_PIO is not set
+CONFIG_E100=m
+CONFIG_E100_NAPI=y
+CONFIG_FEALNX=m
+CONFIG_NATSEMI=m
+CONFIG_NE2K_PCI=m
+CONFIG_8139CP=m
+CONFIG_8139TOO=m
+CONFIG_8139TOO_PIO=y
+# CONFIG_8139TOO_TUNE_TWISTER is not set
+CONFIG_8139TOO_8129=y
+# CONFIG_8139_OLD_RX_RESET is not set
+CONFIG_SIS900=m
+CONFIG_EPIC100=m
+# CONFIG_SUNDANCE is not set
+CONFIG_VIA_RHINE=m
+CONFIG_VIA_RHINE_MMIO=y
+
+#
+# Ethernet (1000 Mbit)
+#
+CONFIG_ACENIC=m
+# CONFIG_ACENIC_OMIT_TIGON_I is not set
+CONFIG_DL2K=m
+CONFIG_E1000=m
+CONFIG_E1000_NAPI=y
+CONFIG_NS83820=m
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+CONFIG_R8169=m
+CONFIG_R8169_NAPI=y
+CONFIG_SK98LIN=m
+CONFIG_VIA_VELOCITY=m
+CONFIG_TIGON3=m
+
+#
+# Ethernet (10000 Mbit)
+#
+CONFIG_IXGB=m
+CONFIG_IXGB_NAPI=y
+CONFIG_S2IO=m
+CONFIG_S2IO_NAPI=y
+
+#
+# Token Ring devices
+#
+CONFIG_TR=y
+CONFIG_IBMOL=m
+CONFIG_3C359=m
+CONFIG_TMS380TR=m
+CONFIG_TMSPCI=m
+CONFIG_ABYSS=m
+
+#
+# Wireless LAN (non-hamradio)
+#
+CONFIG_NET_RADIO=y
+
+#
+# Obsolete Wireless cards support (pre-802.11)
+#
+# CONFIG_STRIP is not set
+CONFIG_PCMCIA_WAVELAN=m
+CONFIG_PCMCIA_NETWAVE=m
+
+#
+# Wireless 802.11 Frequency Hopping cards support
+#
+# CONFIG_PCMCIA_RAYCS is not set
+
+#
+# Wireless 802.11b ISA/PCI cards support
+#
+# CONFIG_IEEE80211 is not set
+CONFIG_HERMES=m
+CONFIG_PLX_HERMES=m
+CONFIG_TMD_HERMES=m
+CONFIG_PCI_HERMES=m
+CONFIG_ATMEL=m
+CONFIG_PCI_ATMEL=m
+
+#
+# Wireless 802.11b Pcmcia/Cardbus cards support
+#
+CONFIG_PCMCIA_HERMES=m
+CONFIG_AIRO_CS=m
+CONFIG_PCMCIA_ATMEL=m
+CONFIG_PCMCIA_WL3501=m
+
+#
+# Prism GT/Duette 802.11(a/b/g) PCI/Cardbus support
+#
+CONFIG_PRISM54=m
+CONFIG_NET_WIRELESS=y
+
+#
+# PCMCIA network device support
+#
+CONFIG_NET_PCMCIA=y
+CONFIG_PCMCIA_3C589=m
+CONFIG_PCMCIA_3C574=m
+CONFIG_PCMCIA_FMVJ18X=m
+CONFIG_PCMCIA_PCNET=m
+CONFIG_PCMCIA_NMCLAN=m
+CONFIG_PCMCIA_SMC91C92=m
+CONFIG_PCMCIA_XIRC2PS=m
+CONFIG_PCMCIA_AXNET=m
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+
+#
+# ATM drivers
+#
+CONFIG_ATM_TCP=m
+CONFIG_ATM_LANAI=m
+CONFIG_ATM_ENI=m
+# CONFIG_ATM_ENI_DEBUG is not set
+# CONFIG_ATM_ENI_TUNE_BURST is not set
+CONFIG_ATM_FIRESTREAM=m
+# CONFIG_ATM_ZATM is not set
+CONFIG_ATM_IDT77252=m
+# CONFIG_ATM_IDT77252_DEBUG is not set
+# CONFIG_ATM_IDT77252_RCV_ALL is not set
+CONFIG_ATM_IDT77252_USE_SUNI=y
+CONFIG_ATM_AMBASSADOR=m
+# CONFIG_ATM_AMBASSADOR_DEBUG is not set
+CONFIG_ATM_HORIZON=m
+# CONFIG_ATM_HORIZON_DEBUG is not set
+CONFIG_ATM_FORE200E_MAYBE=m
+# CONFIG_ATM_FORE200E_PCA is not set
+CONFIG_ATM_HE=m
+# CONFIG_ATM_HE_USE_SUNI is not set
+CONFIG_FDDI=y
+# CONFIG_DEFXX is not set
+# CONFIG_SKFP is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PLIP is not set
+CONFIG_PPP=m
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_ASYNC=m
+CONFIG_PPP_SYNC_TTY=m
+CONFIG_PPP_DEFLATE=m
+# CONFIG_PPP_BSDCOMP is not set
+CONFIG_PPPOE=m
+CONFIG_PPPOATM=m
+# CONFIG_SLIP is not set
+CONFIG_NET_FC=y
+# CONFIG_SHAPER is not set
+CONFIG_NETCONSOLE=m
+CONFIG_NETDUMP=m
+
+#
+# ISDN subsystem
+#
+CONFIG_ISDN=m
+
+#
+# Old ISDN4Linux
+#
+CONFIG_ISDN_I4L=m
+CONFIG_ISDN_PPP=y
+CONFIG_ISDN_PPP_VJ=y
+CONFIG_ISDN_MPP=y
+CONFIG_IPPP_FILTER=y
+# CONFIG_ISDN_PPP_BSDCOMP is not set
+CONFIG_ISDN_AUDIO=y
+CONFIG_ISDN_TTY_FAX=y
+
+#
+# ISDN feature submodules
+#
+
+#
+# ISDN4Linux hardware drivers
+#
+
+#
+# Passive cards
+#
+CONFIG_ISDN_DRV_HISAX=m
+
+#
+# D-channel protocol features
+#
+CONFIG_HISAX_EURO=y
+CONFIG_DE_AOC=y
+CONFIG_HISAX_NO_SENDCOMPLETE=y
+CONFIG_HISAX_NO_LLC=y
+CONFIG_HISAX_NO_KEYPAD=y
+CONFIG_HISAX_1TR6=y
+CONFIG_HISAX_NI1=y
+CONFIG_HISAX_MAX_CARDS=8
+
+#
+# HiSax supported cards
+#
+CONFIG_HISAX_16_3=y
+CONFIG_HISAX_TELESPCI=y
+CONFIG_HISAX_S0BOX=y
+CONFIG_HISAX_FRITZPCI=y
+CONFIG_HISAX_AVM_A1_PCMCIA=y
+CONFIG_HISAX_ELSA=y
+CONFIG_HISAX_DIEHLDIVA=y
+CONFIG_HISAX_SEDLBAUER=y
+CONFIG_HISAX_NETJET=y
+CONFIG_HISAX_NETJET_U=y
+CONFIG_HISAX_NICCY=y
+CONFIG_HISAX_BKM_A4T=y
+CONFIG_HISAX_SCT_QUADRO=y
+CONFIG_HISAX_GAZEL=y
+CONFIG_HISAX_HFC_PCI=y
+CONFIG_HISAX_W6692=y
+CONFIG_HISAX_HFC_SX=y
+CONFIG_HISAX_ENTERNOW_PCI=y
+# CONFIG_HISAX_DEBUG is not set
+
+#
+# HiSax PCMCIA card service modules
+#
+CONFIG_HISAX_SEDLBAUER_CS=m
+CONFIG_HISAX_ELSA_CS=m
+CONFIG_HISAX_AVM_A1_CS=m
+CONFIG_HISAX_TELES_CS=m
+
+#
+# HiSax sub driver modules
+#
+CONFIG_HISAX_ST5481=m
+CONFIG_HISAX_HFCUSB=m
+CONFIG_HISAX_FRITZ_PCIPNP=m
+CONFIG_HISAX_HDLC=y
+
+#
+# Active cards
+#
+CONFIG_ISDN_DRV_TPAM=m
+
+#
+# CAPI subsystem
+#
+CONFIG_ISDN_CAPI=m
+CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON=y
+CONFIG_ISDN_CAPI_MIDDLEWARE=y
+CONFIG_ISDN_CAPI_CAPI20=m
+CONFIG_ISDN_CAPI_CAPIFS_BOOL=y
+CONFIG_ISDN_CAPI_CAPIFS=m
+CONFIG_ISDN_CAPI_CAPIDRV=m
+
+#
+# CAPI hardware drivers
+#
+
+#
+# Active AVM cards
+#
+CONFIG_CAPI_AVM=y
+
+#
+# Active Eicon DIVA Server cards
+#
+# CONFIG_CAPI_EICON is not set
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+CONFIG_INPUT_JOYDEV=m
+# CONFIG_INPUT_TSDEV is not set
+CONFIG_INPUT_EVDEV=y
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input I/O drivers
+#
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=y
+CONFIG_SERIO=y
+CONFIG_SERIO_I8042=y
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_CT82C710 is not set
+# CONFIG_SERIO_PARKBD is not set
+# CONFIG_SERIO_PCIPS2 is not set
+# CONFIG_SERIO_RAW is not set
+
+#
+# Input Device Drivers
+#
+CONFIG_INPUT_KEYBOARD=y
+CONFIG_KEYBOARD_ATKBD=y
+# CONFIG_KEYBOARD_SUNKBD is not set
+# CONFIG_KEYBOARD_LKKBD is not set
+# CONFIG_KEYBOARD_XTKBD is not set
+# CONFIG_KEYBOARD_NEWTON is not set
+CONFIG_INPUT_MOUSE=y
+CONFIG_MOUSE_PS2=y
+CONFIG_MOUSE_SERIAL=m
+CONFIG_MOUSE_VSXXXAA=m
+CONFIG_INPUT_JOYSTICK=y
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_GUNZE=m
+CONFIG_INPUT_MISC=y
+CONFIG_INPUT_UINPUT=m
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+CONFIG_SERIAL_NONSTANDARD=y
+# CONFIG_ROCKETPORT is not set
+# CONFIG_CYCLADES is not set
+# CONFIG_SYNCLINK is not set
+# CONFIG_SYNCLINKMP is not set
+CONFIG_N_HDLC=m
+CONFIG_STALDRV=y
+CONFIG_SGI_SNSC=y
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_CS=m
+CONFIG_SERIAL_8250_ACPI=y
+CONFIG_SERIAL_8250_NR_UARTS=20
+CONFIG_SERIAL_8250_EXTENDED=y
+CONFIG_SERIAL_8250_SHARE_IRQ=y
+CONFIG_SERIAL_8250_DETECT_IRQ=y
+CONFIG_SERIAL_8250_MULTIPORT=y
+CONFIG_SERIAL_8250_RSA=y
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_SERIAL_SGI_L1_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+# CONFIG_LEGACY_PTYS is not set
+# CONFIG_CRASH is not set
+CONFIG_PRINTER=m
+CONFIG_LP_CONSOLE=y
+CONFIG_PPDEV=m
+# CONFIG_TIPAR is not set
+
+#
+# IPMI
+#
+CONFIG_IPMI_HANDLER=m
+# CONFIG_IPMI_PANIC_EVENT is not set
+CONFIG_IPMI_DEVICE_INTERFACE=m
+CONFIG_IPMI_SI=m
+CONFIG_IPMI_WATCHDOG=m
+CONFIG_IPMI_POWEROFF=m
+
+#
+# Watchdog Cards
+#
+CONFIG_WATCHDOG=y
+# CONFIG_WATCHDOG_NOWAYOUT is not set
+
+#
+# Watchdog Device Drivers
+#
+CONFIG_SOFT_WATCHDOG=m
+CONFIG_I8XX_TCO=m
+
+#
+# PCI-based Watchdog Cards
+#
+CONFIG_PCIPCWATCHDOG=m
+CONFIG_WDTPCI=m
+CONFIG_WDT_501_PCI=y
+
+#
+# USB-based Watchdog Cards
+#
+CONFIG_USBPCWATCHDOG=m
+# CONFIG_HW_RANDOM is not set
+CONFIG_EFI_RTC=y
+CONFIG_DTLK=m
+# CONFIG_R3964 is not set
+# CONFIG_APPLICOM is not set
+
+#
+# Ftape, the floppy tape device driver
+#
+CONFIG_AGP=y
+CONFIG_AGP_I460=y
+CONFIG_AGP_HP_ZX1=y
+CONFIG_DRM=y
+# CONFIG_DRM_TDFX is not set
+CONFIG_DRM_R128=m
+CONFIG_DRM_RADEON=m
+CONFIG_DRM_MGA=m
+# CONFIG_DRM_SIS is not set
+
+#
+# PCMCIA character devices
+#
+# CONFIG_SYNCLINK_CS is not set
+CONFIG_RAW_DRIVER=y
+# CONFIG_HPET is not set
+CONFIG_MAX_RAW_DEVS=8192
+# CONFIG_MMTIMER is not set
+
+#
+# I2C support
+#
+CONFIG_I2C=m
+CONFIG_I2C_CHARDEV=m
+
+#
+# I2C Algorithms
+#
+CONFIG_I2C_ALGOBIT=m
+CONFIG_I2C_ALGOPCF=m
+CONFIG_I2C_ALGOPCA=m
+
+#
+# I2C Hardware Bus support
+#
+CONFIG_I2C_ALI1535=m
+CONFIG_I2C_ALI1563=m
+CONFIG_I2C_ALI15X3=m
+CONFIG_I2C_AMD756=m
+CONFIG_I2C_AMD8111=m
+CONFIG_I2C_I801=m
+CONFIG_I2C_I810=m
+CONFIG_I2C_ISA=m
+CONFIG_I2C_NFORCE2=m
+# CONFIG_I2C_PARPORT is not set
+# CONFIG_I2C_PARPORT_LIGHT is not set
+CONFIG_I2C_PROSAVAGE=m
+CONFIG_I2C_SAVAGE4=m
+# CONFIG_SCx200_ACB is not set
+CONFIG_I2C_SIS5595=m
+CONFIG_I2C_SIS630=m
+CONFIG_I2C_SIS96X=m
+CONFIG_I2C_VIA=m
+CONFIG_I2C_VIAPRO=m
+CONFIG_I2C_VOODOO3=m
+# CONFIG_I2C_PCA_ISA is not set
+
+#
+# Hardware Sensors Chip support
+#
+CONFIG_I2C_SENSOR=m
+CONFIG_SENSORS_ADM1021=m
+CONFIG_SENSORS_ADM1025=m
+CONFIG_SENSORS_ADM1031=m
+CONFIG_SENSORS_ASB100=m
+CONFIG_SENSORS_DS1621=m
+CONFIG_SENSORS_FSCHER=m
+CONFIG_SENSORS_GL518SM=m
+CONFIG_SENSORS_IT87=m
+CONFIG_SENSORS_LM75=m
+CONFIG_SENSORS_LM77=m
+CONFIG_SENSORS_LM78=m
+CONFIG_SENSORS_LM80=m
+CONFIG_SENSORS_LM83=m
+CONFIG_SENSORS_LM85=m
+CONFIG_SENSORS_LM90=m
+CONFIG_SENSORS_MAX1619=m
+CONFIG_SENSORS_SMSC47M1=m
+CONFIG_SENSORS_VIA686A=m
+CONFIG_SENSORS_W83781D=m
+CONFIG_SENSORS_W83L785TS=m
+CONFIG_SENSORS_W83627HF=m
+
+#
+# Other I2C Chip support
+#
+CONFIG_SENSORS_EEPROM=m
+CONFIG_SENSORS_PCF8574=m
+CONFIG_SENSORS_PCF8591=m
+CONFIG_SENSORS_RTC8564=m
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_ALGO is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
+#
+# Misc devices
+#
+
+#
+# Multimedia devices
+#
+CONFIG_VIDEO_DEV=m
+
+#
+# Video For Linux
+#
+
+#
+# Video Adapters
+#
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_SAA5246A is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+CONFIG_VIDEO_OVCAMCHIP=m
+
+#
+# Radio Adapters
+#
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+
+#
+# Graphics support
+#
+CONFIG_FB=y
+CONFIG_FB_MODE_HELPERS=y
+CONFIG_FB_CIRRUS=m
+# CONFIG_FB_PM2 is not set
+# CONFIG_FB_CYBER2000 is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_IMSTT is not set
+CONFIG_FB_RIVA=m
+# CONFIG_FB_RIVA_I2C is not set
+# CONFIG_FB_RIVA_DEBUG is not set
+# CONFIG_FB_MATROX is not set
+# CONFIG_FB_RADEON_OLD is not set
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_ATY is not set
+# CONFIG_FB_SIS is not set
+# CONFIG_FB_NEOMAGIC is not set
+CONFIG_FB_KYRO=m
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VIRTUAL is not set
+
+#
+# Console display driver support
+#
+CONFIG_VGA_CONSOLE=y
+CONFIG_DUMMY_CONSOLE=y
+CONFIG_FRAMEBUFFER_CONSOLE=y
+# CONFIG_FONTS is not set
+CONFIG_FONT_8x8=y
+CONFIG_FONT_8x16=y
+
+#
+# Logo configuration
+#
+CONFIG_LOGO=y
+# CONFIG_LOGO_LINUX_MONO is not set
+# CONFIG_LOGO_LINUX_VGA16 is not set
+CONFIG_LOGO_LINUX_CLUT224=y
+
+#
+# Sound
+#
+CONFIG_SOUND=m
+
+#
+# Advanced Linux Sound Architecture
+#
+CONFIG_SND=m
+CONFIG_SND_TIMER=m
+CONFIG_SND_PCM=m
+CONFIG_SND_HWDEP=m
+CONFIG_SND_RAWMIDI=m
+CONFIG_SND_SEQUENCER=m
+CONFIG_SND_SEQ_DUMMY=m
+CONFIG_SND_OSSEMUL=y
+CONFIG_SND_MIXER_OSS=m
+CONFIG_SND_PCM_OSS=m
+CONFIG_SND_SEQUENCER_OSS=y
+# CONFIG_SND_VERBOSE_PRINTK is not set
+# CONFIG_SND_DEBUG is not set
+
+#
+# Generic devices
+#
+CONFIG_SND_MPU401_UART=m
+CONFIG_SND_OPL3_LIB=m
+CONFIG_SND_VX_LIB=m
+CONFIG_SND_DUMMY=m
+CONFIG_SND_VIRMIDI=m
+CONFIG_SND_MTPAV=m
+# CONFIG_SND_SERIAL_U16550 is not set
+CONFIG_SND_MPU401=m
+
+#
+# PCI devices
+#
+CONFIG_SND_AC97_CODEC=m
+CONFIG_SND_ALI5451=m
+CONFIG_SND_ATIIXP=m
+CONFIG_SND_ATIIXP_MODEM=m
+CONFIG_SND_AU8810=m
+CONFIG_SND_AU8820=m
+CONFIG_SND_AU8830=m
+CONFIG_SND_AZT3328=m
+CONFIG_SND_BT87X=m
+CONFIG_SND_CS46XX=m
+CONFIG_SND_CS46XX_NEW_DSP=y
+CONFIG_SND_CS4281=m
+CONFIG_SND_EMU10K1=m
+CONFIG_SND_KORG1212=m
+CONFIG_SND_MIXART=m
+CONFIG_SND_NM256=m
+CONFIG_SND_RME32=m
+CONFIG_SND_RME96=m
+CONFIG_SND_RME9652=m
+CONFIG_SND_HDSP=m
+CONFIG_SND_TRIDENT=m
+CONFIG_SND_YMFPCI=m
+CONFIG_SND_ALS4000=m
+CONFIG_SND_CMIPCI=m
+CONFIG_SND_ENS1370=m
+CONFIG_SND_ENS1371=m
+CONFIG_SND_ES1938=m
+CONFIG_SND_ES1968=m
+CONFIG_SND_MAESTRO3=m
+CONFIG_SND_FM801=m
+CONFIG_SND_FM801_TEA575X=m
+CONFIG_SND_ICE1712=m
+CONFIG_SND_ICE1724=m
+CONFIG_SND_INTEL8X0=m
+CONFIG_SND_INTEL8X0M=m
+CONFIG_SND_SONICVIBES=m
+CONFIG_SND_VIA82XX=m
+CONFIG_SND_VX222=m
+
+#
+# ALSA USB devices
+#
+CONFIG_SND_USB_AUDIO=m
+CONFIG_SND_USB_USX2Y=m
+
+#
+# PCMCIA devices
+#
+
+#
+# Open Sound System
+#
+# CONFIG_SOUND_PRIME is not set
+
+#
+# USB support
+#
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+CONFIG_USB_DEVICEFS=y
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+CONFIG_USB_SUSPEND=y
+# CONFIG_USB_OTG is not set
+
+#
+# USB Host Controller Drivers
+#
+CONFIG_USB_EHCI_HCD=m
+CONFIG_USB_EHCI_SPLIT_ISO=y
+CONFIG_USB_EHCI_ROOT_HUB_TT=y
+CONFIG_USB_OHCI_HCD=m
+CONFIG_USB_UHCI_HCD=m
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_AUDIO is not set
+
+#
+# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem
+#
+CONFIG_USB_MIDI=m
+CONFIG_USB_ACM=m
+CONFIG_USB_PRINTER=m
+CONFIG_USB_STORAGE=m
+# CONFIG_USB_STORAGE_DEBUG is not set
+CONFIG_USB_STORAGE_RW_DETECT=y
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_DPCM=y
+CONFIG_USB_STORAGE_HP8200e=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+
+#
+# USB Human Interface Devices (HID)
+#
+CONFIG_USB_HID=y
+CONFIG_USB_HIDINPUT=y
+CONFIG_HID_FF=y
+CONFIG_HID_PID=y
+CONFIG_LOGITECH_FF=y
+CONFIG_THRUSTMASTER_FF=y
+CONFIG_USB_HIDDEV=y
+CONFIG_USB_AIPTEK=m
+CONFIG_USB_WACOM=m
+CONFIG_USB_KBTAB=m
+CONFIG_USB_POWERMATE=m
+CONFIG_USB_MTOUCH=m
+CONFIG_USB_EGALAX=m
+CONFIG_USB_XPAD=m
+CONFIG_USB_ATI_REMOTE=m
+
+#
+# USB Imaging devices
+#
+CONFIG_USB_MDC800=m
+CONFIG_USB_MICROTEK=m
+CONFIG_USB_HPUSBSCSI=m
+
+#
+# USB Multimedia devices
+#
+CONFIG_USB_DABUSB=m
+CONFIG_USB_VICAM=m
+CONFIG_USB_DSBR=m
+CONFIG_USB_IBMCAM=m
+CONFIG_USB_KONICAWC=m
+CONFIG_USB_OV511=m
+CONFIG_USB_SE401=m
+CONFIG_USB_SN9C102=m
+CONFIG_USB_STV680=m
+CONFIG_USB_W9968CF=m
+CONFIG_USB_PWC=m
+
+#
+# USB Network adaptors
+#
+CONFIG_USB_CATC=m
+CONFIG_USB_KAWETH=m
+CONFIG_USB_PEGASUS=m
+CONFIG_USB_RTL8150=m
+CONFIG_USB_USBNET=m
+
+#
+# USB Host-to-Host Cables
+#
+CONFIG_USB_ALI_M5632=y
+CONFIG_USB_AN2720=y
+CONFIG_USB_BELKIN=y
+CONFIG_USB_GENESYS=y
+CONFIG_USB_NET1080=y
+CONFIG_USB_PL2301=y
+
+#
+# Intelligent USB Devices/Gadgets
+#
+CONFIG_USB_ARMLINUX=y
+CONFIG_USB_EPSON2888=y
+CONFIG_USB_ZAURUS=y
+CONFIG_USB_CDCETHER=y
+
+#
+# USB Network Adapters
+#
+CONFIG_USB_AX8817X=y
+
+#
+# USB port drivers
+#
+CONFIG_USB_USS720=m
+
+#
+# USB Serial Converter support
+#
+CONFIG_USB_SERIAL=m
+CONFIG_USB_SERIAL_GENERIC=y
+CONFIG_USB_SERIAL_BELKIN=m
+CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m
+CONFIG_USB_SERIAL_EMPEG=m
+CONFIG_USB_SERIAL_FTDI_SIO=m
+CONFIG_USB_SERIAL_VISOR=m
+CONFIG_USB_SERIAL_IPAQ=m
+CONFIG_USB_SERIAL_IR=m
+CONFIG_USB_SERIAL_EDGEPORT=m
+CONFIG_USB_SERIAL_EDGEPORT_TI=m
+CONFIG_USB_SERIAL_KEYSPAN_PDA=m
+CONFIG_USB_SERIAL_KEYSPAN=m
+CONFIG_USB_SERIAL_KEYSPAN_MPR=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XA=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XB=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19=y
+CONFIG_USB_SERIAL_KEYSPAN_USA18X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QW=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QI=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y
+CONFIG_USB_SERIAL_KLSI=m
+CONFIG_USB_SERIAL_KOBIL_SCT=m
+CONFIG_USB_SERIAL_MCT_U232=m
+CONFIG_USB_SERIAL_PL2303=m
+CONFIG_USB_SERIAL_SAFE=m
+CONFIG_USB_SERIAL_SAFE_PADDED=y
+CONFIG_USB_SERIAL_CYBERJACK=m
+CONFIG_USB_SERIAL_XIRCOM=m
+CONFIG_USB_SERIAL_OMNINET=m
+CONFIG_USB_EZUSB=y
+
+#
+# USB Miscellaneous drivers
+#
+CONFIG_USB_EMI62=m
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_TIGL is not set
+CONFIG_USB_AUERSWALD=m
+CONFIG_USB_RIO500=m
+CONFIG_USB_LEGOTOWER=m
+CONFIG_USB_LCD=m
+CONFIG_USB_LED=m
+# CONFIG_USB_CYTHERM is not set
+CONFIG_USB_PHIDGETSERVO=m
+CONFIG_USB_TEST=m
+
+#
+# USB ATM/DSL drivers
+#
+CONFIG_USB_ATM=m
+CONFIG_USB_SPEEDTOUCH=m
+
+#
+# USB Gadget Support
+#
+# CONFIG_USB_GADGET is not set
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT2_FS_POSIX_ACL=y
+CONFIG_EXT2_FS_SECURITY=y
+CONFIG_EXT3_FS=m
+CONFIG_EXT3_FS_XATTR=y
+CONFIG_EXT3_FS_POSIX_ACL=y
+CONFIG_EXT3_FS_SECURITY=y
+CONFIG_JBD=m
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_JFS_FS is not set
+CONFIG_FS_POSIX_ACL=y
+# CONFIG_XFS_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_QUOTA=y
+# CONFIG_QFMT_V1 is not set
+CONFIG_QFMT_V2=y
+CONFIG_QUOTACTL=y
+# CONFIG_AUTOFS_FS is not set
+CONFIG_AUTOFS4_FS=m
+
+#
+# CD-ROM/DVD Filesystems
+#
+CONFIG_ISO9660_FS=y
+CONFIG_JOLIET=y
+CONFIG_ZISOFS=y
+CONFIG_ZISOFS_FS=y
+CONFIG_UDF_FS=m
+CONFIG_UDF_NLS=y
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=m
+CONFIG_MSDOS_FS=m
+CONFIG_VFAT_FS=m
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="ascii"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+CONFIG_SYSFS=y
+# CONFIG_DEVFS_FS is not set
+CONFIG_DEVPTS_FS_XATTR=y
+CONFIG_DEVPTS_FS_SECURITY=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_XATTR=y
+CONFIG_TMPFS_SECURITY=y
+CONFIG_HUGETLBFS=y
+CONFIG_HUGETLB_PAGE=y
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not set
+# CONFIG_AFFS_FS is not set
+CONFIG_HFS_FS=m
+CONFIG_HFSPLUS_FS=m
+# CONFIG_BEFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+CONFIG_CRAMFS=m
+CONFIG_VXFS_FS=m
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=m
+CONFIG_NFS_V3=y
+CONFIG_NFS_V4=y
+CONFIG_NFS_DIRECTIO=y
+CONFIG_NFSD=m
+CONFIG_NFSD_V3=y
+CONFIG_NFSD_V4=y
+CONFIG_NFSD_TCP=y
+CONFIG_LOCKD=m
+CONFIG_LOCKD_V4=y
+CONFIG_EXPORTFS=m
+CONFIG_SUNRPC=m
+CONFIG_SUNRPC_GSS=m
+CONFIG_RPCSEC_GSS_KRB5=m
+CONFIG_RPCSEC_GSS_SPKM3=m
+CONFIG_SMB_FS=m
+# CONFIG_SMB_NLS_DEFAULT is not set
+CONFIG_CIFS=m
+# CONFIG_CIFS_STATS is not set
+CONFIG_CIFS_XATTR=y
+CONFIG_CIFS_POSIX=y
+# CONFIG_NCP_FS is not set
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_ACORN_PARTITION is not set
+CONFIG_OSF_PARTITION=y
+# CONFIG_AMIGA_PARTITION is not set
+# CONFIG_ATARI_PARTITION is not set
+CONFIG_MAC_PARTITION=y
+CONFIG_MSDOS_PARTITION=y
+CONFIG_BSD_DISKLABEL=y
+CONFIG_MINIX_SUBPARTITION=y
+CONFIG_SOLARIS_X86_PARTITION=y
+CONFIG_UNIXWARE_DISKLABEL=y
+# CONFIG_LDM_PARTITION is not set
+CONFIG_SGI_PARTITION=y
+# CONFIG_ULTRIX_PARTITION is not set
+CONFIG_SUN_PARTITION=y
+CONFIG_EFI_PARTITION=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS=y
+CONFIG_NLS_DEFAULT="utf8"
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_CODEPAGE_737=m
+CONFIG_NLS_CODEPAGE_775=m
+CONFIG_NLS_CODEPAGE_850=m
+CONFIG_NLS_CODEPAGE_852=m
+CONFIG_NLS_CODEPAGE_855=m
+CONFIG_NLS_CODEPAGE_857=m
+CONFIG_NLS_CODEPAGE_860=m
+CONFIG_NLS_CODEPAGE_861=m
+CONFIG_NLS_CODEPAGE_862=m
+CONFIG_NLS_CODEPAGE_863=m
+CONFIG_NLS_CODEPAGE_864=m
+CONFIG_NLS_CODEPAGE_865=m
+CONFIG_NLS_CODEPAGE_866=m
+CONFIG_NLS_CODEPAGE_869=m
+CONFIG_NLS_CODEPAGE_936=m
+CONFIG_NLS_CODEPAGE_950=m
+CONFIG_NLS_CODEPAGE_932=m
+CONFIG_NLS_CODEPAGE_949=m
+CONFIG_NLS_CODEPAGE_874=m
+CONFIG_NLS_ISO8859_8=m
+CONFIG_NLS_CODEPAGE_1250=m
+CONFIG_NLS_CODEPAGE_1251=m
+CONFIG_NLS_ASCII=y
+CONFIG_NLS_ISO8859_1=m
+CONFIG_NLS_ISO8859_2=m
+CONFIG_NLS_ISO8859_3=m
+CONFIG_NLS_ISO8859_4=m
+CONFIG_NLS_ISO8859_5=m
+CONFIG_NLS_ISO8859_6=m
+CONFIG_NLS_ISO8859_7=m
+CONFIG_NLS_ISO8859_9=m
+CONFIG_NLS_ISO8859_13=m
+CONFIG_NLS_ISO8859_14=m
+CONFIG_NLS_ISO8859_15=m
+CONFIG_NLS_KOI8_R=m
+CONFIG_NLS_KOI8_U=m
+CONFIG_NLS_UTF8=m
+
+#
+# Library routines
+#
+CONFIG_CRC_CCITT=m
+CONFIG_CRC32=y
+CONFIG_LIBCRC32C=m
+CONFIG_ZLIB_INFLATE=y
+CONFIG_ZLIB_DEFLATE=m
+
+#
+# HP Simulator drivers
+#
+# CONFIG_HP_SIMETH is not set
+# CONFIG_HP_SIMSERIAL is not set
+# CONFIG_HP_SIMSCSI is not set
+
+#
+# Profiling support
+#
+CONFIG_PROFILING=y
+CONFIG_OPROFILE=m
+
+#
+# Kernel hacking
+#
+CONFIG_DEBUG_KERNEL=y
+CONFIG_MAGIC_SYSRQ=y
+# CONFIG_DEBUG_SLAB is not set
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_SPINLOCK_SLEEP=y
+# CONFIG_DEBUG_INFO is not set
+CONFIG_IA64_GRANULE_16MB=y
+# CONFIG_IA64_GRANULE_64MB is not set
+# CONFIG_IA64_PRINT_HAZARDS is not set
+# CONFIG_DISABLE_VHPT is not set
+# CONFIG_IA64_DEBUG_CMPXCHG is not set
+# CONFIG_IA64_DEBUG_IRQ is not set
+
+#
+# Security options
+#
+CONFIG_SECURITY=y
+CONFIG_SECURITY_NETWORK=y
+CONFIG_SECURITY_CAPABILITIES=y
+# CONFIG_SECURITY_ROOTPLUG is not set
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM_VALUE=1
+CONFIG_SECURITY_SELINUX_DISABLE=y
+CONFIG_SECURITY_SELINUX_DEVELOP=y
+CONFIG_SECURITY_SELINUX_AVC_STATS=y
+# CONFIG_SECURITY_SELINUX_MLS is not set
+
+#
+# Cryptographic options
+#
+CONFIG_CRYPTO=y
+CONFIG_CRYPTO_HMAC=y
+CONFIG_CRYPTO_NULL=m
+CONFIG_CRYPTO_MD4=m
+CONFIG_CRYPTO_MD5=m
+CONFIG_CRYPTO_SHA1=y
+CONFIG_CRYPTO_SHA256=m
+CONFIG_CRYPTO_SHA512=m
+CONFIG_CRYPTO_WP512=m
+CONFIG_CRYPTO_DES=m
+CONFIG_CRYPTO_BLOWFISH=m
+CONFIG_CRYPTO_TWOFISH=m
+CONFIG_CRYPTO_SERPENT=m
+CONFIG_CRYPTO_AES=m
+CONFIG_CRYPTO_CAST5=m
+CONFIG_CRYPTO_CAST6=m
+CONFIG_CRYPTO_TEA=m
+CONFIG_CRYPTO_ARC4=m
+CONFIG_CRYPTO_KHAZAD=m
+CONFIG_CRYPTO_DEFLATE=m
+CONFIG_CRYPTO_MICHAEL_MIC=m
+CONFIG_CRYPTO_CRC32C=m
+# CONFIG_CRYPTO_TEST is not set
+CONFIG_CRYPTO_SIGNATURE=y
+CONFIG_CRYPTO_SIGNATURE_DSA=y
+CONFIG_CRYPTO_MPILIB=y
diff --git a/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-x86_64-smp.config b/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-x86_64-smp.config
new file mode 100644 (file)
index 0000000..9d35318
--- /dev/null
@@ -0,0 +1,2632 @@
+#
+# Automatically generated make config: don't edit
+#
+CONFIG_MMU=y
+CONFIG_SMP=y
+# CONFIG_HOTPLUG_CPU is not set
+CONFIG_LOCALVERSION=""
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_CLEAN_COMPILE=y
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+
+#
+# General setup
+#
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+CONFIG_BSD_PROCESS_ACCT=y
+# CONFIG_BSD_PROCESS_ACCT_V3 is not set
+CONFIG_SYSCTL=y
+CONFIG_LOG_BUF_SHIFT=17
+# CONFIG_IKCONFIG is not set
+# CONFIG_EMBEDDED is not set
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_ALL is not set
+CONFIG_KALLSYMS_EXTRA_PASS=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+# CONFIG_PREEMPT is not set
+CONFIG_PREEMPT_VOLUNTARY=y
+CONFIG_POSIX_MQUEUE=y
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+CONFIG_MODVERSIONS=y
+CONFIG_KMOD=y
+CONFIG_MODULE_SIG=y
+# CONFIG_MODULE_SIG_FORCE is not set
+
+#
+# Bus options (PCI, PCMCIA, EISA, MCA, ISA)
+#
+CONFIG_PCI=y
+CONFIG_PCI_MSI=y
+CONFIG_PCI_LEGACY_PROC=y
+# CONFIG_PCI_NAMES is not set
+CONFIG_ISA=y
+# CONFIG_EISA is not set
+# CONFIG_MCA is not set
+# CONFIG_SCx200 is not set
+CONFIG_HOTPLUG=y
+
+#
+# PCMCIA/CardBus support
+#
+CONFIG_PCMCIA=m
+# CONFIG_PCMCIA_DEBUG is not set
+CONFIG_YENTA=y
+CONFIG_CARDBUS=y
+# CONFIG_I82092 is not set
+CONFIG_I82365=m
+CONFIG_PD6729=m
+CONFIG_TCIC=m
+CONFIG_PCMCIA_PROBE=y
+
+#
+# Executable file formats
+#
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_AOUT is not set
+CONFIG_BINFMT_MISC=y
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_FW_LOADER=y
+
+#
+# Memory Technology Devices (MTD)
+#
+CONFIG_MTD=m
+# CONFIG_MTD_DEBUG is not set
+CONFIG_MTD_PARTITIONS=m
+CONFIG_MTD_CONCAT=m
+CONFIG_MTD_REDBOOT_PARTS=m
+CONFIG_MTD_CMDLINE_PARTS=y
+CONFIG_MTD_PARTITIONS=y
+#
+# User Modules And Translation Layers
+#
+CONFIG_MTD_CHAR=m
+CONFIG_MTD_BLOCK=m
+CONFIG_MTD_BLOCK_RO=m
+CONFIG_FTL=m
+CONFIG_NFTL=m
+CONFIG_NFTL_RW=y
+# CONFIG_INFTL is not set
+
+#
+# RAM/ROM/Flash chip drivers
+#
+CONFIG_MTD_CFI=m
+CONFIG_MTD_JEDECPROBE=m
+CONFIG_MTD_GEN_PROBE=m
+# CONFIG_MTD_CFI_ADV_OPTIONS is not set
+CONFIG_MTD_CFI_INTELEXT=m
+CONFIG_MTD_CFI_AMDSTD=m
+CONFIG_MTD_CFI_STAA=m
+CONFIG_MTD_RAM=m
+CONFIG_MTD_ROM=m
+CONFIG_MTD_ABSENT=m
+# CONFIG_MTD_OBSOLETE_CHIPS is not set
+
+#
+# Mapping drivers for chip access
+#
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PHYSMAP is not set
+# CONFIG_MTD_PNC2000 is not set
+CONFIG_MTD_SC520CDP=m
+CONFIG_MTD_NETSC520=m
+CONFIG_MTD_SBC_GXX=m
+CONFIG_MTD_ELAN_104NC=m
+CONFIG_MTD_SCx200_DOCFLASH=m
+# CONFIG_MTD_AMD76XROM is not set
+# CONFIG_MTD_SCB2_FLASH is not set
+# CONFIG_MTD_NETtel is not set
+# CONFIG_MTD_DILNETPC is not set
+# CONFIG_MTD_L440GX is not set
+# CONFIG_MTD_PCI is not set
+
+#
+# Self-contained MTD device drivers
+#
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_PMC551_BUGFIX is not set
+# CONFIG_MTD_PMC551_DEBUG is not set
+# CONFIG_MTD_SLRAM is not set
+CONFIG_MTD_MTDRAM=m
+CONFIG_MTDRAM_TOTAL_SIZE=4096
+CONFIG_MTDRAM_ERASE_SIZE=128
+# CONFIG_MTD_BLKMTD is not set
+
+#
+# Disk-On-Chip Device Drivers
+#
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+CONFIG_MTD_DOCPROBE=m
+# CONFIG_MTD_DOCPROBE_ADVANCED is not set
+CONFIG_MTD_DOCPROBE_ADDRESS=0
+
+#
+# NAND Flash Device Drivers
+#
+CONFIG_MTD_NAND=m
+# CONFIG_MTD_NAND_VERIFY_WRITE is not set
+CONFIG_MTD_NAND_IDS=m
+
+# CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
+# CONFIG_MTD_REDBOOT_PARTS_READONLY is not set
+CONFIG_MTD_CFI_AMDSTD_RETRY=3
+# CONFIG_MTD_ICHXROM is not set
+# CONFIG_MTD_PHRAM is not set
+# CONFIG_MTD_NAND_DISKONCHIP is not set
+# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set
+
+
+#
+# Parallel port support
+#
+CONFIG_PARPORT=m
+CONFIG_PARPORT_PC=m
+CONFIG_PARPORT_PC_CML1=m
+CONFIG_PARPORT_SERIAL=m
+# CONFIG_PARPORT_PC_FIFO is not set
+# CONFIG_PARPORT_PC_SUPERIO is not set
+CONFIG_PARPORT_PC_PCMCIA=m
+# CONFIG_PARPORT_OTHER is not set
+CONFIG_PARPORT_1284=y
+
+#
+# Plug and Play support
+#
+CONFIG_PNP=y
+# CONFIG_PNP_DEBUG is not set
+
+#
+# Protocols
+#
+# CONFIG_ISAPNP is not set
+# CONFIG_PNPBIOS is not set
+
+#
+# Block devices
+#
+CONFIG_BLK_DEV_FD=m
+# CONFIG_BLK_DEV_XD is not set
+# CONFIG_PARIDE is not set
+CONFIG_BLK_CPQ_DA=m
+CONFIG_BLK_CPQ_CISS_DA=m
+CONFIG_CISS_SCSI_TAPE=y
+CONFIG_BLK_DEV_DAC960=m
+# CONFIG_BLK_DEV_UMEM is not set
+CONFIG_BLK_DEV_LOOP=m
+CONFIG_BLK_DEV_CRYPTOLOOP=m
+CONFIG_BLK_DEV_NBD=m
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=16384
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_BLK_DEV_ATIIXP=y
+CONFIG_BLK_DEV_DELKIN=y
+CONFIG_BLK_DEV_IT8212=y
+CONFIG_LBD=y
+# CONFIG_DCSSBLK is not set
+
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_IDE_GENERIC=y
+# CONFIG_HPT34X_AUTODMA is not set
+
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_HD_IDE is not set
+CONFIG_BLK_DEV_IDEDISK=y
+CONFIG_IDEDISK_MULTI_MODE=y
+CONFIG_BLK_DEV_IDECS=m
+CONFIG_BLK_DEV_IDECD=y
+# CONFIG_BLK_DEV_IDETAPE is not set
+CONFIG_BLK_DEV_IDEFLOPPY=y
+CONFIG_BLK_DEV_IDESCSI=m
+# CONFIG_IDE_TASK_IOCTL is not set
+# CONFIG_IDE_TASKFILE_IO is not set
+# CONFIG_BLK_DEV_IDE_SATA is not set
+
+#
+# IDE chipset support/bugfixes
+#
+# CONFIG_BLK_DEV_CMD640 is not set
+# CONFIG_BLK_DEV_CMD640_ENHANCED is not set
+CONFIG_BLK_DEV_IDEPNP=y
+CONFIG_BLK_DEV_IDEPCI=y
+CONFIG_IDEPCI_SHARE_IRQ=y
+# CONFIG_BLK_DEV_OFFBOARD is not set
+CONFIG_BLK_DEV_GENERIC=y
+# CONFIG_BLK_DEV_OPTI621 is not set
+CONFIG_BLK_DEV_RZ1000=y
+CONFIG_BLK_DEV_IDEDMA_PCI=y
+# CONFIG_BLK_DEV_IDEDMA_FORCED is not set
+CONFIG_IDEDMA_PCI_AUTO=y
+# CONFIG_IDEDMA_ONLYDISK is not set
+CONFIG_BLK_DEV_AEC62XX=y
+CONFIG_BLK_DEV_ALI15X3=y
+# CONFIG_WDC_ALI15X3 is not set
+CONFIG_BLK_DEV_AMD74XX=y
+CONFIG_BLK_DEV_CMD64X=y
+CONFIG_BLK_DEV_TRIFLEX=y
+CONFIG_BLK_DEV_CY82C693=y
+CONFIG_BLK_DEV_CS5520=y
+CONFIG_BLK_DEV_CS5530=y
+CONFIG_BLK_DEV_HPT34X=y
+CONFIG_BLK_DEV_HPT366=y
+# CONFIG_BLK_DEV_SC1200 is not set
+CONFIG_BLK_DEV_PIIX=y
+# CONFIG_BLK_DEV_NS87415 is not set
+CONFIG_BLK_DEV_PDC202XX_OLD=y
+# CONFIG_PDC202XX_BURST is not set
+CONFIG_BLK_DEV_PDC202XX_NEW=y
+CONFIG_PDC202XX_FORCE=y
+CONFIG_BLK_DEV_SVWKS=y
+CONFIG_BLK_DEV_SIIMAGE=y
+CONFIG_BLK_DEV_SIS5513=y
+CONFIG_BLK_DEV_SLC90E66=y
+# CONFIG_BLK_DEV_TRM290 is not set
+CONFIG_BLK_DEV_VIA82CXXX=y
+# CONFIG_IDE_CHIPSETS is not set
+CONFIG_BLK_DEV_IDEDMA=y
+# CONFIG_IDEDMA_IVB is not set
+CONFIG_IDEDMA_AUTO=y
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+CONFIG_SCSI=m
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=m
+CONFIG_CHR_DEV_ST=m
+CONFIG_CHR_DEV_OSST=m
+CONFIG_BLK_DEV_SR=m
+CONFIG_BLK_DEV_SR_VENDOR=y
+CONFIG_CHR_DEV_SG=m
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SPI_ATTRS=y
+CONFIG_SCSI_FC_ATTRS=y
+
+#
+# SCSI low-level drivers
+#
+CONFIG_BLK_DEV_3W_XXXX_RAID=m
+CONFIG_SCSI_3W_9XXX=m
+# CONFIG_SCSI_7000FASST is not set
+CONFIG_SCSI_ACARD=m
+CONFIG_SCSI_AHA152X=m
+# CONFIG_SCSI_AHA1542 is not set
+CONFIG_SCSI_AACRAID=m
+CONFIG_SCSI_AIC7XXX=m
+CONFIG_AIC7XXX_CMDS_PER_DEVICE=4
+CONFIG_AIC7XXX_RESET_DELAY_MS=15000
+# CONFIG_AIC7XXX_PROBE_EISA_VL is not set
+# CONFIG_AIC7XXX_BUILD_FIRMWARE is not set
+# CONFIG_AIC7XXX_DEBUG_ENABLE is not set
+CONFIG_AIC7XXX_DEBUG_MASK=0
+# CONFIG_AIC7XXX_REG_PRETTY_PRINT is not set
+CONFIG_SCSI_AIC7XXX_OLD=m
+CONFIG_SCSI_AIC79XX=m
+CONFIG_AIC79XX_CMDS_PER_DEVICE=4
+CONFIG_AIC79XX_RESET_DELAY_MS=15000
+# CONFIG_AIC79XX_BUILD_FIRMWARE is not set
+# CONFIG_AIC79XX_ENABLE_RD_STRM is not set
+# CONFIG_AIC79XX_DEBUG_ENABLE is not set
+CONFIG_AIC79XX_DEBUG_MASK=0
+# CONFIG_AIC79XX_REG_PRETTY_PRINT is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_IN2000 is not set
+CONFIG_MEGARAID_NEWGEN=y
+CONFIG_MEGARAID_MM=m
+CONFIG_MEGARAID_MAILBOX=m
+CONFIG_SCSI_SATA=y
+CONFIG_SCSI_SATA_SVW=m
+CONFIG_SCSI_ATA_PIIX=m
+CONFIG_SCSI_SATA_PROMISE=m
+CONFIG_SCSI_SATA_VIA=m
+CONFIG_BLK_DEV_SX8=m
+CONFIG_SCSI_SATA_VITESSE=m
+CONFIG_SCSI_SATA_SIL=m
+CONFIG_SCSI_SATA_SIS=m
+CONFIG_SCSI_SATA_SX4=m
+CONFIG_SCSI_SATA_NV=m
+CONFIG_SCSI_SATA_AHCI=m
+
+# CONFIG_SCSI_BUSLOGIC is not set
+CONFIG_SCSI_INITIO=m
+# CONFIG_SCSI_OMIT_FLASHPOINT is not set
+# CONFIG_SCSI_CPQFCTS is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_DTC3280 is not set
+# CONFIG_SCSI_EATA is not set
+# CONFIG_SCSI_EATA_PIO is not set
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+CONFIG_SCSI_GDTH=m
+# CONFIG_SCSI_GENERIC_NCR5380 is not set
+# CONFIG_SCSI_GENERIC_NCR5380_MMIO is not set
+CONFIG_SCSI_IPS=m
+# CONFIG_SCSI_INIA100 is not set
+CONFIG_SCSI_PPA=m
+CONFIG_SCSI_IMM=m
+# CONFIG_SCSI_IZIP_EPP16 is not set
+# CONFIG_SCSI_IZIP_SLOW_CTR is not set
+# CONFIG_SCSI_NCR53C406A is not set
+CONFIG_SCSI_SYM53C8XX_2=m
+CONFIG_SCSI_SYM53C8XX_DMA_ADDRESSING_MODE=1
+CONFIG_SCSI_SYM53C8XX_DEFAULT_TAGS=16
+CONFIG_SCSI_SYM53C8XX_MAX_TAGS=64
+# CONFIG_SCSI_SYM53C8XX_IOMAPPED is not set
+# CONFIG_SCSI_PAS16 is not set
+# CONFIG_SCSI_PSI240I is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_SCSI_QLOGIC_FC is not set
+# CONFIG_SCSI_QLOGIC_FC_FIRMWARE is not set
+CONFIG_SCSI_QLOGIC_1280=m
+# CONFIG_SCSI_SYM53C416 is not set
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_T128 is not set
+# CONFIG_SCSI_U14_34F is not set
+# CONFIG_SCSI_ULTRASTOR is not set
+# CONFIG_SCSI_NSP32 is not set
+# CONFIG_SCSI_DEBUG is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_SCSI_QLA2XXX=m
+CONFIG_SCSI_QLA21XX=m
+CONFIG_SCSI_QLA22XX=m
+CONFIG_SCSI_QLA2300=m
+CONFIG_SCSI_QLA2322=m
+CONFIG_SCSI_QLA6312=m
+CONFIG_SCSI_QLA6322=m
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_DPT_I2O is not set
+
+CONFIG_SCSI_LPFC=m
+
+#
+# PCMCIA SCSI adapter support
+#
+# CONFIG_PCMCIA_AHA152X is not set
+# CONFIG_PCMCIA_FDOMAIN is not set
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+
+
+#
+# Old CD-ROM drivers (not SCSI, not IDE)
+#
+# CONFIG_CD_NO_IDESCSI is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+CONFIG_MD=y
+CONFIG_BLK_DEV_MD=y
+CONFIG_MD_LINEAR=m
+CONFIG_MD_RAID0=m
+CONFIG_MD_RAID1=m
+CONFIG_MD_RAID5=m
+CONFIG_MD_RAID6=m
+CONFIG_MD_RAID10=m
+CONFIG_MD_MULTIPATH=m
+CONFIG_BLK_DEV_DM=m
+CONFIG_DM_SNAPSHOT=m
+CONFIG_DM_MIRROR=m
+CONFIG_DM_ZERO=m
+CONFIG_DM_CRYPT=m
+
+#
+# Fusion MPT device support
+#
+CONFIG_FUSION=m
+CONFIG_FUSION_MAX_SGE=40
+CONFIG_FUSION_CTL=m
+CONFIG_FUSION_LAN=m
+
+#
+# IEEE 1394 (FireWire) support (EXPERIMENTAL)
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# Subsystem Options
+#
+# CONFIG_IEEE1394_VERBOSEDEBUG is not set
+CONFIG_IEEE1394_OUI_DB=y
+
+#
+# Device Drivers
+#
+# CONFIG_IEEE1394_PCILYNX is not set
+CONFIG_IEEE1394_OHCI1394=m
+
+#
+# Protocol Drivers
+#
+CONFIG_IEEE1394_VIDEO1394=m
+CONFIG_IEEE1394_SBP2=m
+# CONFIG_IEEE1394_SBP2_PHYS_DMA is not set
+# CONFIG_IEEE1394_ETH1394 is not set
+CONFIG_IEEE1394_DV1394=m
+CONFIG_IEEE1394_RAWIO=m
+CONFIG_IEEE1394_CMP=m
+CONFIG_IEEE1394_AMDTP=m
+# CONFIG_IEEE1394_EXTRA_CONFIG_ROMS is not set
+
+#
+# I2O device support
+#
+CONFIG_I2O=m
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+CONFIG_PACKET=y
+CONFIG_PACKET_MMAP=y
+CONFIG_NETLINK_DEV=y
+CONFIG_UNIX=y
+CONFIG_NET_KEY=m
+CONFIG_INET=y
+CONFIG_INET_TUNNEL=m
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_FWMARK=y
+CONFIG_IP_ROUTE_MULTIPATH=y
+CONFIG_IP_ROUTE_VERBOSE=y
+# CONFIG_IP_PNP is not set
+CONFIG_NET_IPIP=m
+CONFIG_NET_IPGRE=m
+CONFIG_NET_IPGRE_BROADCAST=y
+CONFIG_IP_MROUTE=y
+CONFIG_IP_PIMSM_V1=y
+CONFIG_IP_PIMSM_V2=y
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+CONFIG_INET_AH=m
+CONFIG_INET_ESP=m
+CONFIG_INET_IPCOMP=m
+CONFIG_NETCONSOLE=m
+# CONFIG_NETPOLL_RX is not set
+CONFIG_NETPOLL_TRAP=y
+CONFIG_NET_POLL_CONTROLLER=y
+CONFIG_NETDUMP=m
+CONFIG_DISKDUMP=m
+CONFIG_SCSI_DUMP=m
+CONFIG_SD_IOSTATS=y
+
+#
+# IP: Virtual Server Configuration
+#
+CONFIG_IP_VS=m
+# CONFIG_IP_VS_DEBUG is not set
+CONFIG_IP_VS_TAB_BITS=12
+CONFIG_IP_VS_PROTO_TCP=y
+CONFIG_IP_VS_PROTO_UDP=y
+CONFIG_IP_VS_PROTO_ESP=y
+CONFIG_IP_VS_PROTO_AH=y
+CONFIG_IP_VS_RR=m
+CONFIG_IP_VS_WRR=m
+CONFIG_IP_VS_LC=m
+CONFIG_IP_VS_WLC=m
+CONFIG_IP_VS_LBLC=m
+CONFIG_IP_VS_LBLCR=m
+CONFIG_IP_VS_DH=m
+CONFIG_IP_VS_SH=m
+CONFIG_IP_VS_SED=m
+CONFIG_IP_VS_NQ=m
+CONFIG_IP_VS_FTP=m
+
+
+CONFIG_IPV6=m
+CONFIG_IPV6_PRIVACY=y
+CONFIG_INET6_AH=m
+CONFIG_INET6_ESP=m
+CONFIG_INET6_IPCOMP=m
+CONFIG_IPV6_TUNNEL=m
+# CONFIG_DECNET is not set
+CONFIG_BRIDGE=m
+CONFIG_NETFILTER=y
+# CONFIG_NETFILTER_DEBUG is not set
+CONFIG_BRIDGE_NETFILTER=y
+
+#
+# IP: Netfilter Configuration
+#
+CONFIG_IP_NF_CONNTRACK=m
+CONFIG_IP_NF_FTP=m
+CONFIG_IP_NF_IRC=m
+CONFIG_IP_NF_TFTP=m
+CONFIG_IP_NF_AMANDA=m
+CONFIG_IP_NF_QUEUE=m
+CONFIG_IP_NF_RAW=m
+CONFIG_IP_NF_IPTABLES=m
+CONFIG_IP_NF_MATCH_COMMENT=m
+CONFIG_IP_NF_MATCH_LIMIT=m
+CONFIG_IP_NF_MATCH_IPRANGE=m
+CONFIG_IP_NF_MATCH_MAC=m
+CONFIG_IP_NF_MATCH_PKTTYPE=m
+CONFIG_IP_NF_MATCH_MARK=m
+CONFIG_IP_NF_MATCH_MULTIPORT=m
+CONFIG_IP_NF_MATCH_TOS=m
+CONFIG_IP_NF_MATCH_RECENT=m
+CONFIG_IP_NF_MATCH_ECN=m
+CONFIG_IP_NF_MATCH_DSCP=m
+CONFIG_IP_NF_MATCH_AH_ESP=m
+CONFIG_IP_NF_MATCH_LENGTH=m
+CONFIG_IP_NF_MATCH_TTL=m
+CONFIG_IP_NF_MATCH_TCPMSS=m
+CONFIG_IP_NF_MATCH_HELPER=m
+CONFIG_IP_NF_MATCH_STATE=m
+CONFIG_IP_NF_MATCH_CONNTRACK=m
+CONFIG_IP_NF_MATCH_OWNER=m
+CONFIG_IP_NF_MATCH_PHYSDEV=m
+CONFIG_IP_NF_MATCH_ADDRTYPE=m
+CONFIG_IP_NF_MATCH_REALM=m
+CONFIG_IP_NF_MATCH_SCTP=m
+CONFIG_IP_NF_FILTER=m
+CONFIG_IP_NF_TARGET_REJECT=m
+CONFIG_IP_NF_NAT=m
+CONFIG_IP_NF_NAT_NEEDED=y
+CONFIG_IP_NF_TARGET_MASQUERADE=m
+CONFIG_IP_NF_TARGET_REDIRECT=m
+CONFIG_IP_NF_TARGET_NETMAP=m
+CONFIG_IP_NF_TARGET_SAME=m
+CONFIG_IP_NF_TARGET_NOTRACK=m
+CONFIG_IP_NF_NAT_LOCAL=y
+CONFIG_IP_NF_NAT_SNMP_BASIC=m
+CONFIG_IP_NF_NAT_IRC=m
+CONFIG_IP_NF_NAT_FTP=m
+CONFIG_IP_NF_NAT_TFTP=m
+CONFIG_IP_NF_NAT_AMANDA=m
+CONFIG_IP_NF_MANGLE=m
+CONFIG_IP_NF_TARGET_TOS=m
+CONFIG_IP_NF_TARGET_ECN=m
+CONFIG_IP_NF_TARGET_DSCP=m
+CONFIG_IP_NF_TARGET_MARK=m
+CONFIG_IP_NF_TARGET_CLASSIFY=m
+CONFIG_IP_NF_TARGET_LOG=m
+CONFIG_IP_NF_TARGET_ULOG=m
+CONFIG_IP_NF_TARGET_TCPMSS=m
+CONFIG_IP_NF_ARPTABLES=m
+CONFIG_IP_NF_ARPFILTER=m
+CONFIG_IP_NF_ARP_MANGLE=m
+CONFIG_IP_NF_CT_ACCT=y
+CONFIG_IP_NF_CT_PROTO_SCTP=m
+# CONFIG_IP_NF_COMPAT_IPCHAINS is not set
+# CONFIG_IP_NF_COMPAT_IPFWADM is not set
+
+#
+# IPv6: Netfilter Configuration
+#
+# CONFIG_IP6_NF_QUEUE is not set
+CONFIG_IP6_NF_IPTABLES=m
+CONFIG_IP6_NF_MATCH_LIMIT=m
+CONFIG_IP6_NF_MATCH_MAC=m
+CONFIG_IP6_NF_MATCH_RT=m
+CONFIG_IP6_NF_MATCH_OPTS=m
+CONFIG_IP6_NF_MATCH_FRAG=m
+CONFIG_IP6_NF_MATCH_HL=m
+CONFIG_IP6_NF_MATCH_MULTIPORT=m
+CONFIG_IP6_NF_MATCH_OWNER=m
+CONFIG_IP6_NF_MATCH_MARK=m
+CONFIG_IP6_NF_MATCH_IPV6HEADER=m
+CONFIG_IP6_NF_MATCH_AHESP=m
+CONFIG_IP6_NF_MATCH_LENGTH=m
+CONFIG_IP6_NF_MATCH_EUI64=m
+CONFIG_IP6_NF_MATCH_PHYSDEV=m
+CONFIG_IP6_NF_FILTER=m
+CONFIG_IP6_NF_TARGET_LOG=m
+CONFIG_IP6_NF_MANGLE=m
+CONFIG_IP6_NF_TARGET_MARK=m
+CONFIG_IP6_NF_RAW=m
+
+
+#
+# Bridge: Netfilter Configuration
+#
+CONFIG_BRIDGE_NF_EBTABLES=m
+CONFIG_BRIDGE_EBT_BROUTE=m
+CONFIG_BRIDGE_EBT_T_FILTER=m
+CONFIG_BRIDGE_EBT_T_NAT=m
+CONFIG_BRIDGE_EBT_802_3=m
+CONFIG_BRIDGE_EBT_AMONG=m
+CONFIG_BRIDGE_EBT_ARP=m
+CONFIG_BRIDGE_EBT_IP=m
+CONFIG_BRIDGE_EBT_LIMIT=m
+CONFIG_BRIDGE_EBT_MARK=m
+CONFIG_BRIDGE_EBT_PKTTYPE=m
+CONFIG_BRIDGE_EBT_STP=m
+CONFIG_BRIDGE_EBT_VLAN=m
+CONFIG_BRIDGE_EBT_ARPREPLY=m
+CONFIG_BRIDGE_EBT_DNAT=m
+CONFIG_BRIDGE_EBT_MARK_T=m
+CONFIG_BRIDGE_EBT_REDIRECT=m
+CONFIG_BRIDGE_EBT_SNAT=m
+CONFIG_BRIDGE_EBT_LOG=m
+CONFIG_XFRM=y
+CONFIG_XFRM_USER=y
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+CONFIG_IP_SCTP=m
+# CONFIG_SCTP_DBG_MSG is not set
+# CONFIG_SCTP_DBG_OBJCNT is not set
+# CONFIG_SCTP_HMAC_NONE is not set
+# CONFIG_SCTP_HMAC_SHA1 is not set
+CONFIG_SCTP_HMAC_MD5=y
+CONFIG_ATM=m
+CONFIG_VLAN_8021Q=m
+CONFIG_LLC=m
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_IPX_INTERN is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+CONFIG_COPS_DAYNA=y
+CONFIG_COPS_TANGENT=y
+# CONFIG_IPDDP is not set
+CONFIG_IPDDP_ENCAP=y
+CONFIG_IPDDP_DECAP=y
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+CONFIG_NET_DIVERT=y
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_NET_HW_FLOWCONTROL is not set
+
+#
+# QoS and/or fair queueing
+#
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_CBQ=m
+CONFIG_NET_SCH_HTB=m
+CONFIG_NET_SCH_PRIO=m
+CONFIG_NET_SCH_RED=m
+CONFIG_NET_SCH_SFQ=m
+CONFIG_NET_SCH_TEQL=m
+CONFIG_NET_SCH_TBF=m
+CONFIG_NET_SCH_GRED=m
+CONFIG_NET_SCH_DSMARK=m
+CONFIG_NET_SCH_INGRESS=m
+CONFIG_NET_SCH_HFSC=m
+CONFIG_NET_SCH_NETEM=m
+CONFIG_NET_QOS=y
+CONFIG_NET_ESTIMATOR=y
+CONFIG_NET_CLS=y
+CONFIG_NET_CLS_TCINDEX=m
+CONFIG_NET_CLS_ROUTE4=m
+CONFIG_NET_CLS_ROUTE=y
+CONFIG_NET_CLS_FW=m
+CONFIG_NET_CLS_U32=m
+CONFIG_NET_CLS_RSVP=m
+CONFIG_NET_CLS_RSVP6=m
+CONFIG_NET_CLS_POLICE=y
+# CONFIG_NET_ACT_POLICE is not set
+CONFIG_CLS_U32_PERF=y
+CONFIG_NET_CLS_IND=y
+# CONFIG_NET_CLS_ACT is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+CONFIG_NETDEVICES=y
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+CONFIG_DUMMY=m
+CONFIG_BONDING=m
+# CONFIG_EQUALIZER is not set
+CONFIG_TUN=m
+CONFIG_ETHERTAP=m
+# CONFIG_NET_SB1000 is not set
+
+#
+# ATM
+# 
+CONFIG_ATM_CLIP=m
+CONFIG_ATM_LANE=m
+CONFIG_ATM_BR2684=m
+CONFIG_NET_SCH_ATM=m
+CONFIG_ATM_TCP=m
+CONFIG_ATM_LANAI=m
+CONFIG_ATM_ENI=m
+CONFIG_ATM_FIRESTREAM=m
+# CONFIG_ATM_ZATM is not set
+CONFIG_ATM_IDT77252=m
+CONFIG_ATM_AMBASSADOR=m
+CONFIG_ATM_HORIZON=m
+CONFIG_ATM_FORE200E_MAYBE=m
+CONFIG_ATM_HE=m
+CONFIG_PPPOATM=m
+CONFIG_ATM_NICSTAR=m
+# CONFIG_ATM_IA is not set
+
+
+# CONFIG_ATM_CLIP_NO_ICMP is not set
+# CONFIG_ATM_MPOA is not set
+# CONFIG_ATM_BR2684_IPFILTER is not set
+# CONFIG_ATM_ENI_DEBUG is not set
+# CONFIG_ATM_ENI_TUNE_BURST is not set
+# CONFIG_ATM_ZATM_DEBUG is not set
+# CONFIG_ATM_IDT77252_DEBUG is not set
+# CONFIG_ATM_IDT77252_RCV_ALL is not set
+# CONFIG_ATM_AMBASSADOR_DEBUG is not set
+# CONFIG_ATM_HORIZON_DEBUG is not set
+# CONFIG_ATM_FORE200E_PCA is not set
+# CONFIG_ATM_HE_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_IDT77105 is not set
+# CONFIG_ATM_IA_DEBUG is not set
+
+
+
+
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=m
+CONFIG_HAPPYMEAL=m
+CONFIG_SUNGEM=m
+CONFIG_NET_VENDOR_3COM=y
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+CONFIG_VORTEX=m
+CONFIG_TYPHOON=m
+# CONFIG_LANCE is not set
+CONFIG_NET_VENDOR_SMC=y
+# CONFIG_WD80x3 is not set
+# CONFIG_ULTRA is not set
+CONFIG_SMC9194=m
+CONFIG_NET_VENDOR_RACAL=y
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+
+#
+# Tulip family network device support
+#
+CONFIG_NET_TULIP=y
+CONFIG_DE2104X=m
+CONFIG_TULIP=m
+# CONFIG_TULIP_NAPI is not set
+
+# CONFIG_TULIP_MWI is not set
+CONFIG_TULIP_MMIO=y
+# CONFIG_NI5010 is not set
+# CONFIG_PCMCIA_XIRTULIP is not set
+CONFIG_DE4X5=m
+CONFIG_WINBOND_840=m
+CONFIG_DM9102=m
+CONFIG_PCMCIA_XIRCOM=m
+# CONFIG_AT1700 is not set
+# CONFIG_DEPCA is not set
+# CONFIG_HP100 is not set
+# CONFIG_NET_ISA is not set
+CONFIG_EWRK3=m
+CONFIG_E2100=m
+CONFIG_EEXPRESS=m
+CONFIG_EEXPRESS_PRO=m
+CONFIG_HPLAN_PLUS=m
+CONFIG_HPLAN=m
+CONFIG_LP486E=m
+CONFIG_ETH16I=m
+CONFIG_NE2000=m
+CONFIG_ZNET=m
+CONFIG_SEEQ8005=m
+CONFIG_LNE390=m
+CONFIG_NE3210=m
+CONFIG_ES3210=m
+CONFIG_NET_PCI=y
+CONFIG_PCNET32=m
+CONFIG_AMD8111_ETH=m
+CONFIG_AMD8111E_NAPI=y
+CONFIG_ADAPTEC_STARFIRE=m
+CONFIG_ADAPTEC_STARFIRE_NAPI=y
+# CONFIG_AC3200 is not set
+CONFIG_APRICOT=m
+CONFIG_B44=m
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+CONFIG_EEPRO100=m
+# CONFIG_EEPRO100_PIO is not set
+CONFIG_E100=m
+CONFIG_E100_NAPI=y
+CONFIG_FEALNX=m
+CONFIG_FORCEDETH=m
+CONFIG_NATSEMI=m
+CONFIG_NE2K_PCI=m
+CONFIG_8139CP=m
+CONFIG_8139TOO=m
+CONFIG_8139TOO_PIO=y
+# CONFIG_8139TOO_TUNE_TWISTER is not set
+CONFIG_8139TOO_8129=y
+# CONFIG_8139_OLD_RX_RESET is not set
+CONFIG_SIS900=m
+CONFIG_EPIC100=m
+# CONFIG_SUNDANCE is not set
+# CONFIG_SUNDANCE_MMIO is not set
+CONFIG_TLAN=m
+CONFIG_VIA_RHINE=m
+CONFIG_VIA_RHINE_MMIO=y
+CONFIG_VIA_VELOCITY=m
+CONFIG_NET_POCKET=y
+# CONFIG_ATP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+CONFIG_ACENIC=m
+# CONFIG_ACENIC_OMIT_TIGON_I is not set
+CONFIG_DL2K=m
+CONFIG_E1000=m
+CONFIG_E1000_NAPI=y
+CONFIG_NS83820=m
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+CONFIG_R8169=m
+CONFIG_R8169_NAPI=y
+CONFIG_SK98LIN=m
+CONFIG_TIGON3=m
+
+#
+# Ethernet (10000 Mbit)
+#
+CONFIG_IXGB=m
+CONFIG_IXGB_NAPI=y
+CONFIG_S2IO=m
+CONFIG_S2IO_NAPI=y
+CONFIG_FDDI=y
+# CONFIG_DEFXX is not set
+# CONFIG_SKFP is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PLIP is not set
+CONFIG_PPP=m
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_ASYNC=m
+CONFIG_PPP_SYNC_TTY=m
+CONFIG_PPP_DEFLATE=m
+CONFIG_IPPP_FILTER=y
+# CONFIG_PPP_BSDCOMP is not set
+CONFIG_PPPOE=m
+# CONFIG_SLIP is not set
+
+#
+# Wireless LAN (non-hamradio)
+#
+CONFIG_NET_RADIO=y
+
+#
+# Obsolete Wireless cards support (pre-802.11)
+#
+# CONFIG_STRIP is not set
+# CONFIG_ARLAN is not set
+CONFIG_WAVELAN=m
+CONFIG_PCMCIA_WAVELAN=m
+CONFIG_PCMCIA_NETWAVE=m
+
+#
+# Wireless 802.11 Frequency Hopping cards support
+#
+# CONFIG_PCMCIA_RAYCS is not set
+
+#
+# Wireless 802.11b ISA/PCI cards support
+#
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
+CONFIG_AIRO=m
+CONFIG_HERMES=m
+CONFIG_PLX_HERMES=m
+CONFIG_TMD_HERMES=m
+CONFIG_PCI_HERMES=m
+CONFIG_ATMEL=m
+CONFIG_PCI_ATMEL=m
+CONFIG_PRISM54=m
+
+#
+# Wireless 802.11b Pcmcia/Cardbus cards support
+#
+CONFIG_PCMCIA_HERMES=m
+CONFIG_AIRO_CS=m
+CONFIG_PCMCIA_ATMEL=m
+CONFIG_PCMCIA_WL3501=m
+CONFIG_NET_WIRELESS=y
+
+#
+# Token Ring devices
+#
+CONFIG_TR=y
+CONFIG_IBMOL=m
+CONFIG_3C359=m
+CONFIG_TMS380TR=m
+CONFIG_TMSPCI=m
+CONFIG_ABYSS=m
+CONFIG_IBMTR=m
+CONFIG_IBMLS=m
+CONFIG_SKISA=m
+CONFIG_PROTEON=m
+CONFIG_SMCTR=m
+CONFIG_PCMCIA_IBMTR=m
+
+
+CONFIG_NET_FC=y
+# CONFIG_SHAPER is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+
+#
+# PCMCIA network device support
+#
+CONFIG_NET_PCMCIA=y
+CONFIG_PCMCIA_3C589=m
+CONFIG_PCMCIA_3C574=m
+CONFIG_PCMCIA_FMVJ18X=m
+CONFIG_PCMCIA_PCNET=m
+CONFIG_PCMCIA_NMCLAN=m
+CONFIG_PCMCIA_SMC91C92=m
+CONFIG_PCMCIA_XIRC2PS=m
+CONFIG_PCMCIA_AXNET=m
+
+#
+# Amateur Radio support
+#
+# CONFIG_HAMRADIO is not set
+
+#
+# IrDA (infrared) support
+#
+# CONFIG_IRDA is not set
+# CONFIG_IRDA is not set
+# CONFIG_IRDA_DEBUG is not set
+CONFIG_IRLAN=m
+CONFIG_IRNET=m
+CONFIG_IRCOMM=m
+# CONFIG_IRDA_ULTRA is not set
+CONFIG_IRDA_CACHE_LAST_LSAP=y
+CONFIG_IRDA_FAST_RR=y
+CONFIG_IRTTY_SIR=m
+CONFIG_DONGLE=y
+CONFIG_ESI_DONGLE=m
+CONFIG_ACTISYS_DONGLE=m
+CONFIG_TEKRAM_DONGLE=m
+CONFIG_IRPORT_SIR=m
+# CONFIG_DONGLE_OLD is not set
+CONFIG_LITELINK_DONGLE=m
+CONFIG_MA600_DONGLE=m
+CONFIG_GIRBIL_DONGLE=m
+CONFIG_MCP2120_DONGLE=m
+CONFIG_OLD_BELKIN_DONGLE=m
+CONFIG_ACT200L_DONGLE=m
+
+CONFIG_USB_IRDA=m
+CONFIG_NSC_FIR=m
+CONFIG_SIGMATEL_FIR=m
+# CONFIG_WINBOND_FIR is not set
+# CONFIG_TOSHIBA_FIR is not set
+# CONFIG_SMC_IRCC_FIR is not set
+# CONFIG_ALI_FIR is not set
+# CONFIG_VLSI_FIR is not set
+# CONFIG_VIA_FIR is not set
+
+
+
+#
+# Bluetooth support
+#
+CONFIG_BT=m
+CONFIG_BT_L2CAP=m
+CONFIG_BT_SCO=m
+CONFIG_BT_CMTP=m
+CONFIG_BT_RFCOMM=m
+CONFIG_BT_RFCOMM_TTY=y
+CONFIG_BT_BNEP=m
+CONFIG_BT_BNEP_MC_FILTER=y
+CONFIG_BT_BNEP_PROTO_FILTER=y
+CONFIG_BT_HIDP=m
+
+#
+# Bluetooth device drivers
+#
+CONFIG_BT_HCIUSB=m
+CONFIG_BT_HCIUART=m
+CONFIG_BT_HCIUART_H4=y
+CONFIG_BT_HCIUART_BCSP=y
+CONFIG_BT_HCIUART_BCSP_TXCRC=y
+CONFIG_BT_HCIDTL1=m
+CONFIG_BT_HCIBT3C=m
+CONFIG_BT_HCIBLUECARD=m
+CONFIG_BT_HCIBTUART=m
+CONFIG_BT_HCIVHCI=m
+CONFIG_BT_HCIUSB_SCO=y
+CONFIG_BT_HCIBCM203X=m
+CONFIG_BT_HCIBFUSB=m
+CONFIG_USB_BLUETOOTH_TTY=m
+
+#
+# ISDN subsystem
+#
+
+CONFIG_ISDN=m
+CONFIG_ISDN_I4L=m
+CONFIG_ISDN_DRV_AVMB1_B1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCI=m
+CONFIG_ISDN_DRV_AVMB1_T1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCMCIA=m
+CONFIG_ISDN_DRV_AVMB1_T1PCI=m
+CONFIG_ISDN_DRV_AVMB1_C4=m
+
+CONFIG_ISDN_PPP=y
+CONFIG_ISDN_PPP_VJ=y
+CONFIG_ISDN_MPP=y
+# CONFIG_ISDN_PPP_BSDCOMP is not set
+CONFIG_ISDN_TTY_FAX=y
+CONFIG_DE_AOC=y
+
+CONFIG_ISDN_AUDIO=y
+
+CONFIG_ISDN_DRV_HISAX=m
+CONFIG_ISDN_DRV_ICN=m
+CONFIG_ISDN_DRV_PCBIT=m
+CONFIG_ISDN_DRV_SC=m
+CONFIG_ISDN_DRV_ACT2000=m
+CONFIG_ISDN_DRV_TPAM=m
+CONFIG_ISDN_DRV_AVMB1_B1PCIV4=y
+CONFIG_ISDN_DRV_AVMB1_AVM_CS=m
+
+CONFIG_ISDN_CAPI_CAPIDRV=m
+
+CONFIG_HISAX_EURO=y
+CONFIG_HISAX_1TR6=y
+CONFIG_HISAX_NI1=y
+CONFIG_HISAX_MAX_CARDS=8
+CONFIG_HISAX_16_0=y
+CONFIG_HISAX_16_3=y
+CONFIG_HISAX_TELESPCI=y
+CONFIG_HISAX_S0BOX=y
+CONFIG_HISAX_AVM_A1=y
+CONFIG_HISAX_FRITZPCI=y
+CONFIG_HISAX_AVM_A1_PCMCIA=y
+CONFIG_HISAX_ELSA=y
+CONFIG_HISAX_IX1MICROR2=y
+CONFIG_HISAX_DIEHLDIVA=y
+CONFIG_HISAX_ASUSCOM=y
+CONFIG_HISAX_TELEINT=y
+CONFIG_HISAX_HFCS=y
+CONFIG_HISAX_SEDLBAUER=y
+CONFIG_HISAX_SPORTSTER=y
+CONFIG_HISAX_MIC=y
+CONFIG_HISAX_NETJET=y
+CONFIG_HISAX_NETJET_U=y
+CONFIG_HISAX_NICCY=y
+CONFIG_HISAX_ISURF=y
+CONFIG_HISAX_HSTSAPHIR=y
+CONFIG_HISAX_BKM_A4T=y
+CONFIG_HISAX_SCT_QUADRO=y
+CONFIG_HISAX_GAZEL=y
+CONFIG_HISAX_HFC_PCI=y
+CONFIG_HISAX_W6692=y
+CONFIG_HISAX_HFC_SX=y
+CONFIG_HISAX_ENTERNOW_PCI=y
+# CONFIG_HISAX_DEBUG is not set
+CONFIG_HISAX_AVM_A1_CS=m
+CONFIG_HISAX_ST5481=m
+CONFIG_HISAX_HFCUSB=m
+CONFIG_HISAX_FRITZ_PCIPNP=m
+CONFIG_HISAX_NO_SENDCOMPLETE=y
+CONFIG_HISAX_NO_LLC=y
+CONFIG_HISAX_NO_KEYPAD=y
+CONFIG_HISAX_SEDLBAUER_CS=m
+CONFIG_HISAX_ELSA_CS=m
+CONFIG_HISAX_TELES_CS=m
+
+CONFIG_ISDN_DRV_LOOP=m
+CONFIG_HYSDN=m
+CONFIG_HYSDN_CAPI=y
+
+
+#
+# CAPI subsystem
+#
+CONFIG_ISDN_CAPI=m
+CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON=y
+CONFIG_ISDN_CAPI_MIDDLEWARE=y
+CONFIG_ISDN_CAPI_CAPI20=m
+CONFIG_ISDN_CAPI_CAPIFS_BOOL=y
+CONFIG_ISDN_CAPI_CAPIFS=m
+
+#
+# CAPI hardware drivers
+#
+
+#
+# Active AVM cards
+#
+CONFIG_CAPI_AVM=y
+
+#
+# Active Eicon DIVA Server cards
+#
+# CONFIG_CAPI_EICON is not set
+CONFIG_ISDN_DIVAS=m
+CONFIG_ISDN_DIVAS_BRIPCI=y
+CONFIG_ISDN_DIVAS_PRIPCI=y
+CONFIG_ISDN_DIVAS_DIVACAPI=m
+CONFIG_ISDN_DIVAS_USERIDI=m
+CONFIG_ISDN_DIVAS_MAINT=m
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+CONFIG_INPUT_JOYDEV=m
+# CONFIG_INPUT_TSDEV is not set
+CONFIG_INPUT_EVDEV=y
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input I/O drivers
+#
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=m
+CONFIG_GAMEPORT_NS558=m
+CONFIG_GAMEPORT_L4=m
+CONFIG_GAMEPORT_EMU10K1=m
+CONFIG_GAMEPORT_VORTEX=m
+CONFIG_GAMEPORT_FM801=m
+CONFIG_GAMEPORT_CS461x=m
+CONFIG_SERIO=y
+CONFIG_SERIO_I8042=y
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_RAW is not set
+
+# CONFIG_SERIO_CT82C710 is not set
+# CONFIG_SERIO_PARKBD is not set
+# CONFIG_SERIO_PCIPS2 is not set
+
+#
+# Input Device Drivers
+#
+CONFIG_INPUT_KEYBOARD=y
+CONFIG_KEYBOARD_ATKBD=y
+# CONFIG_KEYBOARD_SUNKBD is not set
+# CONFIG_KEYBOARD_XTKBD is not set
+# CONFIG_KEYBOARD_NEWTON is not set
+# CONFIG_KEYBOARD_LKKBD is not set
+CONFIG_INPUT_MOUSE=y
+CONFIG_MOUSE_PS2=y
+CONFIG_MOUSE_SERIAL=m
+CONFIG_MOUSE_INPORT=m
+CONFIG_MOUSE_ATIXL=y
+CONFIG_MOUSE_LOGIBM=m
+CONFIG_MOUSE_PC110PAD=m
+CONFIG_MOUSE_VSXXXAA=m
+CONFIG_INPUT_JOYSTICK=y
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+CONFIG_JOYSTICK_JOYDUMP=m
+CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_GUNZE=m
+CONFIG_INPUT_MISC=y
+CONFIG_INPUT_PCSPKR=m
+CONFIG_INPUT_UINPUT=m 
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+CONFIG_SERIAL_NONSTANDARD=y
+# CONFIG_ROCKETPORT is not set
+# CONFIG_SYNCLINK is not set
+# CONFIG_SYNCLINKMP is not set
+CONFIG_N_HDLC=m
+CONFIG_STALDRV=y
+# CONFIG_FTAPE is not set
+# CONFIG_IBM_ASM is not set
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_CS=m
+# CONFIG_SERIAL_8250_ACPI is not set
+CONFIG_SERIAL_8250_NR_UARTS=4
+CONFIG_SERIAL_8250_EXTENDED=y
+# CONFIG_SERIAL_8250_MANY_PORTS is not set
+CONFIG_SERIAL_8250_SHARE_IRQ=y
+CONFIG_SERIAL_8250_DETECT_IRQ=y
+CONFIG_SERIAL_8250_MULTIPORT=y
+CONFIG_SERIAL_8250_RSA=y
+# CONFIG_COMPUTONE is not set
+# CONFIG_CYCLADES is not set
+# CONFIG_DIGIEPCA is not set
+# CONFIG_DIGI is not set
+# CONFIG_ESPSERIAL is not set
+# CONFIG_MOXA_INTELLIO is not set
+# CONFIG_MOXA_SMARTIO is not set
+# CONFIG_ISI is not set
+# CONFIG_RISCOM8 is not set
+# CONFIG_SPECIALIX is not set
+# CONFIG_SX is not set
+# CONFIG_RIO is not set
+# CONFIG_STALLION is not set
+# CONFIG_ISTALLION is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+# CONFIG_LEGACY_PTYS is not set
+CONFIG_PRINTER=m
+CONFIG_LP_CONSOLE=y
+CONFIG_PPDEV=m
+# CONFIG_TIPAR is not set
+
+#
+# I2C support
+#
+CONFIG_I2C=m
+CONFIG_I2C_CHARDEV=m
+
+#
+# I2C Algorithms
+#
+# CONFIG_I2C_DEBUG_ALGO is not set
+CONFIG_I2C_ALGOBIT=m
+CONFIG_I2C_ALGOPCF=m
+
+#
+# I2C Hardware Bus support
+#
+CONFIG_I2C_ALI1535=m
+CONFIG_I2C_ALI15X3=m
+CONFIG_I2C_AMD756=m
+CONFIG_I2C_AMD8111=m
+CONFIG_I2C_I801=m
+CONFIG_I2C_I810=m
+CONFIG_I2C_ISA=m
+CONFIG_I2C_NFORCE2=m
+CONFIG_I2C_PIIX4=m
+CONFIG_I2C_PROSAVAGE=m
+CONFIG_I2C_SAVAGE4=m
+# CONFIG_SCx200_ACB is not set
+CONFIG_I2C_SIS5595=m
+CONFIG_I2C_SIS630=m
+CONFIG_I2C_SIS96X=m
+CONFIG_I2C_VIA=m
+CONFIG_I2C_VIAPRO=m
+CONFIG_I2C_VOODOO3=m
+# CONFIG_I2C_ELEKTOR is not set
+CONFIG_I2C_PARPORT=m
+CONFIG_I2C_PARPORT_LIGHT=m
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+# CONFIG_I2C_PARPORT is not set
+CONFIG_I2C_ALI1563=m
+# CONFIG_I2C_PARPORT_LIGHT is not set
+CONFIG_I2C_ALGOPCA=m
+# CONFIG_I2C_PCA_ISA is not set
+
+
+#
+# I2C Hardware Sensors Chip support
+#
+CONFIG_I2C_SENSOR=m
+CONFIG_SENSORS_ADM1021=m
+CONFIG_SENSORS_EEPROM=m
+CONFIG_SENSORS_IT87=m
+CONFIG_SENSORS_LM75=m
+CONFIG_SENSORS_LM78=m
+CONFIG_SENSORS_LM80=m
+CONFIG_SENSORS_LM83=m
+CONFIG_SENSORS_LM85=m
+CONFIG_SENSORS_VIA686A=m
+CONFIG_SENSORS_W83781D=m
+CONFIG_SENSORS_ASB100=m
+CONFIG_SENSORS_LM90=m
+CONFIG_SENSORS_W83L785TS=m
+CONFIG_SENSORS_FSCHER=m
+CONFIG_SENSORS_GL518SM=m
+CONFIG_SENSORS_DS1621=m
+CONFIG_SENSORS_W83627HF=m
+CONFIG_SENSORS_PCF8574=m
+CONFIG_SENSORS_PCF8591=m
+CONFIG_SENSORS_RTC8564=m
+CONFIG_SENSORS_MAX1619=m
+CONFIG_SENSORS_ADM1025=m
+CONFIG_SENSORS_ADM1031=m
+CONFIG_SENSORS_LM77=m
+CONFIG_SENSORS_SMSC47M1=m
+
+# CONFIG_W1 is not set
+
+#
+# Mice
+#
+CONFIG_CRASH=m
+
+#
+# IPMI
+#
+CONFIG_IPMI_HANDLER=m
+# CONFIG_IPMI_PANIC_EVENT is not set
+CONFIG_IPMI_DEVICE_INTERFACE=m
+CONFIG_IPMI_WATCHDOG=m
+CONFIG_IPMI_SI=m
+CONFIG_IPMI_POWEROFF=m
+
+#
+# Watchdog Cards
+#
+CONFIG_WATCHDOG=y
+# CONFIG_WATCHDOG_NOWAYOUT is not set
+CONFIG_SOFT_WATCHDOG=m
+CONFIG_WDT=m
+# CONFIG_WDT_501 is not set
+CONFIG_WDTPCI=m
+CONFIG_WDT_501_PCI=y
+CONFIG_PCWATCHDOG=m
+CONFIG_ACQUIRE_WDT=m
+CONFIG_ADVANTECH_WDT=m
+CONFIG_EUROTECH_WDT=m
+CONFIG_IB700_WDT=m
+CONFIG_I8XX_TCO=m
+# CONFIG_MIXCOMWD is not set
+# CONFIG_SCx200_WDT is not set
+# CONFIG_60XX_WDT is not set
+CONFIG_W83877F_WDT=m
+CONFIG_W83627HF_WDT=m
+CONFIG_MACHZ_WDT=m
+CONFIG_SC520_WDT=m
+CONFIG_ALIM7101_WDT=m
+CONFIG_ALIM1535_WDT=m
+CONFIG_SC1200_WDT=m
+CONFIG_WAFER_WDT=m
+CONFIG_CPU5_WDT=m
+CONFIG_PCIPCWATCHDOG=m
+CONFIG_USBPCWATCHDOG=m
+
+
+CONFIG_HW_RANDOM=m
+# CONFIG_NVRAM is not set
+CONFIG_RTC=y
+CONFIG_DTLK=m
+# CONFIG_R3964 is not set
+# CONFIG_APPLICOM is not set
+# CONFIG_SONYPI is not set
+
+#
+# Ftape, the floppy tape device driver
+#
+CONFIG_AGP=y
+CONFIG_AGP_ALI=y
+CONFIG_AGP_ATI=y
+CONFIG_AGP_AMD=y
+CONFIG_AGP_AMD64=y
+CONFIG_AGP_INTEL=y
+CONFIG_AGP_INTEL_MCH=y
+CONFIG_AGP_NVIDIA=y
+CONFIG_AGP_SIS=y
+CONFIG_AGP_SWORKS=y
+CONFIG_AGP_VIA=y
+CONFIG_AGP_EFFICEON=y
+CONFIG_DRM=y
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+CONFIG_DRM_R128=m
+CONFIG_DRM_RADEON=m
+CONFIG_DRM_I810=m
+CONFIG_DRM_I830=m
+CONFIG_DRM_MGA=m
+# CONFIG_DRM_SIS is not set
+CONFIG_DRM_I915=m
+
+
+
+#
+# PCMCIA character devices
+#
+# CONFIG_SYNCLINK_CS is not set
+
+
+
+# CONFIG_MWAVE is not set
+CONFIG_RAW_DRIVER=y
+CONFIG_MAX_RAW_DEVS=8192
+CONFIG_HANGCHECK_TIMER=m
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Video For Linux
+#
+
+#
+# Video Adapters
+#
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+CONFIG_VIDEO_OVCAMCHIP=m
+
+
+#
+# Radio Adapters
+#
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+CONFIG_DVB_CORE=m
+
+#
+# Supported Frontend Modules
+#
+CONFIG_DVB_STV0299=m
+# CONFIG_DVB_SP887X is not set
+# CONFIG_DVB_ALPS_TDLB7 is not set
+CONFIG_DVB_ALPS_TDMB7=m
+CONFIG_DVB_ATMEL_AT76C651=m
+CONFIG_DVB_CX24110=m
+CONFIG_DVB_GRUNDIG_29504_491=m
+CONFIG_DVB_GRUNDIG_29504_401=m
+CONFIG_DVB_MT312=m
+CONFIG_DVB_VES1820=m
+CONFIG_DVB_VES1X93=m
+CONFIG_DVB_TWINHAN_DST=m
+CONFIG_DVB_TTUSB_DEC=m
+CONFIG_DVB_BT8XX=m
+# CONFIG_DVB_TDA1004X is not set
+CONFIG_DVB_NXT6000=m
+
+#
+# Supported SAA7146 based PCI Adapters
+#
+CONFIG_DVB_AV7110=m
+CONFIG_DVB_AV7110_OSD=y
+# CONFIG_DVB_AV7110_FIRMWARE is not set
+CONFIG_DVB_BUDGET=m
+CONFIG_DVB_BUDGET_CI=m
+CONFIG_DVB_BUDGET_AV=m
+CONFIG_DVB_BUDGET_PATCH=m
+
+#
+# Supported USB Adapters
+#
+CONFIG_DVB_TTUSB_BUDGET=m
+
+#
+# Supported FlexCopII (B2C2) Adapters
+#
+CONFIG_DVB_B2C2_SKYSTAR=m
+CONFIG_VIDEO_SAA7146=m
+CONFIG_VIDEO_SAA7146_VV=m
+CONFIG_VIDEO_VIDEOBUF=m
+CONFIG_VIDEO_TUNER=m
+CONFIG_VIDEO_BUF=m
+CONFIG_VIDEO_BTCX=m
+
+#
+# Graphics support
+#
+CONFIG_FB=y
+# CONFIG_FB_CYBER2000 is not set
+# CONFIG_FB_IMSTT is not set
+CONFIG_FB_VGA16=m
+CONFIG_FB_VESA=y
+CONFIG_VIDEO_SELECT=y
+# CONFIG_FB_HGA is not set
+CONFIG_FB_RIVA=m
+# CONFIG_FB_RIVA_DEBUG is not set
+# CONFIG_FB_RIVA_I2C is not set
+CONFIG_FB_I810=m
+CONFIG_FB_I810_GTF=y
+# CONFIG_FB_MATROX is not set
+CONFIG_FB_MATROX_MILLENIUM=y
+CONFIG_FB_MATROX_MYSTIQUE=y
+CONFIG_FB_MATROX_G450=y
+CONFIG_FB_MATROX_G100=y
+CONFIG_FB_MATROX_I2C=m
+CONFIG_FB_MATROX_MAVEN=m
+CONFIG_FB_MATROX_MULTIHEAD=y
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_RADEON_DEBUG is not set
+# CONFIG_FB_RADEON_OLD is not set
+CONFIG_FB_RADEON_I2C=y
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_ATY is not set
+CONFIG_FB_ATY_CT=y
+CONFIG_FB_ATY_GX=y
+# CONFIG_FB_ATY_XL_INIT is not set
+# CONFIG_FB_SIS is not set
+CONFIG_FB_SIS_300=y
+CONFIG_FB_SIS_315=y
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VIRTUAL is not set
+CONFIG_FB_KYRO=m
+# CONFIG_FB_PM2 is not set
+# CONFIG_FB_PM2_FIFO_DISCONNECT is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+CONFIG_FB_CIRRUS=m
+
+#
+# Console display driver support
+#
+CONFIG_VGA_CONSOLE=y
+# CONFIG_MDA_CONSOLE is not set
+CONFIG_DUMMY_CONSOLE=y
+CONFIG_FRAMEBUFFER_CONSOLE=y
+# CONFIG_FONTS is not set
+
+
+#
+# Logo configuration
+#
+CONFIG_LOGO=y
+# CONFIG_LOGO_LINUX_MONO is not set
+# CONFIG_LOGO_LINUX_VGA16 is not set
+CONFIG_LOGO_LINUX_CLUT224=y
+
+#
+# Sound
+#
+CONFIG_SOUND=m
+
+#
+# Advanced Linux Sound Architecture
+#
+CONFIG_SND=m
+CONFIG_SND_SEQUENCER=m
+CONFIG_SND_SEQ_DUMMY=m
+CONFIG_SND_OSSEMUL=y
+CONFIG_SND_MIXER_OSS=m
+CONFIG_SND_PCM_OSS=m
+CONFIG_SND_SEQUENCER_OSS=y
+CONFIG_SND_RTCTIMER=m
+# CONFIG_SND_VERBOSE_PRINTK is not set
+# CONFIG_SND_DEBUG is not set
+CONFIG_SND_BIT32_EMUL=y
+
+#
+# Generic devices
+#
+CONFIG_SND_DUMMY=m
+CONFIG_SND_VIRMIDI=m
+CONFIG_SND_MTPAV=m
+# CONFIG_SND_SERIAL_U16550 is not set
+CONFIG_SND_MPU401=m
+
+#
+# ISA devices
+#
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+
+#
+# PCI devices
+#
+CONFIG_SND_ALI5451=m
+CONFIG_SND_AZT3328=m
+CONFIG_SND_CS46XX=m
+CONFIG_SND_CS46XX_NEW_DSP=y
+CONFIG_SND_CS4281=m
+CONFIG_SND_EMU10K1=m
+CONFIG_SND_KORG1212=m
+CONFIG_SND_NM256=m
+CONFIG_SND_RME32=m
+CONFIG_SND_RME96=m
+CONFIG_SND_RME9652=m
+CONFIG_SND_HDSP=m
+CONFIG_SND_TRIDENT=m
+CONFIG_SND_YMFPCI=m
+CONFIG_SND_ALS4000=m
+CONFIG_SND_CMIPCI=m
+CONFIG_SND_ENS1370=m
+CONFIG_SND_ENS1371=m
+CONFIG_SND_ES1938=m
+CONFIG_SND_ES1968=m
+CONFIG_SND_MAESTRO3=m
+CONFIG_SND_FM801=m
+CONFIG_SND_ICE1712=m
+CONFIG_SND_ICE1724=m
+CONFIG_SND_INTEL8X0=m
+CONFIG_SND_SONICVIBES=m
+CONFIG_SND_VIA82XX=m
+CONFIG_SND_VX222=m
+CONFIG_SND_BT87X=m
+CONFIG_SND_ATIIXP=m
+CONFIG_SND_ATIIXP_MODEM=m
+CONFIG_SND_AU8810=m
+CONFIG_SND_AU8820=m
+CONFIG_SND_AU8830=m
+CONFIG_SND_MIXART=m
+CONFIG_SND_FM801_TEA575X=m
+CONFIG_SND_INTEL8X0M=m
+CONFIG_SND_PDAUDIOCF=m
+
+
+#
+# ALSA USB devices
+#
+CONFIG_SND_USB_AUDIO=m
+CONFIG_SND_USB_USX2Y=m
+
+#
+# PCMCIA devices
+#
+# CONFIG_SND_VXPOCKET is not set
+# CONFIG_SND_VXP440 is not set
+
+#
+# Open Sound System
+#
+# CONFIG_SOUND_PRIME is not set
+# CONFIG_SOUND_BT878 is not set
+# CONFIG_SOUND_CMPCI is not set
+
+#
+# USB support
+#
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+CONFIG_USB_DEVICEFS=y
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+CONFIG_USB_SUSPEND=y
+
+#
+# USB Host Controller Drivers
+#
+CONFIG_USB_EHCI_HCD=m
+CONFIG_USB_EHCI_SPLIT_ISO=y
+CONFIG_USB_EHCI_ROOT_HUB_TT=y
+CONFIG_USB_OHCI_HCD=m
+CONFIG_USB_UHCI_HCD=m
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_AUDIO is not set
+
+#
+# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem
+#
+CONFIG_USB_MIDI=m
+CONFIG_USB_ACM=m
+CONFIG_USB_PRINTER=m
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_USB_STORAGE=m
+# CONFIG_USB_STORAGE_DEBUG is not set
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_DPCM=y
+CONFIG_USB_STORAGE_HP8200e=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_RW_DETECT=y
+
+#
+# USB Human Interface Devices (HID)
+#
+CONFIG_USB_HID=y
+CONFIG_USB_HIDINPUT=y
+CONFIG_HID_FF=y
+CONFIG_HID_PID=y
+CONFIG_LOGITECH_FF=y
+CONFIG_THRUSTMASTER_FF=y
+CONFIG_USB_HIDDEV=y
+
+#
+# USB HID Boot Protocol drivers
+#
+# CONFIG_USB_KBD is not set
+# CONFIG_USB_MOUSE is not set
+CONFIG_USB_AIPTEK=m
+CONFIG_USB_WACOM=m
+CONFIG_USB_KBTAB=m
+CONFIG_USB_POWERMATE=m
+CONFIG_USB_XPAD=m
+
+#
+# USB Imaging devices
+#
+CONFIG_USB_MDC800=m
+CONFIG_USB_MICROTEK=m
+CONFIG_USB_HPUSBSCSI=m
+
+#
+# USB Multimedia devices
+#
+CONFIG_USB_DABUSB=m
+CONFIG_USB_VICAM=m
+CONFIG_USB_DSBR=m
+CONFIG_USB_IBMCAM=m
+CONFIG_USB_KONICAWC=m
+CONFIG_USB_OV511=m
+CONFIG_USB_SE401=m
+CONFIG_USB_STV680=m
+CONFIG_USB_SN9C102=m
+
+#
+# USB Network adaptors
+#
+CONFIG_USB_CATC=m
+CONFIG_USB_KAWETH=m
+CONFIG_USB_PEGASUS=m
+CONFIG_USB_RTL8150=m
+CONFIG_USB_USBNET=m
+CONFIG_USB_SPEEDTOUCH=m
+
+#
+# USB Host-to-Host Cables
+#
+CONFIG_USB_AN2720=y
+CONFIG_USB_BELKIN=y
+CONFIG_USB_GENESYS=y
+CONFIG_USB_NET1080=y
+CONFIG_USB_PL2301=y
+
+#
+# Intelligent USB Devices/Gadgets
+#
+CONFIG_USB_ARMLINUX=y
+CONFIG_USB_EPSON2888=y
+CONFIG_USB_ZAURUS=y
+CONFIG_USB_CDCETHER=y
+
+#
+# USB Network Adapters
+#
+CONFIG_USB_AX8817X=y
+
+#
+# USB port drivers
+#
+CONFIG_USB_USS720=m
+
+#
+# USB Serial Converter support
+#
+CONFIG_USB_SERIAL=m
+CONFIG_USB_SERIAL_GENERIC=y
+CONFIG_USB_SERIAL_BELKIN=m
+CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m
+CONFIG_USB_SERIAL_EMPEG=m
+CONFIG_USB_SERIAL_FTDI_SIO=m
+CONFIG_USB_SERIAL_VISOR=m
+CONFIG_USB_SERIAL_IPAQ=m
+CONFIG_USB_SERIAL_IR=m
+CONFIG_USB_SERIAL_EDGEPORT=m
+CONFIG_USB_SERIAL_EDGEPORT_TI=m
+CONFIG_USB_SERIAL_KEYSPAN_PDA=m
+CONFIG_USB_SERIAL_KEYSPAN=m
+CONFIG_USB_SERIAL_KEYSPAN_MPR=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XA=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XB=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19=y
+CONFIG_USB_SERIAL_KEYSPAN_USA18X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QW=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QI=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y
+CONFIG_USB_SERIAL_KLSI=m
+CONFIG_USB_SERIAL_KOBIL_SCT=m
+CONFIG_USB_SERIAL_MCT_U232=m
+CONFIG_USB_SERIAL_PL2303=m
+CONFIG_USB_SERIAL_SAFE=m
+CONFIG_USB_SERIAL_SAFE_PADDED=y
+CONFIG_USB_SERIAL_CYBERJACK=m
+CONFIG_USB_SERIAL_XIRCOM=m
+CONFIG_USB_SERIAL_OMNINET=m
+CONFIG_USB_SERIAL_WHITEHEAT=m
+CONFIG_USB_EZUSB=y
+CONFIG_USB_EMI62=m
+CONFIG_USB_LED=m
+CONFIG_USB_G_SERIAL=m
+
+
+#
+# USB Miscellaneous drivers
+#
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_TIGL is not set
+CONFIG_USB_AUERSWALD=m
+CONFIG_USB_RIO500=m
+CONFIG_USB_LCD=m
+CONFIG_USB_TEST=m
+# CONFIG_USB_GADGET is not set
+# CONFIG_USB_GADGET_PXA2XX is not set
+# CONFIG_USB_GADGET_GOKU is not set
+# CONFIG_USB_GADGET_SA1100 is not set
+CONFIG_USB_ZERO=m
+CONFIG_USB_ETH=m
+CONFIG_USB_GADGETFS=m
+CONFIG_USB_W9968CF=m
+CONFIG_USB_PWC=m
+CONFIG_USB_LEGOTOWER=m
+CONFIG_USB_FILE_STORAGE=m
+# CONFIG_USB_FILE_STORAGE_TEST is not set
+CONFIG_USB_MTOUCH=m
+CONFIG_USB_ATI_REMOTE=m
+CONFIG_USB_ALI_M5632=y
+# CONFIG_USB_CYTHERM is not set
+CONFIG_USB_EGALAX=m
+CONFIG_USB_PHIDGETSERVO=m
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT2_FS_POSIX_ACL=y
+CONFIG_EXT2_FS_SECURITY=y
+CONFIG_EXT3_FS=m
+CONFIG_EXT3_FS_XATTR=y
+CONFIG_EXT3_FS_POSIX_ACL=y
+CONFIG_EXT3_FS_SECURITY=y
+CONFIG_JBD=m
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_REISERFS_CHECK is not set
+CONFIG_REISERFS_PROC_INFO=y
+CONFIG_REISERFS_FS_XATTR=y
+CONFIG_REISERFS_FS_POSIX_ACL=y
+CONFIG_REISERFS_FS_SECURITY=y
+# CONFIG_JFS_FS is not set
+# CONFIG_JFS_DEBUG is not set
+# CONFIG_JFS_STATISTICS is not set
+CONFIG_JFS_POSIX_ACL=y
+# CONFIG_XFS_FS is not set
+# CONFIG_XFS_RT is not set
+CONFIG_XFS_QUOTA=y
+CONFIG_XFS_POSIX_ACL=y
+CONFIG_XFS_SECURITY=y
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_QUOTA=y
+# CONFIG_QFMT_V1 is not set
+CONFIG_QFMT_V2=y
+CONFIG_QUOTACTL=y
+# CONFIG_AUTOFS_FS is not set
+CONFIG_AUTOFS4_FS=m
+
+#
+# CD-ROM/DVD Filesystems
+#
+CONFIG_ISO9660_FS=y
+CONFIG_JOLIET=y
+CONFIG_ZISOFS=y
+CONFIG_ZISOFS_FS=y
+CONFIG_UDF_FS=m
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=m
+CONFIG_MSDOS_FS=m
+CONFIG_VFAT_FS=m
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="ascii"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+# CONFIG_DEVFS_FS is not set
+CONFIG_DEVPTS_FS_XATTR=y
+CONFIG_DEVPTS_FS_SECURITY=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_XATTR=y
+CONFIG_TMPFS_SECURITY=y
+CONFIG_HUGETLBFS=y
+CONFIG_HUGETLB_PAGE=y
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not seta
+# CONFIG_AFFS_FS is not set
+# uses sleepon and needs a major update
+CONFIG_HFS_FS=m
+CONFIG_HFSPLUS_FS=m
+# CONFIG_BEFS_FS is not set
+# CONFIG_BEFS_DEBUG is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_JFFS_FS is not set
+CONFIG_JFFS2_FS=m
+CONFIG_JFFS2_FS_DEBUG=0
+CONFIG_JFFS2_FS_NAND=y
+CONFIG_CRAMFS=m
+CONFIG_VXFS_FS=m
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_QNX4FS_RW is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_UFS_FS_WRITE is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=m
+CONFIG_NFS_V3=y
+CONFIG_NFS_V4=y
+CONFIG_NFS_DIRECTIO=y
+CONFIG_NFSD=m
+CONFIG_NFSD_V3=y
+CONFIG_NFSD_V4=y
+CONFIG_NFSD_TCP=y
+CONFIG_LOCKD=m
+CONFIG_LOCKD_V4=y
+CONFIG_EXPORTFS=m
+CONFIG_SUNRPC=m
+CONFIG_SUNRPC_GSS=m
+CONFIG_RPCSEC_GSS_KRB5=m
+CONFIG_RPCSEC_GSS_SPKM3=m
+CONFIG_SMB_FS=m
+# CONFIG_SMB_NLS_DEFAULT is not set
+CONFIG_CIFS=m
+# CONFIG_CIFS_STATS is not set
+CONFIG_CIFS_XATTR=y
+CONFIG_CIFS_POSIX=y
+# CONFIG_NCP_FS is not set
+CONFIG_NCPFS_PACKET_SIGNING=y
+CONFIG_NCPFS_IOCTL_LOCKING=y
+CONFIG_NCPFS_STRONG=y
+CONFIG_NCPFS_NFS_NS=y
+CONFIG_NCPFS_OS2_NS=y
+CONFIG_NCPFS_SMALLDOS=y
+CONFIG_NCPFS_NLS=y
+CONFIG_NCPFS_EXTRAS=y
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+# CONFIG_RXRPC is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_ACORN_PARTITION is not set
+CONFIG_OSF_PARTITION=y
+# CONFIG_AMIGA_PARTITION is not set
+# CONFIG_ATARI_PARTITION is not set
+CONFIG_MAC_PARTITION=y
+CONFIG_MSDOS_PARTITION=y
+CONFIG_BSD_DISKLABEL=y
+CONFIG_MINIX_SUBPARTITION=y
+CONFIG_SOLARIS_X86_PARTITION=y
+CONFIG_UNIXWARE_DISKLABEL=y
+# CONFIG_LDM_PARTITION is not set
+CONFIG_SGI_PARTITION=y
+# CONFIG_ULTRIX_PARTITION is not set
+CONFIG_SUN_PARTITION=y
+CONFIG_EFI_PARTITION=y
+CONFIG_NLS=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS_DEFAULT="utf8"
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_CODEPAGE_737=m
+CONFIG_NLS_CODEPAGE_775=m
+CONFIG_NLS_CODEPAGE_850=m
+CONFIG_NLS_CODEPAGE_852=m
+CONFIG_NLS_CODEPAGE_855=m
+CONFIG_NLS_CODEPAGE_857=m
+CONFIG_NLS_CODEPAGE_860=m
+CONFIG_NLS_CODEPAGE_861=m
+CONFIG_NLS_CODEPAGE_862=m
+CONFIG_NLS_CODEPAGE_863=m
+CONFIG_NLS_CODEPAGE_864=m
+CONFIG_NLS_CODEPAGE_865=m
+CONFIG_NLS_CODEPAGE_866=m
+CONFIG_NLS_CODEPAGE_869=m
+CONFIG_NLS_CODEPAGE_936=m
+CONFIG_NLS_CODEPAGE_950=m
+CONFIG_NLS_CODEPAGE_932=m
+CONFIG_NLS_CODEPAGE_949=m
+CONFIG_NLS_CODEPAGE_874=m
+CONFIG_NLS_ISO8859_8=m
+CONFIG_NLS_CODEPAGE_1250=m
+CONFIG_NLS_CODEPAGE_1251=m
+CONFIG_NLS_ISO8859_1=m
+CONFIG_NLS_ISO8859_2=m
+CONFIG_NLS_ISO8859_3=m
+CONFIG_NLS_ISO8859_4=m
+CONFIG_NLS_ISO8859_5=m
+CONFIG_NLS_ISO8859_6=m
+CONFIG_NLS_ISO8859_7=m
+CONFIG_NLS_ISO8859_9=m
+CONFIG_NLS_ISO8859_13=m
+CONFIG_NLS_ISO8859_14=m
+CONFIG_NLS_ISO8859_15=m
+CONFIG_NLS_KOI8_R=m
+CONFIG_NLS_KOI8_U=m
+CONFIG_NLS_UTF8=m
+CONFIG_NLS_ASCII=y
+
+#
+# Profiling support
+#
+CONFIG_PROFILING=y
+CONFIG_OPROFILE=m
+
+#
+# Tux
+#
+CONFIG_TUX=m
+CONFIG_TUX_EXTCGI=y
+# CONFIG_TUX_EXTENDED_LOG is not set
+# CONFIG_TUX_DEBUG is not set
+
+
+#
+# Kernel hacking
+#
+CONFIG_DEBUG_KERNEL=y
+# CONFIG_DEBUG_SLAB is not set
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_HIGHMEM=y
+# CONFIG_DEBUG_INFO is not set
+CONFIG_DEBUG_SPINLOCK_SLEEP=y
+# CONFIG_FRAME_POINTER is not set
+CONFIG_CC_OPTIMIZE_FOR_SIZE=y
+# CONFIG_DEBUG_DRIVER is not set
+
+#
+# Security options
+#
+CONFIG_SECURITY=y
+CONFIG_SECURITY_NETWORK=y
+CONFIG_SECURITY_CAPABILITIES=y
+# CONFIG_SECURITY_ROOTPLUG is not set
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM=y
+CONFIG_SECURITY_SELINUX_DISABLE=y
+CONFIG_SECURITY_SELINUX_DEVELOP=y
+CONFIG_SECURITY_SELINUX_AVC_STATS=y
+# CONFIG_SECURITY_SELINUX_MLS is not set
+CONFIG_SECURITY_SELINUX_BOOTPARAM_VALUE=1
+CONFIG_AUDIT=y
+CONFIG_AUDITSYSCALL=y
+
+#
+# Cryptographic options
+#
+CONFIG_CRYPTO=y
+CONFIG_CRYPTO_HMAC=y
+CONFIG_CRYPTO_NULL=m
+CONFIG_CRYPTO_MD4=m
+CONFIG_CRYPTO_MD5=m
+CONFIG_CRYPTO_SHA1=y
+CONFIG_CRYPTO_SHA256=m
+CONFIG_CRYPTO_SHA512=m
+CONFIG_CRYPTO_DES=m
+CONFIG_CRYPTO_BLOWFISH=m
+CONFIG_CRYPTO_TWOFISH=m
+CONFIG_CRYPTO_SERPENT=m
+CONFIG_CRYPTO_AES=m
+CONFIG_CRYPTO_CAST5=m
+CONFIG_CRYPTO_CAST6=m
+CONFIG_CRYPTO_DEFLATE=m
+CONFIG_CRYPTO_ARC4=m
+CONFIG_CRYPTO_MICHAEL_MIC=m
+# CONFIG_CRYPTO_TEST is not set
+CONFIG_LIBCRC32C=m
+CONFIG_CRYPTO_CRC32C=m
+CONFIG_CRYPTO_SIGNATURE_DSA=y
+CONFIG_CRYPTO_MPILIB=y
+CONFIG_CRYPTO_TEA=m
+CONFIG_CRYPTO_KHAZAD=m
+CONFIG_CRYPTO_WP512=m
+
+#
+# Library routines
+#
+CONFIG_CRC32=m
+CONFIG_CRC_CCITT=m
+
+CONFIG_ZLIB_INFLATE=y
+CONFIG_ZLIB_DEFLATE=m
+CONFIG_PC=y
+# CONFIG_SCSI_BUSLOGIC is not set
+# CONFIG_SCSI_INIA100 is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+# CONFIG_IPX is not set
+# CONFIG_IPDDP is not set
+# CONFIG_IRDA is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_ISAPNP is not set
+# CONFIG_PCMCIA_AHA152X is not set
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_IEEE1394 is not set
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_WD80x3 is not set
+# CONFIG_IRDA is not set
+# CONFIG_GAMEPORT is not set
+# CONFIG_DVB is not set
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+# CONFIG_REISERFS_FS is not set
+# CONFIG_XFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_ROMFS_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_BINFMT_AOUT is not set
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+# CONFIG_DRM_SIS is not set
+# CONFIG_BLK_DEV_UMEM is not set
+# CONFIG_MWAVE is not set
+# CONFIG_ROCKETPORT is not set
+# CONFIG_R3964 is not set
+# CONFIG_TIPAR is not set
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+# CONFIG_VIDEO_DEV is not set
+# CONFIG_PLIP is not set
+# CONFIG_FB_MATROX is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_HGA is not set
+# CONFIG_FB_ATY is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_AHA1542 is not set
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+# CONFIG_SCSI_IN2000 is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_I82092 is not set
+# CONFIG_YELLOWFIN is not set
+# CONFIG_SUNDANCE is not set
+# CONFIG_ULTRA is not set
+# CONFIG_SKFP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+# CONFIG_AC3200 is not set
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+# CONFIG_LANCE is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+# CONFIG_HAMACHI is not set
+# CONFIG_HP100 is not set
+# CONFIG_EQUALIZER is not set
+# CONFIG_NET_SB1000 is not set
+# CONFIG_DEPCA is not set
+# CONFIG_ATP is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_INFTL is not set
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PCI is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_AUDIT=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_JFS_FS is not set
+# CONFIG_I2C_PCA_ISA is not set
+CONFIG_RAW_DRIVER=y
+# CONFIG_MTD_SCB2_FLASH is not set
+CONFIG_UID16=y
+# CONFIG_MK8 is not set
+# CONFIG_MPSC is not set
+CONFIG_GENERIC_CPU=y
+CONFIG_X86_MSR=y
+CONFIG_X86_CPUID=y
+CONFIG_MTRR=y
+CONFIG_NUMA=y
+CONFIG_K8_NUMA=y
+CONFIG_NR_CPUS=8
+CONFIG_GART_IOMMU=y
+CONFIG_X86_POWERNOW_K8=y
+CONFIG_IA32_EMULATION=y
+# CONFIG_IA32_AOUT is not set
+CONFIG_INIT_DEBUG=y
+# CONFIG_IOMMU_DEBUG is not set
+# CONFIG_CHECKING is not set
+CONFIG_MICROCODE=m 
+CONFIG_SWIOTLB=y
+CONFIG_X86_PM_TIMER=y
+CONFIG_I2O=m
+CONFIG_I2O_BLOCK=m
+CONFIG_I2O_SCSI=m
+CONFIG_I2O_PROC=m
+CONFIG_I2O_CONFIG=y
+CONFIG_TUX=m
+# CONFIG_UNORDERED_IO is not set
+# CONFIG_X86_SPEEDSTEP_CENTRINO is not set
+CONFIG_X86_ACPI_CPUFREQ=y
+# CONFIG_X86_ACPI_CPUFREQ_PROC_INTF is not set
+CONFIG_GENERIC_ISA_DMA=y
+CONFIG_SCHED_SMT=y
+# CONFIG_SOFTWARE_SUSPEND is not set
+# CONFIG_PM_DEBUG is not set
+CONFIG_CPU_FREQ=y
+# CONFIG_CPU_FREQ_PROC_INTF is not set
+# CONFIG_CPU_FREQ_DEFAULT_GOV_PERFORMANCE is not set
+CONFIG_CPU_FREQ_DEFAULT_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_PERFORMANCE=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=m
+CONFIG_CPU_FREQ_GOV_USERSPACE=m
+CONFIG_CPU_FREQ_GOV_ONDEMAND=m
+# CONFIG_CPU_FREQ_24_API is not set
+CONFIG_CPU_FREQ_TABLE=y
+CONFIG_ACPI=y
+CONFIG_ACPI_BOOT=y
+CONFIG_ACPI_INTERPRETER=y
+CONFIG_ACPI_SLEEP=y
+CONFIG_ACPI_AC=m
+CONFIG_ACPI_BATTERY=m
+CONFIG_ACPI_BUTTON=m
+CONFIG_ACPI_FAN=y
+CONFIG_ACPI_PROCESSOR=y
+CONFIG_ACPI_THERMAL=y
+CONFIG_ACPI_ASUS=m
+CONFIG_ACPI_TOSHIBA=m
+# CONFIG_ACPI_DEBUG is not set
+CONFIG_ACPI_BUS=y
+CONFIG_ACPI_EC=y
+CONFIG_ACPI_POWER=y
+CONFIG_ACPI_PCI=y
+CONFIG_ACPI_SYSTEM=y
+CONFIG_ACPI_NUMA=y
+CONFIG_ACPI_BLACKLIST_YEAR=2001
+# CONFIG_SCHEDSTATS is not set
+CONFIG_EDD=m
+CONFIG_PCI_BIOS=y
+CONFIG_PCI_MMCONFIG=y
+CONFIG_KEXEC=y
+CONFIG_NETDUMP=m
+CONFIG_CRASH=m
+CONFIG_HOTPLUG_PCI=y
+# CONFIG_HOTPLUG_PCI_FAKE is not set
+CONFIG_HOTPLUG_PCI_COMPAQ=m
+# CONFIG_HOTPLUG_PCI_COMPAQ_NVRAM is not set
+CONFIG_HOTPLUG_PCI_IBM=m
+CONFIG_HOTPLUG_PCI_ACPI=m 
+CONFIG_HOTPLUG_PCI_ACPI_IBM=m
+# CONFIG_HOTPLUG_PCI_CPCI is not set
+CONFIG_HOTPLUG_PCI_PCIE=m
+# CONFIG_HOTPLUG_PCI_PCIE_POLL_EVENT_MODE is not set
+CONFIG_HOTPLUG_PCI_SHPC=m
+# CONFIG_HOTPLUG_PCI_SHPC_POLL_EVENT_MODE is not set
+# CONFIG_HOTPLUG_PCI_SHPC_PHPRM_LEGACY is not set
+# CONFIG_HPET is not set
+CONFIG_PM=y
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
diff --git a/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-x86_64.config b/lustre/kernel_patches/kernel_configs/kernel-2.6.9-2.6-rhel4-x86_64.config
new file mode 100644 (file)
index 0000000..2c33da7
--- /dev/null
@@ -0,0 +1,2633 @@
+#
+# Automatically generated make config: don't edit
+#
+CONFIG_MMU=y
+# CONFIG_SMP is not set
+# CONFIG_HOTPLUG_CPU is not set
+CONFIG_LOCALVERSION=""
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_CLEAN_COMPILE=y
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+
+#
+# General setup
+#
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+CONFIG_BSD_PROCESS_ACCT=y
+# CONFIG_BSD_PROCESS_ACCT_V3 is not set
+CONFIG_SYSCTL=y
+CONFIG_LOG_BUF_SHIFT=17
+# CONFIG_IKCONFIG is not set
+# CONFIG_EMBEDDED is not set
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_ALL is not set
+CONFIG_KALLSYMS_EXTRA_PASS=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+# CONFIG_PREEMPT is not set
+CONFIG_PREEMPT_VOLUNTARY=y
+CONFIG_POSIX_MQUEUE=y
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+CONFIG_OBSOLETE_MODPARM=y
+CONFIG_MODVERSIONS=y
+CONFIG_KMOD=y
+CONFIG_MODULE_SIG=y
+# CONFIG_MODULE_SIG_FORCE is not set
+
+#
+# Bus options (PCI, PCMCIA, EISA, MCA, ISA)
+#
+CONFIG_PCI=y
+CONFIG_PCI_MSI=y
+CONFIG_PCI_LEGACY_PROC=y
+# CONFIG_PCI_NAMES is not set
+CONFIG_ISA=y
+# CONFIG_EISA is not set
+# CONFIG_MCA is not set
+# CONFIG_SCx200 is not set
+CONFIG_HOTPLUG=y
+
+#
+# PCMCIA/CardBus support
+#
+CONFIG_PCMCIA=m
+# CONFIG_PCMCIA_DEBUG is not set
+CONFIG_YENTA=y
+CONFIG_CARDBUS=y
+# CONFIG_I82092 is not set
+CONFIG_I82365=m
+CONFIG_PD6729=m
+CONFIG_TCIC=m
+CONFIG_PCMCIA_PROBE=y
+
+#
+# Executable file formats
+#
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_AOUT is not set
+CONFIG_BINFMT_MISC=y
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_FW_LOADER=y
+
+#
+# Memory Technology Devices (MTD)
+#
+CONFIG_MTD=m
+# CONFIG_MTD_DEBUG is not set
+CONFIG_MTD_PARTITIONS=m
+CONFIG_MTD_CONCAT=m
+CONFIG_MTD_REDBOOT_PARTS=m
+CONFIG_MTD_CMDLINE_PARTS=y
+CONFIG_MTD_PARTITIONS=y
+#
+# User Modules And Translation Layers
+#
+CONFIG_MTD_CHAR=m
+CONFIG_MTD_BLOCK=m
+CONFIG_MTD_BLOCK_RO=m
+CONFIG_FTL=m
+CONFIG_NFTL=m
+CONFIG_NFTL_RW=y
+# CONFIG_INFTL is not set
+
+#
+# RAM/ROM/Flash chip drivers
+#
+CONFIG_MTD_CFI=m
+CONFIG_MTD_JEDECPROBE=m
+CONFIG_MTD_GEN_PROBE=m
+# CONFIG_MTD_CFI_ADV_OPTIONS is not set
+CONFIG_MTD_CFI_INTELEXT=m
+CONFIG_MTD_CFI_AMDSTD=m
+CONFIG_MTD_CFI_STAA=m
+CONFIG_MTD_RAM=m
+CONFIG_MTD_ROM=m
+CONFIG_MTD_ABSENT=m
+# CONFIG_MTD_OBSOLETE_CHIPS is not set
+
+#
+# Mapping drivers for chip access
+#
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PHYSMAP is not set
+# CONFIG_MTD_PNC2000 is not set
+CONFIG_MTD_SC520CDP=m
+CONFIG_MTD_NETSC520=m
+CONFIG_MTD_SBC_GXX=m
+CONFIG_MTD_ELAN_104NC=m
+CONFIG_MTD_SCx200_DOCFLASH=m
+# CONFIG_MTD_AMD76XROM is not set
+# CONFIG_MTD_SCB2_FLASH is not set
+# CONFIG_MTD_NETtel is not set
+# CONFIG_MTD_DILNETPC is not set
+# CONFIG_MTD_L440GX is not set
+# CONFIG_MTD_PCI is not set
+
+#
+# Self-contained MTD device drivers
+#
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_PMC551_BUGFIX is not set
+# CONFIG_MTD_PMC551_DEBUG is not set
+# CONFIG_MTD_SLRAM is not set
+CONFIG_MTD_MTDRAM=m
+CONFIG_MTDRAM_TOTAL_SIZE=4096
+CONFIG_MTDRAM_ERASE_SIZE=128
+# CONFIG_MTD_BLKMTD is not set
+
+#
+# Disk-On-Chip Device Drivers
+#
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+CONFIG_MTD_DOCPROBE=m
+# CONFIG_MTD_DOCPROBE_ADVANCED is not set
+CONFIG_MTD_DOCPROBE_ADDRESS=0
+
+#
+# NAND Flash Device Drivers
+#
+CONFIG_MTD_NAND=m
+# CONFIG_MTD_NAND_VERIFY_WRITE is not set
+CONFIG_MTD_NAND_IDS=m
+
+# CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
+# CONFIG_MTD_REDBOOT_PARTS_READONLY is not set
+CONFIG_MTD_CFI_AMDSTD_RETRY=3
+# CONFIG_MTD_ICHXROM is not set
+# CONFIG_MTD_PHRAM is not set
+# CONFIG_MTD_NAND_DISKONCHIP is not set
+# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set
+
+
+#
+# Parallel port support
+#
+CONFIG_PARPORT=m
+CONFIG_PARPORT_PC=m
+CONFIG_PARPORT_PC_CML1=m
+CONFIG_PARPORT_SERIAL=m
+# CONFIG_PARPORT_PC_FIFO is not set
+# CONFIG_PARPORT_PC_SUPERIO is not set
+CONFIG_PARPORT_PC_PCMCIA=m
+# CONFIG_PARPORT_OTHER is not set
+CONFIG_PARPORT_1284=y
+
+#
+# Plug and Play support
+#
+CONFIG_PNP=y
+# CONFIG_PNP_DEBUG is not set
+
+#
+# Protocols
+#
+# CONFIG_ISAPNP is not set
+# CONFIG_PNPBIOS is not set
+
+#
+# Block devices
+#
+CONFIG_BLK_DEV_FD=m
+# CONFIG_BLK_DEV_XD is not set
+# CONFIG_PARIDE is not set
+CONFIG_BLK_CPQ_DA=m
+CONFIG_BLK_CPQ_CISS_DA=m
+CONFIG_CISS_SCSI_TAPE=y
+CONFIG_BLK_DEV_DAC960=m
+# CONFIG_BLK_DEV_UMEM is not set
+CONFIG_BLK_DEV_LOOP=m
+CONFIG_BLK_DEV_CRYPTOLOOP=m
+CONFIG_BLK_DEV_NBD=m
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=16384
+CONFIG_BLK_DEV_INITRD=y
+CONFIG_BLK_DEV_ATIIXP=y
+CONFIG_BLK_DEV_DELKIN=y
+CONFIG_BLK_DEV_IT8212=y
+CONFIG_LBD=y
+# CONFIG_DCSSBLK is not set
+
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+CONFIG_IDE=y
+CONFIG_IDE_GENERIC=y
+# CONFIG_HPT34X_AUTODMA is not set
+
+CONFIG_BLK_DEV_IDE=y
+
+#
+# Please see Documentation/ide.txt for help/info on IDE drives
+#
+# CONFIG_BLK_DEV_HD_IDE is not set
+CONFIG_BLK_DEV_IDEDISK=y
+CONFIG_IDEDISK_MULTI_MODE=y
+CONFIG_BLK_DEV_IDECS=m
+CONFIG_BLK_DEV_IDECD=y
+# CONFIG_BLK_DEV_IDETAPE is not set
+CONFIG_BLK_DEV_IDEFLOPPY=y
+CONFIG_BLK_DEV_IDESCSI=m
+# CONFIG_IDE_TASK_IOCTL is not set
+# CONFIG_IDE_TASKFILE_IO is not set
+# CONFIG_BLK_DEV_IDE_SATA is not set
+
+#
+# IDE chipset support/bugfixes
+#
+# CONFIG_BLK_DEV_CMD640 is not set
+# CONFIG_BLK_DEV_CMD640_ENHANCED is not set
+CONFIG_BLK_DEV_IDEPNP=y
+CONFIG_BLK_DEV_IDEPCI=y
+CONFIG_IDEPCI_SHARE_IRQ=y
+# CONFIG_BLK_DEV_OFFBOARD is not set
+CONFIG_BLK_DEV_GENERIC=y
+# CONFIG_BLK_DEV_OPTI621 is not set
+CONFIG_BLK_DEV_RZ1000=y
+CONFIG_BLK_DEV_IDEDMA_PCI=y
+# CONFIG_BLK_DEV_IDEDMA_FORCED is not set
+CONFIG_IDEDMA_PCI_AUTO=y
+# CONFIG_IDEDMA_ONLYDISK is not set
+CONFIG_BLK_DEV_AEC62XX=y
+CONFIG_BLK_DEV_ALI15X3=y
+# CONFIG_WDC_ALI15X3 is not set
+CONFIG_BLK_DEV_AMD74XX=y
+CONFIG_BLK_DEV_CMD64X=y
+CONFIG_BLK_DEV_TRIFLEX=y
+CONFIG_BLK_DEV_CY82C693=y
+CONFIG_BLK_DEV_CS5520=y
+CONFIG_BLK_DEV_CS5530=y
+CONFIG_BLK_DEV_HPT34X=y
+CONFIG_BLK_DEV_HPT366=y
+# CONFIG_BLK_DEV_SC1200 is not set
+CONFIG_BLK_DEV_PIIX=y
+# CONFIG_BLK_DEV_NS87415 is not set
+CONFIG_BLK_DEV_PDC202XX_OLD=y
+# CONFIG_PDC202XX_BURST is not set
+CONFIG_BLK_DEV_PDC202XX_NEW=y
+CONFIG_PDC202XX_FORCE=y
+CONFIG_BLK_DEV_SVWKS=y
+CONFIG_BLK_DEV_SIIMAGE=y
+CONFIG_BLK_DEV_SIS5513=y
+CONFIG_BLK_DEV_SLC90E66=y
+# CONFIG_BLK_DEV_TRM290 is not set
+CONFIG_BLK_DEV_VIA82CXXX=y
+# CONFIG_IDE_CHIPSETS is not set
+CONFIG_BLK_DEV_IDEDMA=y
+# CONFIG_IDEDMA_IVB is not set
+CONFIG_IDEDMA_AUTO=y
+# CONFIG_BLK_DEV_HD is not set
+
+#
+# SCSI device support
+#
+CONFIG_SCSI=m
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=m
+CONFIG_CHR_DEV_ST=m
+CONFIG_CHR_DEV_OSST=m
+CONFIG_BLK_DEV_SR=m
+CONFIG_BLK_DEV_SR_VENDOR=y
+CONFIG_CHR_DEV_SG=m
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SPI_ATTRS=y
+CONFIG_SCSI_FC_ATTRS=y
+
+#
+# SCSI low-level drivers
+#
+CONFIG_BLK_DEV_3W_XXXX_RAID=m
+CONFIG_SCSI_3W_9XXX=m
+# CONFIG_SCSI_7000FASST is not set
+CONFIG_SCSI_ACARD=m
+CONFIG_SCSI_AHA152X=m
+# CONFIG_SCSI_AHA1542 is not set
+CONFIG_SCSI_AACRAID=m
+CONFIG_SCSI_AIC7XXX=m
+CONFIG_AIC7XXX_CMDS_PER_DEVICE=4
+CONFIG_AIC7XXX_RESET_DELAY_MS=15000
+# CONFIG_AIC7XXX_PROBE_EISA_VL is not set
+# CONFIG_AIC7XXX_BUILD_FIRMWARE is not set
+# CONFIG_AIC7XXX_DEBUG_ENABLE is not set
+CONFIG_AIC7XXX_DEBUG_MASK=0
+# CONFIG_AIC7XXX_REG_PRETTY_PRINT is not set
+CONFIG_SCSI_AIC7XXX_OLD=m
+CONFIG_SCSI_AIC79XX=m
+CONFIG_AIC79XX_CMDS_PER_DEVICE=4
+CONFIG_AIC79XX_RESET_DELAY_MS=15000
+# CONFIG_AIC79XX_BUILD_FIRMWARE is not set
+# CONFIG_AIC79XX_ENABLE_RD_STRM is not set
+# CONFIG_AIC79XX_DEBUG_ENABLE is not set
+CONFIG_AIC79XX_DEBUG_MASK=0
+# CONFIG_AIC79XX_REG_PRETTY_PRINT is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_IN2000 is not set
+CONFIG_MEGARAID_NEWGEN=y
+CONFIG_MEGARAID_MM=m
+CONFIG_MEGARAID_MAILBOX=m
+CONFIG_SCSI_SATA=y
+CONFIG_SCSI_SATA_SVW=m
+CONFIG_SCSI_ATA_PIIX=m
+CONFIG_SCSI_SATA_PROMISE=m
+CONFIG_SCSI_SATA_VIA=m
+CONFIG_BLK_DEV_SX8=m
+CONFIG_SCSI_SATA_VITESSE=m
+CONFIG_SCSI_SATA_SIL=m
+CONFIG_SCSI_SATA_SIS=m
+CONFIG_SCSI_SATA_SX4=m
+CONFIG_SCSI_SATA_NV=m
+CONFIG_SCSI_SATA_AHCI=m
+
+# CONFIG_SCSI_BUSLOGIC is not set
+CONFIG_SCSI_INITIO=m
+# CONFIG_SCSI_OMIT_FLASHPOINT is not set
+# CONFIG_SCSI_CPQFCTS is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_DTC3280 is not set
+# CONFIG_SCSI_EATA is not set
+# CONFIG_SCSI_EATA_PIO is not set
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+CONFIG_SCSI_GDTH=m
+# CONFIG_SCSI_GENERIC_NCR5380 is not set
+# CONFIG_SCSI_GENERIC_NCR5380_MMIO is not set
+CONFIG_SCSI_IPS=m
+# CONFIG_SCSI_INIA100 is not set
+CONFIG_SCSI_PPA=m
+CONFIG_SCSI_IMM=m
+# CONFIG_SCSI_IZIP_EPP16 is not set
+# CONFIG_SCSI_IZIP_SLOW_CTR is not set
+# CONFIG_SCSI_NCR53C406A is not set
+CONFIG_SCSI_SYM53C8XX_2=m
+CONFIG_SCSI_SYM53C8XX_DMA_ADDRESSING_MODE=1
+CONFIG_SCSI_SYM53C8XX_DEFAULT_TAGS=16
+CONFIG_SCSI_SYM53C8XX_MAX_TAGS=64
+# CONFIG_SCSI_SYM53C8XX_IOMAPPED is not set
+# CONFIG_SCSI_PAS16 is not set
+# CONFIG_SCSI_PSI240I is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_SCSI_QLOGIC_FC is not set
+# CONFIG_SCSI_QLOGIC_FC_FIRMWARE is not set
+CONFIG_SCSI_QLOGIC_1280=m
+# CONFIG_SCSI_SYM53C416 is not set
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_T128 is not set
+# CONFIG_SCSI_U14_34F is not set
+# CONFIG_SCSI_ULTRASTOR is not set
+# CONFIG_SCSI_NSP32 is not set
+# CONFIG_SCSI_DEBUG is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_SCSI_QLA2XXX=m
+CONFIG_SCSI_QLA21XX=m
+CONFIG_SCSI_QLA22XX=m
+CONFIG_SCSI_QLA2300=m
+CONFIG_SCSI_QLA2322=m
+CONFIG_SCSI_QLA6312=m
+CONFIG_SCSI_QLA6322=m
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_DPT_I2O is not set
+
+CONFIG_SCSI_LPFC=m
+
+#
+# PCMCIA SCSI adapter support
+#
+# CONFIG_PCMCIA_AHA152X is not set
+# CONFIG_PCMCIA_FDOMAIN is not set
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+
+
+#
+# Old CD-ROM drivers (not SCSI, not IDE)
+#
+# CONFIG_CD_NO_IDESCSI is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+CONFIG_MD=y
+CONFIG_BLK_DEV_MD=y
+CONFIG_MD_LINEAR=m
+CONFIG_MD_RAID0=m
+CONFIG_MD_RAID1=m
+CONFIG_MD_RAID5=m
+CONFIG_MD_RAID6=m
+CONFIG_MD_RAID10=m
+CONFIG_MD_MULTIPATH=m
+CONFIG_BLK_DEV_DM=m
+CONFIG_DM_SNAPSHOT=m
+CONFIG_DM_MIRROR=m
+CONFIG_DM_ZERO=m
+CONFIG_DM_CRYPT=m
+
+#
+# Fusion MPT device support
+#
+CONFIG_FUSION=m
+CONFIG_FUSION_MAX_SGE=40
+CONFIG_FUSION_CTL=m
+CONFIG_FUSION_LAN=m
+
+#
+# IEEE 1394 (FireWire) support (EXPERIMENTAL)
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# Subsystem Options
+#
+# CONFIG_IEEE1394_VERBOSEDEBUG is not set
+CONFIG_IEEE1394_OUI_DB=y
+
+#
+# Device Drivers
+#
+# CONFIG_IEEE1394_PCILYNX is not set
+CONFIG_IEEE1394_OHCI1394=m
+
+#
+# Protocol Drivers
+#
+CONFIG_IEEE1394_VIDEO1394=m
+CONFIG_IEEE1394_SBP2=m
+# CONFIG_IEEE1394_SBP2_PHYS_DMA is not set
+# CONFIG_IEEE1394_ETH1394 is not set
+CONFIG_IEEE1394_DV1394=m
+CONFIG_IEEE1394_RAWIO=m
+CONFIG_IEEE1394_CMP=m
+CONFIG_IEEE1394_AMDTP=m
+# CONFIG_IEEE1394_EXTRA_CONFIG_ROMS is not set
+
+#
+# I2O device support
+#
+CONFIG_I2O=m
+
+#
+# Networking support
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+CONFIG_PACKET=y
+CONFIG_PACKET_MMAP=y
+CONFIG_NETLINK_DEV=y
+CONFIG_UNIX=y
+CONFIG_NET_KEY=m
+CONFIG_INET=y
+CONFIG_INET_TUNNEL=m
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_FWMARK=y
+CONFIG_IP_ROUTE_MULTIPATH=y
+CONFIG_IP_ROUTE_VERBOSE=y
+# CONFIG_IP_PNP is not set
+CONFIG_NET_IPIP=m
+CONFIG_NET_IPGRE=m
+CONFIG_NET_IPGRE_BROADCAST=y
+CONFIG_IP_MROUTE=y
+CONFIG_IP_PIMSM_V1=y
+CONFIG_IP_PIMSM_V2=y
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+CONFIG_INET_AH=m
+CONFIG_INET_ESP=m
+CONFIG_INET_IPCOMP=m
+CONFIG_NETCONSOLE=m
+# CONFIG_NETPOLL_RX is not set
+CONFIG_NETPOLL_TRAP=y
+CONFIG_NET_POLL_CONTROLLER=y
+CONFIG_NETDUMP=m
+CONFIG_DISKDUMP=m
+CONFIG_SCSI_DUMP=m
+CONFIG_SD_IOSTATS=y
+
+#
+# IP: Virtual Server Configuration
+#
+CONFIG_IP_VS=m
+# CONFIG_IP_VS_DEBUG is not set
+CONFIG_IP_VS_TAB_BITS=12
+CONFIG_IP_VS_PROTO_TCP=y
+CONFIG_IP_VS_PROTO_UDP=y
+CONFIG_IP_VS_PROTO_ESP=y
+CONFIG_IP_VS_PROTO_AH=y
+CONFIG_IP_VS_RR=m
+CONFIG_IP_VS_WRR=m
+CONFIG_IP_VS_LC=m
+CONFIG_IP_VS_WLC=m
+CONFIG_IP_VS_LBLC=m
+CONFIG_IP_VS_LBLCR=m
+CONFIG_IP_VS_DH=m
+CONFIG_IP_VS_SH=m
+CONFIG_IP_VS_SED=m
+CONFIG_IP_VS_NQ=m
+CONFIG_IP_VS_FTP=m
+
+
+CONFIG_IPV6=m
+CONFIG_IPV6_PRIVACY=y
+CONFIG_INET6_AH=m
+CONFIG_INET6_ESP=m
+CONFIG_INET6_IPCOMP=m
+CONFIG_IPV6_TUNNEL=m
+# CONFIG_DECNET is not set
+CONFIG_BRIDGE=m
+CONFIG_NETFILTER=y
+# CONFIG_NETFILTER_DEBUG is not set
+CONFIG_BRIDGE_NETFILTER=y
+
+#
+# IP: Netfilter Configuration
+#
+CONFIG_IP_NF_CONNTRACK=m
+CONFIG_IP_NF_FTP=m
+CONFIG_IP_NF_IRC=m
+CONFIG_IP_NF_TFTP=m
+CONFIG_IP_NF_AMANDA=m
+CONFIG_IP_NF_QUEUE=m
+CONFIG_IP_NF_RAW=m
+CONFIG_IP_NF_IPTABLES=m
+CONFIG_IP_NF_MATCH_COMMENT=m
+CONFIG_IP_NF_MATCH_LIMIT=m
+CONFIG_IP_NF_MATCH_IPRANGE=m
+CONFIG_IP_NF_MATCH_MAC=m
+CONFIG_IP_NF_MATCH_PKTTYPE=m
+CONFIG_IP_NF_MATCH_MARK=m
+CONFIG_IP_NF_MATCH_MULTIPORT=m
+CONFIG_IP_NF_MATCH_TOS=m
+CONFIG_IP_NF_MATCH_RECENT=m
+CONFIG_IP_NF_MATCH_ECN=m
+CONFIG_IP_NF_MATCH_DSCP=m
+CONFIG_IP_NF_MATCH_AH_ESP=m
+CONFIG_IP_NF_MATCH_LENGTH=m
+CONFIG_IP_NF_MATCH_TTL=m
+CONFIG_IP_NF_MATCH_TCPMSS=m
+CONFIG_IP_NF_MATCH_HELPER=m
+CONFIG_IP_NF_MATCH_STATE=m
+CONFIG_IP_NF_MATCH_CONNTRACK=m
+CONFIG_IP_NF_MATCH_OWNER=m
+CONFIG_IP_NF_MATCH_PHYSDEV=m
+CONFIG_IP_NF_MATCH_ADDRTYPE=m
+CONFIG_IP_NF_MATCH_REALM=m
+CONFIG_IP_NF_MATCH_SCTP=m
+CONFIG_IP_NF_FILTER=m
+CONFIG_IP_NF_TARGET_REJECT=m
+CONFIG_IP_NF_NAT=m
+CONFIG_IP_NF_NAT_NEEDED=y
+CONFIG_IP_NF_TARGET_MASQUERADE=m
+CONFIG_IP_NF_TARGET_REDIRECT=m
+CONFIG_IP_NF_TARGET_NETMAP=m
+CONFIG_IP_NF_TARGET_SAME=m
+CONFIG_IP_NF_TARGET_NOTRACK=m
+CONFIG_IP_NF_NAT_LOCAL=y
+CONFIG_IP_NF_NAT_SNMP_BASIC=m
+CONFIG_IP_NF_NAT_IRC=m
+CONFIG_IP_NF_NAT_FTP=m
+CONFIG_IP_NF_NAT_TFTP=m
+CONFIG_IP_NF_NAT_AMANDA=m
+CONFIG_IP_NF_MANGLE=m
+CONFIG_IP_NF_TARGET_TOS=m
+CONFIG_IP_NF_TARGET_ECN=m
+CONFIG_IP_NF_TARGET_DSCP=m
+CONFIG_IP_NF_TARGET_MARK=m
+CONFIG_IP_NF_TARGET_CLASSIFY=m
+CONFIG_IP_NF_TARGET_LOG=m
+CONFIG_IP_NF_TARGET_ULOG=m
+CONFIG_IP_NF_TARGET_TCPMSS=m
+CONFIG_IP_NF_ARPTABLES=m
+CONFIG_IP_NF_ARPFILTER=m
+CONFIG_IP_NF_ARP_MANGLE=m
+CONFIG_IP_NF_CT_ACCT=y
+CONFIG_IP_NF_CT_PROTO_SCTP=m
+# CONFIG_IP_NF_COMPAT_IPCHAINS is not set
+# CONFIG_IP_NF_COMPAT_IPFWADM is not set
+
+#
+# IPv6: Netfilter Configuration
+#
+# CONFIG_IP6_NF_QUEUE is not set
+CONFIG_IP6_NF_IPTABLES=m
+CONFIG_IP6_NF_MATCH_LIMIT=m
+CONFIG_IP6_NF_MATCH_MAC=m
+CONFIG_IP6_NF_MATCH_RT=m
+CONFIG_IP6_NF_MATCH_OPTS=m
+CONFIG_IP6_NF_MATCH_FRAG=m
+CONFIG_IP6_NF_MATCH_HL=m
+CONFIG_IP6_NF_MATCH_MULTIPORT=m
+CONFIG_IP6_NF_MATCH_OWNER=m
+CONFIG_IP6_NF_MATCH_MARK=m
+CONFIG_IP6_NF_MATCH_IPV6HEADER=m
+CONFIG_IP6_NF_MATCH_AHESP=m
+CONFIG_IP6_NF_MATCH_LENGTH=m
+CONFIG_IP6_NF_MATCH_EUI64=m
+CONFIG_IP6_NF_MATCH_PHYSDEV=m
+CONFIG_IP6_NF_FILTER=m
+CONFIG_IP6_NF_TARGET_LOG=m
+CONFIG_IP6_NF_MANGLE=m
+CONFIG_IP6_NF_TARGET_MARK=m
+CONFIG_IP6_NF_RAW=m
+
+
+#
+# Bridge: Netfilter Configuration
+#
+CONFIG_BRIDGE_NF_EBTABLES=m
+CONFIG_BRIDGE_EBT_BROUTE=m
+CONFIG_BRIDGE_EBT_T_FILTER=m
+CONFIG_BRIDGE_EBT_T_NAT=m
+CONFIG_BRIDGE_EBT_802_3=m
+CONFIG_BRIDGE_EBT_AMONG=m
+CONFIG_BRIDGE_EBT_ARP=m
+CONFIG_BRIDGE_EBT_IP=m
+CONFIG_BRIDGE_EBT_LIMIT=m
+CONFIG_BRIDGE_EBT_MARK=m
+CONFIG_BRIDGE_EBT_PKTTYPE=m
+CONFIG_BRIDGE_EBT_STP=m
+CONFIG_BRIDGE_EBT_VLAN=m
+CONFIG_BRIDGE_EBT_ARPREPLY=m
+CONFIG_BRIDGE_EBT_DNAT=m
+CONFIG_BRIDGE_EBT_MARK_T=m
+CONFIG_BRIDGE_EBT_REDIRECT=m
+CONFIG_BRIDGE_EBT_SNAT=m
+CONFIG_BRIDGE_EBT_LOG=m
+CONFIG_XFRM=y
+CONFIG_XFRM_USER=y
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+CONFIG_IP_SCTP=m
+# CONFIG_SCTP_DBG_MSG is not set
+# CONFIG_SCTP_DBG_OBJCNT is not set
+# CONFIG_SCTP_HMAC_NONE is not set
+# CONFIG_SCTP_HMAC_SHA1 is not set
+CONFIG_SCTP_HMAC_MD5=y
+CONFIG_ATM=m
+CONFIG_VLAN_8021Q=m
+CONFIG_LLC=m
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_IPX_INTERN is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+CONFIG_COPS_DAYNA=y
+CONFIG_COPS_TANGENT=y
+# CONFIG_IPDDP is not set
+CONFIG_IPDDP_ENCAP=y
+CONFIG_IPDDP_DECAP=y
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+CONFIG_NET_DIVERT=y
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_NET_HW_FLOWCONTROL is not set
+
+#
+# QoS and/or fair queueing
+#
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_CBQ=m
+CONFIG_NET_SCH_HTB=m
+CONFIG_NET_SCH_PRIO=m
+CONFIG_NET_SCH_RED=m
+CONFIG_NET_SCH_SFQ=m
+CONFIG_NET_SCH_TEQL=m
+CONFIG_NET_SCH_TBF=m
+CONFIG_NET_SCH_GRED=m
+CONFIG_NET_SCH_DSMARK=m
+CONFIG_NET_SCH_INGRESS=m
+CONFIG_NET_SCH_HFSC=m
+CONFIG_NET_SCH_NETEM=m
+CONFIG_NET_QOS=y
+CONFIG_NET_ESTIMATOR=y
+CONFIG_NET_CLS=y
+CONFIG_NET_CLS_TCINDEX=m
+CONFIG_NET_CLS_ROUTE4=m
+CONFIG_NET_CLS_ROUTE=y
+CONFIG_NET_CLS_FW=m
+CONFIG_NET_CLS_U32=m
+CONFIG_NET_CLS_RSVP=m
+CONFIG_NET_CLS_RSVP6=m
+CONFIG_NET_CLS_POLICE=y
+# CONFIG_NET_ACT_POLICE is not set
+CONFIG_CLS_U32_PERF=y
+CONFIG_NET_CLS_IND=y
+# CONFIG_NET_CLS_ACT is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+CONFIG_NETDEVICES=y
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+CONFIG_DUMMY=m
+CONFIG_BONDING=m
+# CONFIG_EQUALIZER is not set
+CONFIG_TUN=m
+CONFIG_ETHERTAP=m
+# CONFIG_NET_SB1000 is not set
+
+#
+# ATM
+# 
+CONFIG_ATM_CLIP=m
+CONFIG_ATM_LANE=m
+CONFIG_ATM_BR2684=m
+CONFIG_NET_SCH_ATM=m
+CONFIG_ATM_TCP=m
+CONFIG_ATM_LANAI=m
+CONFIG_ATM_ENI=m
+CONFIG_ATM_FIRESTREAM=m
+# CONFIG_ATM_ZATM is not set
+CONFIG_ATM_IDT77252=m
+CONFIG_ATM_AMBASSADOR=m
+CONFIG_ATM_HORIZON=m
+CONFIG_ATM_FORE200E_MAYBE=m
+CONFIG_ATM_HE=m
+CONFIG_PPPOATM=m
+CONFIG_ATM_NICSTAR=m
+# CONFIG_ATM_IA is not set
+
+
+# CONFIG_ATM_CLIP_NO_ICMP is not set
+# CONFIG_ATM_MPOA is not set
+# CONFIG_ATM_BR2684_IPFILTER is not set
+# CONFIG_ATM_ENI_DEBUG is not set
+# CONFIG_ATM_ENI_TUNE_BURST is not set
+# CONFIG_ATM_ZATM_DEBUG is not set
+# CONFIG_ATM_IDT77252_DEBUG is not set
+# CONFIG_ATM_IDT77252_RCV_ALL is not set
+# CONFIG_ATM_AMBASSADOR_DEBUG is not set
+# CONFIG_ATM_HORIZON_DEBUG is not set
+# CONFIG_ATM_FORE200E_PCA is not set
+# CONFIG_ATM_HE_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_SUNI is not set
+# CONFIG_ATM_NICSTAR_USE_IDT77105 is not set
+# CONFIG_ATM_IA_DEBUG is not set
+
+
+
+
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=m
+CONFIG_HAPPYMEAL=m
+CONFIG_SUNGEM=m
+CONFIG_NET_VENDOR_3COM=y
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+CONFIG_VORTEX=m
+CONFIG_TYPHOON=m
+# CONFIG_LANCE is not set
+CONFIG_NET_VENDOR_SMC=y
+# CONFIG_WD80x3 is not set
+# CONFIG_ULTRA is not set
+CONFIG_SMC9194=m
+CONFIG_NET_VENDOR_RACAL=y
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+
+#
+# Tulip family network device support
+#
+CONFIG_NET_TULIP=y
+CONFIG_DE2104X=m
+CONFIG_TULIP=m
+# CONFIG_TULIP_NAPI is not set
+
+# CONFIG_TULIP_MWI is not set
+CONFIG_TULIP_MMIO=y
+# CONFIG_NI5010 is not set
+# CONFIG_PCMCIA_XIRTULIP is not set
+CONFIG_DE4X5=m
+CONFIG_WINBOND_840=m
+CONFIG_DM9102=m
+CONFIG_PCMCIA_XIRCOM=m
+# CONFIG_AT1700 is not set
+# CONFIG_DEPCA is not set
+# CONFIG_HP100 is not set
+# CONFIG_NET_ISA is not set
+CONFIG_EWRK3=m
+CONFIG_E2100=m
+CONFIG_EEXPRESS=m
+CONFIG_EEXPRESS_PRO=m
+CONFIG_HPLAN_PLUS=m
+CONFIG_HPLAN=m
+CONFIG_LP486E=m
+CONFIG_ETH16I=m
+CONFIG_NE2000=m
+CONFIG_ZNET=m
+CONFIG_SEEQ8005=m
+CONFIG_LNE390=m
+CONFIG_NE3210=m
+CONFIG_ES3210=m
+CONFIG_NET_PCI=y
+CONFIG_PCNET32=m
+CONFIG_AMD8111_ETH=m
+CONFIG_AMD8111E_NAPI=y
+CONFIG_ADAPTEC_STARFIRE=m
+CONFIG_ADAPTEC_STARFIRE_NAPI=y
+# CONFIG_AC3200 is not set
+CONFIG_APRICOT=m
+CONFIG_B44=m
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+CONFIG_EEPRO100=m
+# CONFIG_EEPRO100_PIO is not set
+CONFIG_E100=m
+CONFIG_E100_NAPI=y
+CONFIG_FEALNX=m
+CONFIG_FORCEDETH=m
+CONFIG_NATSEMI=m
+CONFIG_NE2K_PCI=m
+CONFIG_8139CP=m
+CONFIG_8139TOO=m
+CONFIG_8139TOO_PIO=y
+# CONFIG_8139TOO_TUNE_TWISTER is not set
+CONFIG_8139TOO_8129=y
+# CONFIG_8139_OLD_RX_RESET is not set
+CONFIG_SIS900=m
+CONFIG_EPIC100=m
+# CONFIG_SUNDANCE is not set
+# CONFIG_SUNDANCE_MMIO is not set
+CONFIG_TLAN=m
+CONFIG_VIA_RHINE=m
+CONFIG_VIA_RHINE_MMIO=y
+CONFIG_VIA_VELOCITY=m
+CONFIG_NET_POCKET=y
+# CONFIG_ATP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+CONFIG_ACENIC=m
+# CONFIG_ACENIC_OMIT_TIGON_I is not set
+CONFIG_DL2K=m
+CONFIG_E1000=m
+CONFIG_E1000_NAPI=y
+CONFIG_NS83820=m
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+CONFIG_R8169=m
+CONFIG_R8169_NAPI=y
+CONFIG_SK98LIN=m
+CONFIG_TIGON3=m
+
+#
+# Ethernet (10000 Mbit)
+#
+CONFIG_IXGB=m
+CONFIG_IXGB_NAPI=y
+CONFIG_S2IO=m
+CONFIG_S2IO_NAPI=y
+CONFIG_FDDI=y
+# CONFIG_DEFXX is not set
+# CONFIG_SKFP is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PLIP is not set
+CONFIG_PPP=m
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_ASYNC=m
+CONFIG_PPP_SYNC_TTY=m
+CONFIG_PPP_DEFLATE=m
+CONFIG_IPPP_FILTER=y
+# CONFIG_PPP_BSDCOMP is not set
+CONFIG_PPPOE=m
+# CONFIG_SLIP is not set
+
+#
+# Wireless LAN (non-hamradio)
+#
+CONFIG_NET_RADIO=y
+
+#
+# Obsolete Wireless cards support (pre-802.11)
+#
+# CONFIG_STRIP is not set
+# CONFIG_ARLAN is not set
+CONFIG_WAVELAN=m
+CONFIG_PCMCIA_WAVELAN=m
+CONFIG_PCMCIA_NETWAVE=m
+
+#
+# Wireless 802.11 Frequency Hopping cards support
+#
+# CONFIG_PCMCIA_RAYCS is not set
+
+#
+# Wireless 802.11b ISA/PCI cards support
+#
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
+CONFIG_AIRO=m
+CONFIG_HERMES=m
+CONFIG_PLX_HERMES=m
+CONFIG_TMD_HERMES=m
+CONFIG_PCI_HERMES=m
+CONFIG_ATMEL=m
+CONFIG_PCI_ATMEL=m
+CONFIG_PRISM54=m
+
+#
+# Wireless 802.11b Pcmcia/Cardbus cards support
+#
+CONFIG_PCMCIA_HERMES=m
+CONFIG_AIRO_CS=m
+CONFIG_PCMCIA_ATMEL=m
+CONFIG_PCMCIA_WL3501=m
+CONFIG_NET_WIRELESS=y
+
+#
+# Token Ring devices
+#
+CONFIG_TR=y
+CONFIG_IBMOL=m
+CONFIG_3C359=m
+CONFIG_TMS380TR=m
+CONFIG_TMSPCI=m
+CONFIG_ABYSS=m
+CONFIG_IBMTR=m
+CONFIG_IBMLS=m
+CONFIG_SKISA=m
+CONFIG_PROTEON=m
+CONFIG_SMCTR=m
+CONFIG_PCMCIA_IBMTR=m
+
+
+CONFIG_NET_FC=y
+# CONFIG_SHAPER is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+
+#
+# PCMCIA network device support
+#
+CONFIG_NET_PCMCIA=y
+CONFIG_PCMCIA_3C589=m
+CONFIG_PCMCIA_3C574=m
+CONFIG_PCMCIA_FMVJ18X=m
+CONFIG_PCMCIA_PCNET=m
+CONFIG_PCMCIA_NMCLAN=m
+CONFIG_PCMCIA_SMC91C92=m
+CONFIG_PCMCIA_XIRC2PS=m
+CONFIG_PCMCIA_AXNET=m
+
+#
+# Amateur Radio support
+#
+# CONFIG_HAMRADIO is not set
+
+#
+# IrDA (infrared) support
+#
+# CONFIG_IRDA is not set
+# CONFIG_IRDA is not set
+# CONFIG_IRDA_DEBUG is not set
+CONFIG_IRLAN=m
+CONFIG_IRNET=m
+CONFIG_IRCOMM=m
+# CONFIG_IRDA_ULTRA is not set
+CONFIG_IRDA_CACHE_LAST_LSAP=y
+CONFIG_IRDA_FAST_RR=y
+CONFIG_IRTTY_SIR=m
+CONFIG_DONGLE=y
+CONFIG_ESI_DONGLE=m
+CONFIG_ACTISYS_DONGLE=m
+CONFIG_TEKRAM_DONGLE=m
+CONFIG_IRPORT_SIR=m
+# CONFIG_DONGLE_OLD is not set
+CONFIG_LITELINK_DONGLE=m
+CONFIG_MA600_DONGLE=m
+CONFIG_GIRBIL_DONGLE=m
+CONFIG_MCP2120_DONGLE=m
+CONFIG_OLD_BELKIN_DONGLE=m
+CONFIG_ACT200L_DONGLE=m
+
+CONFIG_USB_IRDA=m
+CONFIG_NSC_FIR=m
+CONFIG_SIGMATEL_FIR=m
+# CONFIG_WINBOND_FIR is not set
+# CONFIG_TOSHIBA_FIR is not set
+# CONFIG_SMC_IRCC_FIR is not set
+# CONFIG_ALI_FIR is not set
+# CONFIG_VLSI_FIR is not set
+# CONFIG_VIA_FIR is not set
+
+
+
+#
+# Bluetooth support
+#
+CONFIG_BT=m
+CONFIG_BT_L2CAP=m
+CONFIG_BT_SCO=m
+CONFIG_BT_CMTP=m
+CONFIG_BT_RFCOMM=m
+CONFIG_BT_RFCOMM_TTY=y
+CONFIG_BT_BNEP=m
+CONFIG_BT_BNEP_MC_FILTER=y
+CONFIG_BT_BNEP_PROTO_FILTER=y
+CONFIG_BT_HIDP=m
+
+#
+# Bluetooth device drivers
+#
+CONFIG_BT_HCIUSB=m
+CONFIG_BT_HCIUART=m
+CONFIG_BT_HCIUART_H4=y
+CONFIG_BT_HCIUART_BCSP=y
+CONFIG_BT_HCIUART_BCSP_TXCRC=y
+CONFIG_BT_HCIDTL1=m
+CONFIG_BT_HCIBT3C=m
+CONFIG_BT_HCIBLUECARD=m
+CONFIG_BT_HCIBTUART=m
+CONFIG_BT_HCIVHCI=m
+CONFIG_BT_HCIUSB_SCO=y
+CONFIG_BT_HCIBCM203X=m
+CONFIG_BT_HCIBFUSB=m
+CONFIG_USB_BLUETOOTH_TTY=m
+
+#
+# ISDN subsystem
+#
+
+CONFIG_ISDN=m
+CONFIG_ISDN_I4L=m
+CONFIG_ISDN_DRV_AVMB1_B1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCI=m
+CONFIG_ISDN_DRV_AVMB1_T1ISA=m
+CONFIG_ISDN_DRV_AVMB1_B1PCMCIA=m
+CONFIG_ISDN_DRV_AVMB1_T1PCI=m
+CONFIG_ISDN_DRV_AVMB1_C4=m
+
+CONFIG_ISDN_PPP=y
+CONFIG_ISDN_PPP_VJ=y
+CONFIG_ISDN_MPP=y
+# CONFIG_ISDN_PPP_BSDCOMP is not set
+CONFIG_ISDN_TTY_FAX=y
+CONFIG_DE_AOC=y
+
+CONFIG_ISDN_AUDIO=y
+
+CONFIG_ISDN_DRV_HISAX=m
+CONFIG_ISDN_DRV_ICN=m
+CONFIG_ISDN_DRV_PCBIT=m
+CONFIG_ISDN_DRV_SC=m
+CONFIG_ISDN_DRV_ACT2000=m
+CONFIG_ISDN_DRV_TPAM=m
+CONFIG_ISDN_DRV_AVMB1_B1PCIV4=y
+CONFIG_ISDN_DRV_AVMB1_AVM_CS=m
+
+CONFIG_ISDN_CAPI_CAPIDRV=m
+
+CONFIG_HISAX_EURO=y
+CONFIG_HISAX_1TR6=y
+CONFIG_HISAX_NI1=y
+CONFIG_HISAX_MAX_CARDS=8
+CONFIG_HISAX_16_0=y
+CONFIG_HISAX_16_3=y
+CONFIG_HISAX_TELESPCI=y
+CONFIG_HISAX_S0BOX=y
+CONFIG_HISAX_AVM_A1=y
+CONFIG_HISAX_FRITZPCI=y
+CONFIG_HISAX_AVM_A1_PCMCIA=y
+CONFIG_HISAX_ELSA=y
+CONFIG_HISAX_IX1MICROR2=y
+CONFIG_HISAX_DIEHLDIVA=y
+CONFIG_HISAX_ASUSCOM=y
+CONFIG_HISAX_TELEINT=y
+CONFIG_HISAX_HFCS=y
+CONFIG_HISAX_SEDLBAUER=y
+CONFIG_HISAX_SPORTSTER=y
+CONFIG_HISAX_MIC=y
+CONFIG_HISAX_NETJET=y
+CONFIG_HISAX_NETJET_U=y
+CONFIG_HISAX_NICCY=y
+CONFIG_HISAX_ISURF=y
+CONFIG_HISAX_HSTSAPHIR=y
+CONFIG_HISAX_BKM_A4T=y
+CONFIG_HISAX_SCT_QUADRO=y
+CONFIG_HISAX_GAZEL=y
+CONFIG_HISAX_HFC_PCI=y
+CONFIG_HISAX_W6692=y
+CONFIG_HISAX_HFC_SX=y
+CONFIG_HISAX_ENTERNOW_PCI=y
+# CONFIG_HISAX_DEBUG is not set
+CONFIG_HISAX_AVM_A1_CS=m
+CONFIG_HISAX_ST5481=m
+CONFIG_HISAX_HFCUSB=m
+CONFIG_HISAX_FRITZ_PCIPNP=m
+CONFIG_HISAX_NO_SENDCOMPLETE=y
+CONFIG_HISAX_NO_LLC=y
+CONFIG_HISAX_NO_KEYPAD=y
+CONFIG_HISAX_SEDLBAUER_CS=m
+CONFIG_HISAX_ELSA_CS=m
+CONFIG_HISAX_TELES_CS=m
+
+CONFIG_ISDN_DRV_LOOP=m
+CONFIG_HYSDN=m
+CONFIG_HYSDN_CAPI=y
+
+
+#
+# CAPI subsystem
+#
+CONFIG_ISDN_CAPI=m
+CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON=y
+CONFIG_ISDN_CAPI_MIDDLEWARE=y
+CONFIG_ISDN_CAPI_CAPI20=m
+CONFIG_ISDN_CAPI_CAPIFS_BOOL=y
+CONFIG_ISDN_CAPI_CAPIFS=m
+
+#
+# CAPI hardware drivers
+#
+
+#
+# Active AVM cards
+#
+CONFIG_CAPI_AVM=y
+
+#
+# Active Eicon DIVA Server cards
+#
+# CONFIG_CAPI_EICON is not set
+CONFIG_ISDN_DIVAS=m
+CONFIG_ISDN_DIVAS_BRIPCI=y
+CONFIG_ISDN_DIVAS_PRIPCI=y
+CONFIG_ISDN_DIVAS_DIVACAPI=m
+CONFIG_ISDN_DIVAS_USERIDI=m
+CONFIG_ISDN_DIVAS_MAINT=m
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+CONFIG_INPUT_JOYDEV=m
+# CONFIG_INPUT_TSDEV is not set
+CONFIG_INPUT_EVDEV=y
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input I/O drivers
+#
+# CONFIG_GAMEPORT is not set
+CONFIG_SOUND_GAMEPORT=m
+CONFIG_GAMEPORT_NS558=m
+CONFIG_GAMEPORT_L4=m
+CONFIG_GAMEPORT_EMU10K1=m
+CONFIG_GAMEPORT_VORTEX=m
+CONFIG_GAMEPORT_FM801=m
+CONFIG_GAMEPORT_CS461x=m
+CONFIG_SERIO=y
+CONFIG_SERIO_I8042=y
+CONFIG_SERIO_SERPORT=y
+# CONFIG_SERIO_RAW is not set
+
+# CONFIG_SERIO_CT82C710 is not set
+# CONFIG_SERIO_PARKBD is not set
+# CONFIG_SERIO_PCIPS2 is not set
+
+#
+# Input Device Drivers
+#
+CONFIG_INPUT_KEYBOARD=y
+CONFIG_KEYBOARD_ATKBD=y
+# CONFIG_KEYBOARD_SUNKBD is not set
+# CONFIG_KEYBOARD_XTKBD is not set
+# CONFIG_KEYBOARD_NEWTON is not set
+# CONFIG_KEYBOARD_LKKBD is not set
+CONFIG_INPUT_MOUSE=y
+CONFIG_MOUSE_PS2=y
+CONFIG_MOUSE_SERIAL=m
+CONFIG_MOUSE_INPORT=m
+CONFIG_MOUSE_ATIXL=y
+CONFIG_MOUSE_LOGIBM=m
+CONFIG_MOUSE_PC110PAD=m
+CONFIG_MOUSE_VSXXXAA=m
+CONFIG_INPUT_JOYSTICK=y
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+CONFIG_JOYSTICK_JOYDUMP=m
+CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_GUNZE=m
+CONFIG_INPUT_MISC=y
+CONFIG_INPUT_PCSPKR=m
+CONFIG_INPUT_UINPUT=m 
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+CONFIG_SERIAL_NONSTANDARD=y
+# CONFIG_ROCKETPORT is not set
+# CONFIG_SYNCLINK is not set
+# CONFIG_SYNCLINKMP is not set
+CONFIG_N_HDLC=m
+CONFIG_STALDRV=y
+# CONFIG_FTAPE is not set
+# CONFIG_IBM_ASM is not set
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_CS=m
+# CONFIG_SERIAL_8250_ACPI is not set
+CONFIG_SERIAL_8250_NR_UARTS=4
+CONFIG_SERIAL_8250_EXTENDED=y
+# CONFIG_SERIAL_8250_MANY_PORTS is not set
+CONFIG_SERIAL_8250_SHARE_IRQ=y
+CONFIG_SERIAL_8250_DETECT_IRQ=y
+CONFIG_SERIAL_8250_MULTIPORT=y
+CONFIG_SERIAL_8250_RSA=y
+# CONFIG_COMPUTONE is not set
+# CONFIG_CYCLADES is not set
+# CONFIG_DIGIEPCA is not set
+# CONFIG_DIGI is not set
+# CONFIG_ESPSERIAL is not set
+# CONFIG_MOXA_INTELLIO is not set
+# CONFIG_MOXA_SMARTIO is not set
+# CONFIG_ISI is not set
+# CONFIG_RISCOM8 is not set
+# CONFIG_SPECIALIX is not set
+# CONFIG_SX is not set
+# CONFIG_RIO is not set
+# CONFIG_STALLION is not set
+# CONFIG_ISTALLION is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+# CONFIG_LEGACY_PTYS is not set
+CONFIG_PRINTER=m
+CONFIG_LP_CONSOLE=y
+CONFIG_PPDEV=m
+# CONFIG_TIPAR is not set
+
+#
+# I2C support
+#
+CONFIG_I2C=m
+CONFIG_I2C_CHARDEV=m
+
+#
+# I2C Algorithms
+#
+# CONFIG_I2C_DEBUG_ALGO is not set
+CONFIG_I2C_ALGOBIT=m
+CONFIG_I2C_ALGOPCF=m
+
+#
+# I2C Hardware Bus support
+#
+CONFIG_I2C_ALI1535=m
+CONFIG_I2C_ALI15X3=m
+CONFIG_I2C_AMD756=m
+CONFIG_I2C_AMD8111=m
+CONFIG_I2C_I801=m
+CONFIG_I2C_I810=m
+CONFIG_I2C_ISA=m
+CONFIG_I2C_NFORCE2=m
+CONFIG_I2C_PIIX4=m
+CONFIG_I2C_PROSAVAGE=m
+CONFIG_I2C_SAVAGE4=m
+# CONFIG_SCx200_ACB is not set
+CONFIG_I2C_SIS5595=m
+CONFIG_I2C_SIS630=m
+CONFIG_I2C_SIS96X=m
+CONFIG_I2C_VIA=m
+CONFIG_I2C_VIAPRO=m
+CONFIG_I2C_VOODOO3=m
+# CONFIG_I2C_ELEKTOR is not set
+CONFIG_I2C_PARPORT=m
+CONFIG_I2C_PARPORT_LIGHT=m
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+# CONFIG_I2C_PARPORT is not set
+CONFIG_I2C_ALI1563=m
+# CONFIG_I2C_PARPORT_LIGHT is not set
+CONFIG_I2C_ALGOPCA=m
+# CONFIG_I2C_PCA_ISA is not set
+
+
+#
+# I2C Hardware Sensors Chip support
+#
+CONFIG_I2C_SENSOR=m
+CONFIG_SENSORS_ADM1021=m
+CONFIG_SENSORS_EEPROM=m
+CONFIG_SENSORS_IT87=m
+CONFIG_SENSORS_LM75=m
+CONFIG_SENSORS_LM78=m
+CONFIG_SENSORS_LM80=m
+CONFIG_SENSORS_LM83=m
+CONFIG_SENSORS_LM85=m
+CONFIG_SENSORS_VIA686A=m
+CONFIG_SENSORS_W83781D=m
+CONFIG_SENSORS_ASB100=m
+CONFIG_SENSORS_LM90=m
+CONFIG_SENSORS_W83L785TS=m
+CONFIG_SENSORS_FSCHER=m
+CONFIG_SENSORS_GL518SM=m
+CONFIG_SENSORS_DS1621=m
+CONFIG_SENSORS_W83627HF=m
+CONFIG_SENSORS_PCF8574=m
+CONFIG_SENSORS_PCF8591=m
+CONFIG_SENSORS_RTC8564=m
+CONFIG_SENSORS_MAX1619=m
+CONFIG_SENSORS_ADM1025=m
+CONFIG_SENSORS_ADM1031=m
+CONFIG_SENSORS_LM77=m
+CONFIG_SENSORS_SMSC47M1=m
+
+# CONFIG_W1 is not set
+
+#
+# Mice
+#
+CONFIG_CRASH=m
+
+#
+# IPMI
+#
+CONFIG_IPMI_HANDLER=m
+# CONFIG_IPMI_PANIC_EVENT is not set
+CONFIG_IPMI_DEVICE_INTERFACE=m
+CONFIG_IPMI_WATCHDOG=m
+CONFIG_IPMI_SI=m
+CONFIG_IPMI_POWEROFF=m
+
+#
+# Watchdog Cards
+#
+CONFIG_WATCHDOG=y
+# CONFIG_WATCHDOG_NOWAYOUT is not set
+CONFIG_SOFT_WATCHDOG=m
+CONFIG_WDT=m
+# CONFIG_WDT_501 is not set
+CONFIG_WDTPCI=m
+CONFIG_WDT_501_PCI=y
+CONFIG_PCWATCHDOG=m
+CONFIG_ACQUIRE_WDT=m
+CONFIG_ADVANTECH_WDT=m
+CONFIG_EUROTECH_WDT=m
+CONFIG_IB700_WDT=m
+CONFIG_I8XX_TCO=m
+# CONFIG_MIXCOMWD is not set
+# CONFIG_SCx200_WDT is not set
+# CONFIG_60XX_WDT is not set
+CONFIG_W83877F_WDT=m
+CONFIG_W83627HF_WDT=m
+CONFIG_MACHZ_WDT=m
+CONFIG_SC520_WDT=m
+CONFIG_ALIM7101_WDT=m
+CONFIG_ALIM1535_WDT=m
+CONFIG_SC1200_WDT=m
+CONFIG_WAFER_WDT=m
+CONFIG_CPU5_WDT=m
+CONFIG_PCIPCWATCHDOG=m
+CONFIG_USBPCWATCHDOG=m
+
+
+CONFIG_HW_RANDOM=m
+# CONFIG_NVRAM is not set
+CONFIG_RTC=y
+CONFIG_DTLK=m
+# CONFIG_R3964 is not set
+# CONFIG_APPLICOM is not set
+# CONFIG_SONYPI is not set
+
+#
+# Ftape, the floppy tape device driver
+#
+CONFIG_AGP=y
+CONFIG_AGP_ALI=y
+CONFIG_AGP_ATI=y
+CONFIG_AGP_AMD=y
+CONFIG_AGP_AMD64=y
+CONFIG_AGP_INTEL=y
+CONFIG_AGP_INTEL_MCH=y
+CONFIG_AGP_NVIDIA=y
+CONFIG_AGP_SIS=y
+CONFIG_AGP_SWORKS=y
+CONFIG_AGP_VIA=y
+CONFIG_AGP_EFFICEON=y
+CONFIG_DRM=y
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+CONFIG_DRM_R128=m
+CONFIG_DRM_RADEON=m
+CONFIG_DRM_I810=m
+CONFIG_DRM_I830=m
+CONFIG_DRM_MGA=m
+# CONFIG_DRM_SIS is not set
+CONFIG_DRM_I915=m
+
+
+
+#
+# PCMCIA character devices
+#
+# CONFIG_SYNCLINK_CS is not set
+
+
+
+# CONFIG_MWAVE is not set
+CONFIG_RAW_DRIVER=y
+CONFIG_MAX_RAW_DEVS=8192
+CONFIG_HANGCHECK_TIMER=m
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Video For Linux
+#
+
+#
+# Video Adapters
+#
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+CONFIG_VIDEO_OVCAMCHIP=m
+
+
+#
+# Radio Adapters
+#
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+CONFIG_DVB_CORE=m
+
+#
+# Supported Frontend Modules
+#
+CONFIG_DVB_STV0299=m
+# CONFIG_DVB_SP887X is not set
+# CONFIG_DVB_ALPS_TDLB7 is not set
+CONFIG_DVB_ALPS_TDMB7=m
+CONFIG_DVB_ATMEL_AT76C651=m
+CONFIG_DVB_CX24110=m
+CONFIG_DVB_GRUNDIG_29504_491=m
+CONFIG_DVB_GRUNDIG_29504_401=m
+CONFIG_DVB_MT312=m
+CONFIG_DVB_VES1820=m
+CONFIG_DVB_VES1X93=m
+CONFIG_DVB_TWINHAN_DST=m
+CONFIG_DVB_TTUSB_DEC=m
+CONFIG_DVB_BT8XX=m
+# CONFIG_DVB_TDA1004X is not set
+CONFIG_DVB_NXT6000=m
+
+#
+# Supported SAA7146 based PCI Adapters
+#
+CONFIG_DVB_AV7110=m
+CONFIG_DVB_AV7110_OSD=y
+# CONFIG_DVB_AV7110_FIRMWARE is not set
+CONFIG_DVB_BUDGET=m
+CONFIG_DVB_BUDGET_CI=m
+CONFIG_DVB_BUDGET_AV=m
+CONFIG_DVB_BUDGET_PATCH=m
+
+#
+# Supported USB Adapters
+#
+CONFIG_DVB_TTUSB_BUDGET=m
+
+#
+# Supported FlexCopII (B2C2) Adapters
+#
+CONFIG_DVB_B2C2_SKYSTAR=m
+CONFIG_VIDEO_SAA7146=m
+CONFIG_VIDEO_SAA7146_VV=m
+CONFIG_VIDEO_VIDEOBUF=m
+CONFIG_VIDEO_TUNER=m
+CONFIG_VIDEO_BUF=m
+CONFIG_VIDEO_BTCX=m
+
+#
+# Graphics support
+#
+CONFIG_FB=y
+# CONFIG_FB_CYBER2000 is not set
+# CONFIG_FB_IMSTT is not set
+CONFIG_FB_VGA16=m
+CONFIG_FB_VESA=y
+CONFIG_VIDEO_SELECT=y
+# CONFIG_FB_HGA is not set
+CONFIG_FB_RIVA=m
+# CONFIG_FB_RIVA_DEBUG is not set
+# CONFIG_FB_RIVA_I2C is not set
+CONFIG_FB_I810=m
+CONFIG_FB_I810_GTF=y
+# CONFIG_FB_MATROX is not set
+CONFIG_FB_MATROX_MILLENIUM=y
+CONFIG_FB_MATROX_MYSTIQUE=y
+CONFIG_FB_MATROX_G450=y
+CONFIG_FB_MATROX_G100=y
+CONFIG_FB_MATROX_I2C=m
+CONFIG_FB_MATROX_MAVEN=m
+CONFIG_FB_MATROX_MULTIHEAD=y
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_RADEON_DEBUG is not set
+# CONFIG_FB_RADEON_OLD is not set
+CONFIG_FB_RADEON_I2C=y
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_ATY is not set
+CONFIG_FB_ATY_CT=y
+CONFIG_FB_ATY_GX=y
+# CONFIG_FB_ATY_XL_INIT is not set
+# CONFIG_FB_SIS is not set
+CONFIG_FB_SIS_300=y
+CONFIG_FB_SIS_315=y
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VIRTUAL is not set
+CONFIG_FB_KYRO=m
+# CONFIG_FB_PM2 is not set
+# CONFIG_FB_PM2_FIFO_DISCONNECT is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+CONFIG_FB_CIRRUS=m
+
+#
+# Console display driver support
+#
+CONFIG_VGA_CONSOLE=y
+# CONFIG_MDA_CONSOLE is not set
+CONFIG_DUMMY_CONSOLE=y
+CONFIG_FRAMEBUFFER_CONSOLE=y
+# CONFIG_FONTS is not set
+
+
+#
+# Logo configuration
+#
+CONFIG_LOGO=y
+# CONFIG_LOGO_LINUX_MONO is not set
+# CONFIG_LOGO_LINUX_VGA16 is not set
+CONFIG_LOGO_LINUX_CLUT224=y
+
+#
+# Sound
+#
+CONFIG_SOUND=m
+
+#
+# Advanced Linux Sound Architecture
+#
+CONFIG_SND=m
+CONFIG_SND_SEQUENCER=m
+CONFIG_SND_SEQ_DUMMY=m
+CONFIG_SND_OSSEMUL=y
+CONFIG_SND_MIXER_OSS=m
+CONFIG_SND_PCM_OSS=m
+CONFIG_SND_SEQUENCER_OSS=y
+CONFIG_SND_RTCTIMER=m
+# CONFIG_SND_VERBOSE_PRINTK is not set
+# CONFIG_SND_DEBUG is not set
+CONFIG_SND_BIT32_EMUL=y
+
+#
+# Generic devices
+#
+CONFIG_SND_DUMMY=m
+CONFIG_SND_VIRMIDI=m
+CONFIG_SND_MTPAV=m
+# CONFIG_SND_SERIAL_U16550 is not set
+CONFIG_SND_MPU401=m
+
+#
+# ISA devices
+#
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+
+#
+# PCI devices
+#
+CONFIG_SND_ALI5451=m
+CONFIG_SND_AZT3328=m
+CONFIG_SND_CS46XX=m
+CONFIG_SND_CS46XX_NEW_DSP=y
+CONFIG_SND_CS4281=m
+CONFIG_SND_EMU10K1=m
+CONFIG_SND_KORG1212=m
+CONFIG_SND_NM256=m
+CONFIG_SND_RME32=m
+CONFIG_SND_RME96=m
+CONFIG_SND_RME9652=m
+CONFIG_SND_HDSP=m
+CONFIG_SND_TRIDENT=m
+CONFIG_SND_YMFPCI=m
+CONFIG_SND_ALS4000=m
+CONFIG_SND_CMIPCI=m
+CONFIG_SND_ENS1370=m
+CONFIG_SND_ENS1371=m
+CONFIG_SND_ES1938=m
+CONFIG_SND_ES1968=m
+CONFIG_SND_MAESTRO3=m
+CONFIG_SND_FM801=m
+CONFIG_SND_ICE1712=m
+CONFIG_SND_ICE1724=m
+CONFIG_SND_INTEL8X0=m
+CONFIG_SND_SONICVIBES=m
+CONFIG_SND_VIA82XX=m
+CONFIG_SND_VX222=m
+CONFIG_SND_BT87X=m
+CONFIG_SND_ATIIXP=m
+CONFIG_SND_ATIIXP_MODEM=m
+CONFIG_SND_AU8810=m
+CONFIG_SND_AU8820=m
+CONFIG_SND_AU8830=m
+CONFIG_SND_MIXART=m
+CONFIG_SND_FM801_TEA575X=m
+CONFIG_SND_INTEL8X0M=m
+CONFIG_SND_PDAUDIOCF=m
+
+
+#
+# ALSA USB devices
+#
+CONFIG_SND_USB_AUDIO=m
+CONFIG_SND_USB_USX2Y=m
+
+#
+# PCMCIA devices
+#
+# CONFIG_SND_VXPOCKET is not set
+# CONFIG_SND_VXP440 is not set
+
+#
+# Open Sound System
+#
+# CONFIG_SOUND_PRIME is not set
+# CONFIG_SOUND_BT878 is not set
+# CONFIG_SOUND_CMPCI is not set
+
+#
+# USB support
+#
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+CONFIG_USB_DEVICEFS=y
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+CONFIG_USB_SUSPEND=y
+
+#
+# USB Host Controller Drivers
+#
+CONFIG_USB_EHCI_HCD=m
+CONFIG_USB_EHCI_SPLIT_ISO=y
+CONFIG_USB_EHCI_ROOT_HUB_TT=y
+CONFIG_USB_OHCI_HCD=m
+CONFIG_USB_UHCI_HCD=m
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_AUDIO is not set
+
+#
+# USB Bluetooth TTY can only be used with disabled Bluetooth subsystem
+#
+CONFIG_USB_MIDI=m
+CONFIG_USB_ACM=m
+CONFIG_USB_PRINTER=m
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_USB_STORAGE=m
+# CONFIG_USB_STORAGE_DEBUG is not set
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_DPCM=y
+CONFIG_USB_STORAGE_HP8200e=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_RW_DETECT=y
+
+#
+# USB Human Interface Devices (HID)
+#
+CONFIG_USB_HID=y
+CONFIG_USB_HIDINPUT=y
+CONFIG_HID_FF=y
+CONFIG_HID_PID=y
+CONFIG_LOGITECH_FF=y
+CONFIG_THRUSTMASTER_FF=y
+CONFIG_USB_HIDDEV=y
+
+#
+# USB HID Boot Protocol drivers
+#
+# CONFIG_USB_KBD is not set
+# CONFIG_USB_MOUSE is not set
+CONFIG_USB_AIPTEK=m
+CONFIG_USB_WACOM=m
+CONFIG_USB_KBTAB=m
+CONFIG_USB_POWERMATE=m
+CONFIG_USB_XPAD=m
+
+#
+# USB Imaging devices
+#
+CONFIG_USB_MDC800=m
+CONFIG_USB_MICROTEK=m
+CONFIG_USB_HPUSBSCSI=m
+
+#
+# USB Multimedia devices
+#
+CONFIG_USB_DABUSB=m
+CONFIG_USB_VICAM=m
+CONFIG_USB_DSBR=m
+CONFIG_USB_IBMCAM=m
+CONFIG_USB_KONICAWC=m
+CONFIG_USB_OV511=m
+CONFIG_USB_SE401=m
+CONFIG_USB_STV680=m
+CONFIG_USB_SN9C102=m
+
+#
+# USB Network adaptors
+#
+CONFIG_USB_CATC=m
+CONFIG_USB_KAWETH=m
+CONFIG_USB_PEGASUS=m
+CONFIG_USB_RTL8150=m
+CONFIG_USB_USBNET=m
+CONFIG_USB_SPEEDTOUCH=m
+
+#
+# USB Host-to-Host Cables
+#
+CONFIG_USB_AN2720=y
+CONFIG_USB_BELKIN=y
+CONFIG_USB_GENESYS=y
+CONFIG_USB_NET1080=y
+CONFIG_USB_PL2301=y
+
+#
+# Intelligent USB Devices/Gadgets
+#
+CONFIG_USB_ARMLINUX=y
+CONFIG_USB_EPSON2888=y
+CONFIG_USB_ZAURUS=y
+CONFIG_USB_CDCETHER=y
+
+#
+# USB Network Adapters
+#
+CONFIG_USB_AX8817X=y
+
+#
+# USB port drivers
+#
+CONFIG_USB_USS720=m
+
+#
+# USB Serial Converter support
+#
+CONFIG_USB_SERIAL=m
+CONFIG_USB_SERIAL_GENERIC=y
+CONFIG_USB_SERIAL_BELKIN=m
+CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m
+CONFIG_USB_SERIAL_EMPEG=m
+CONFIG_USB_SERIAL_FTDI_SIO=m
+CONFIG_USB_SERIAL_VISOR=m
+CONFIG_USB_SERIAL_IPAQ=m
+CONFIG_USB_SERIAL_IR=m
+CONFIG_USB_SERIAL_EDGEPORT=m
+CONFIG_USB_SERIAL_EDGEPORT_TI=m
+CONFIG_USB_SERIAL_KEYSPAN_PDA=m
+CONFIG_USB_SERIAL_KEYSPAN=m
+CONFIG_USB_SERIAL_KEYSPAN_MPR=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XA=y
+CONFIG_USB_SERIAL_KEYSPAN_USA28XB=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19=y
+CONFIG_USB_SERIAL_KEYSPAN_USA18X=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QW=y
+CONFIG_USB_SERIAL_KEYSPAN_USA19QI=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49W=y
+CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y
+CONFIG_USB_SERIAL_KLSI=m
+CONFIG_USB_SERIAL_KOBIL_SCT=m
+CONFIG_USB_SERIAL_MCT_U232=m
+CONFIG_USB_SERIAL_PL2303=m
+CONFIG_USB_SERIAL_SAFE=m
+CONFIG_USB_SERIAL_SAFE_PADDED=y
+CONFIG_USB_SERIAL_CYBERJACK=m
+CONFIG_USB_SERIAL_XIRCOM=m
+CONFIG_USB_SERIAL_OMNINET=m
+CONFIG_USB_SERIAL_WHITEHEAT=m
+CONFIG_USB_EZUSB=y
+CONFIG_USB_EMI62=m
+CONFIG_USB_LED=m
+CONFIG_USB_G_SERIAL=m
+
+
+#
+# USB Miscellaneous drivers
+#
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_TIGL is not set
+CONFIG_USB_AUERSWALD=m
+CONFIG_USB_RIO500=m
+CONFIG_USB_LCD=m
+CONFIG_USB_TEST=m
+# CONFIG_USB_GADGET is not set
+# CONFIG_USB_GADGET_PXA2XX is not set
+# CONFIG_USB_GADGET_GOKU is not set
+# CONFIG_USB_GADGET_SA1100 is not set
+CONFIG_USB_ZERO=m
+CONFIG_USB_ETH=m
+CONFIG_USB_GADGETFS=m
+CONFIG_USB_W9968CF=m
+CONFIG_USB_PWC=m
+CONFIG_USB_LEGOTOWER=m
+CONFIG_USB_FILE_STORAGE=m
+# CONFIG_USB_FILE_STORAGE_TEST is not set
+CONFIG_USB_MTOUCH=m
+CONFIG_USB_ATI_REMOTE=m
+CONFIG_USB_ALI_M5632=y
+# CONFIG_USB_CYTHERM is not set
+CONFIG_USB_EGALAX=m
+CONFIG_USB_PHIDGETSERVO=m
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT2_FS_POSIX_ACL=y
+CONFIG_EXT2_FS_SECURITY=y
+CONFIG_EXT3_FS=m
+CONFIG_EXT3_FS_XATTR=y
+CONFIG_EXT3_FS_POSIX_ACL=y
+CONFIG_EXT3_FS_SECURITY=y
+CONFIG_JBD=m
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_REISERFS_CHECK is not set
+CONFIG_REISERFS_PROC_INFO=y
+CONFIG_REISERFS_FS_XATTR=y
+CONFIG_REISERFS_FS_POSIX_ACL=y
+CONFIG_REISERFS_FS_SECURITY=y
+# CONFIG_JFS_FS is not set
+# CONFIG_JFS_DEBUG is not set
+# CONFIG_JFS_STATISTICS is not set
+CONFIG_JFS_POSIX_ACL=y
+# CONFIG_XFS_FS is not set
+# CONFIG_XFS_RT is not set
+CONFIG_XFS_QUOTA=y
+CONFIG_XFS_POSIX_ACL=y
+CONFIG_XFS_SECURITY=y
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_QUOTA=y
+# CONFIG_QFMT_V1 is not set
+CONFIG_QFMT_V2=y
+CONFIG_QUOTACTL=y
+# CONFIG_AUTOFS_FS is not set
+CONFIG_AUTOFS4_FS=m
+
+#
+# CD-ROM/DVD Filesystems
+#
+CONFIG_ISO9660_FS=y
+CONFIG_JOLIET=y
+CONFIG_ZISOFS=y
+CONFIG_ZISOFS_FS=y
+CONFIG_UDF_FS=m
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=m
+CONFIG_MSDOS_FS=m
+CONFIG_VFAT_FS=m
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="ascii"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+# CONFIG_DEVFS_FS is not set
+CONFIG_DEVPTS_FS_XATTR=y
+CONFIG_DEVPTS_FS_SECURITY=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_XATTR=y
+CONFIG_TMPFS_SECURITY=y
+CONFIG_HUGETLBFS=y
+CONFIG_HUGETLB_PAGE=y
+CONFIG_RAMFS=y
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not seta
+# CONFIG_AFFS_FS is not set
+# uses sleepon and needs a major update
+CONFIG_HFS_FS=m
+CONFIG_HFSPLUS_FS=m
+# CONFIG_BEFS_FS is not set
+# CONFIG_BEFS_DEBUG is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_JFFS_FS is not set
+CONFIG_JFFS2_FS=m
+CONFIG_JFFS2_FS_DEBUG=0
+CONFIG_JFFS2_FS_NAND=y
+CONFIG_CRAMFS=m
+CONFIG_VXFS_FS=m
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_QNX4FS_RW is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_UFS_FS_WRITE is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=m
+CONFIG_NFS_V3=y
+CONFIG_NFS_V4=y
+CONFIG_NFS_DIRECTIO=y
+CONFIG_NFSD=m
+CONFIG_NFSD_V3=y
+CONFIG_NFSD_V4=y
+CONFIG_NFSD_TCP=y
+CONFIG_LOCKD=m
+CONFIG_LOCKD_V4=y
+CONFIG_EXPORTFS=m
+CONFIG_SUNRPC=m
+CONFIG_SUNRPC_GSS=m
+CONFIG_RPCSEC_GSS_KRB5=m
+CONFIG_RPCSEC_GSS_SPKM3=m
+CONFIG_SMB_FS=m
+# CONFIG_SMB_NLS_DEFAULT is not set
+CONFIG_CIFS=m
+# CONFIG_CIFS_STATS is not set
+CONFIG_CIFS_XATTR=y
+CONFIG_CIFS_POSIX=y
+# CONFIG_NCP_FS is not set
+CONFIG_NCPFS_PACKET_SIGNING=y
+CONFIG_NCPFS_IOCTL_LOCKING=y
+CONFIG_NCPFS_STRONG=y
+CONFIG_NCPFS_NFS_NS=y
+CONFIG_NCPFS_OS2_NS=y
+CONFIG_NCPFS_SMALLDOS=y
+CONFIG_NCPFS_NLS=y
+CONFIG_NCPFS_EXTRAS=y
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+# CONFIG_RXRPC is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_ACORN_PARTITION is not set
+CONFIG_OSF_PARTITION=y
+# CONFIG_AMIGA_PARTITION is not set
+# CONFIG_ATARI_PARTITION is not set
+CONFIG_MAC_PARTITION=y
+CONFIG_MSDOS_PARTITION=y
+CONFIG_BSD_DISKLABEL=y
+CONFIG_MINIX_SUBPARTITION=y
+CONFIG_SOLARIS_X86_PARTITION=y
+CONFIG_UNIXWARE_DISKLABEL=y
+# CONFIG_LDM_PARTITION is not set
+CONFIG_SGI_PARTITION=y
+# CONFIG_ULTRIX_PARTITION is not set
+CONFIG_SUN_PARTITION=y
+CONFIG_EFI_PARTITION=y
+CONFIG_NLS=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS_DEFAULT="utf8"
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_CODEPAGE_737=m
+CONFIG_NLS_CODEPAGE_775=m
+CONFIG_NLS_CODEPAGE_850=m
+CONFIG_NLS_CODEPAGE_852=m
+CONFIG_NLS_CODEPAGE_855=m
+CONFIG_NLS_CODEPAGE_857=m
+CONFIG_NLS_CODEPAGE_860=m
+CONFIG_NLS_CODEPAGE_861=m
+CONFIG_NLS_CODEPAGE_862=m
+CONFIG_NLS_CODEPAGE_863=m
+CONFIG_NLS_CODEPAGE_864=m
+CONFIG_NLS_CODEPAGE_865=m
+CONFIG_NLS_CODEPAGE_866=m
+CONFIG_NLS_CODEPAGE_869=m
+CONFIG_NLS_CODEPAGE_936=m
+CONFIG_NLS_CODEPAGE_950=m
+CONFIG_NLS_CODEPAGE_932=m
+CONFIG_NLS_CODEPAGE_949=m
+CONFIG_NLS_CODEPAGE_874=m
+CONFIG_NLS_ISO8859_8=m
+CONFIG_NLS_CODEPAGE_1250=m
+CONFIG_NLS_CODEPAGE_1251=m
+CONFIG_NLS_ISO8859_1=m
+CONFIG_NLS_ISO8859_2=m
+CONFIG_NLS_ISO8859_3=m
+CONFIG_NLS_ISO8859_4=m
+CONFIG_NLS_ISO8859_5=m
+CONFIG_NLS_ISO8859_6=m
+CONFIG_NLS_ISO8859_7=m
+CONFIG_NLS_ISO8859_9=m
+CONFIG_NLS_ISO8859_13=m
+CONFIG_NLS_ISO8859_14=m
+CONFIG_NLS_ISO8859_15=m
+CONFIG_NLS_KOI8_R=m
+CONFIG_NLS_KOI8_U=m
+CONFIG_NLS_UTF8=m
+CONFIG_NLS_ASCII=y
+
+#
+# Profiling support
+#
+CONFIG_PROFILING=y
+CONFIG_OPROFILE=m
+
+#
+# Tux
+#
+CONFIG_TUX=m
+CONFIG_TUX_EXTCGI=y
+# CONFIG_TUX_EXTENDED_LOG is not set
+# CONFIG_TUX_DEBUG is not set
+
+
+#
+# Kernel hacking
+#
+CONFIG_DEBUG_KERNEL=y
+# CONFIG_DEBUG_SLAB is not set
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_HIGHMEM=y
+# CONFIG_DEBUG_INFO is not set
+CONFIG_DEBUG_SPINLOCK_SLEEP=y
+# CONFIG_FRAME_POINTER is not set
+CONFIG_CC_OPTIMIZE_FOR_SIZE=y
+# CONFIG_DEBUG_DRIVER is not set
+
+#
+# Security options
+#
+CONFIG_SECURITY=y
+CONFIG_SECURITY_NETWORK=y
+CONFIG_SECURITY_CAPABILITIES=y
+# CONFIG_SECURITY_ROOTPLUG is not set
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SELINUX_BOOTPARAM=y
+CONFIG_SECURITY_SELINUX_DISABLE=y
+CONFIG_SECURITY_SELINUX_DEVELOP=y
+CONFIG_SECURITY_SELINUX_AVC_STATS=y
+# CONFIG_SECURITY_SELINUX_MLS is not set
+CONFIG_SECURITY_SELINUX_BOOTPARAM_VALUE=1
+CONFIG_AUDIT=y
+CONFIG_AUDITSYSCALL=y
+
+#
+# Cryptographic options
+#
+CONFIG_CRYPTO=y
+CONFIG_CRYPTO_HMAC=y
+CONFIG_CRYPTO_NULL=m
+CONFIG_CRYPTO_MD4=m
+CONFIG_CRYPTO_MD5=m
+CONFIG_CRYPTO_SHA1=y
+CONFIG_CRYPTO_SHA256=m
+CONFIG_CRYPTO_SHA512=m
+CONFIG_CRYPTO_DES=m
+CONFIG_CRYPTO_BLOWFISH=m
+CONFIG_CRYPTO_TWOFISH=m
+CONFIG_CRYPTO_SERPENT=m
+CONFIG_CRYPTO_AES=m
+CONFIG_CRYPTO_CAST5=m
+CONFIG_CRYPTO_CAST6=m
+CONFIG_CRYPTO_DEFLATE=m
+CONFIG_CRYPTO_ARC4=m
+CONFIG_CRYPTO_MICHAEL_MIC=m
+# CONFIG_CRYPTO_TEST is not set
+CONFIG_LIBCRC32C=m
+CONFIG_CRYPTO_CRC32C=m
+CONFIG_CRYPTO_SIGNATURE_DSA=y
+CONFIG_CRYPTO_MPILIB=y
+CONFIG_CRYPTO_TEA=m
+CONFIG_CRYPTO_KHAZAD=m
+CONFIG_CRYPTO_WP512=m
+
+#
+# Library routines
+#
+CONFIG_CRC32=m
+CONFIG_CRC_CCITT=m
+
+CONFIG_ZLIB_INFLATE=y
+CONFIG_ZLIB_DEFLATE=m
+CONFIG_PC=y
+# CONFIG_SCSI_BUSLOGIC is not set
+# CONFIG_SCSI_INIA100 is not set
+# CONFIG_ATALK is not set
+# CONFIG_DEV_APPLETALK is not set
+# CONFIG_LTPC is not set
+# CONFIG_COPS is not set
+# CONFIG_IPX is not set
+# CONFIG_IPDDP is not set
+# CONFIG_IRDA is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_ISAPNP is not set
+# CONFIG_PCMCIA_AHA152X is not set
+# CONFIG_PCMCIA_NINJA_SCSI is not set
+# CONFIG_PCMCIA_QLOGIC is not set
+# CONFIG_IEEE1394 is not set
+# CONFIG_EL1 is not set
+# CONFIG_EL2 is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_WD80x3 is not set
+# CONFIG_IRDA is not set
+# CONFIG_GAMEPORT is not set
+# CONFIG_DVB is not set
+# CONFIG_SND_AD1816A is not set
+# CONFIG_SND_AD1848 is not set
+# CONFIG_SND_CS4231 is not set
+# CONFIG_SND_CS4232 is not set
+# CONFIG_SND_CS4236 is not set
+# CONFIG_SND_ES968 is not set
+# CONFIG_SND_ES1688 is not set
+# CONFIG_SND_ES18XX is not set
+# CONFIG_SND_GUSCLASSIC is not set
+# CONFIG_SND_GUSEXTREME is not set
+# CONFIG_SND_GUSMAX is not set
+# CONFIG_SND_INTERWAVE is not set
+# CONFIG_SND_INTERWAVE_STB is not set
+# CONFIG_SND_OPTI92X_AD1848 is not set
+# CONFIG_SND_OPTI92X_CS4231 is not set
+# CONFIG_SND_OPTI93X is not set
+# CONFIG_SND_SB8 is not set
+# CONFIG_SND_SB16 is not set
+# CONFIG_SND_SBAWE is not set
+# CONFIG_SND_SB16_CSP=y
+# CONFIG_SND_WAVEFRONT is not set
+# CONFIG_SND_ALS100 is not set
+# CONFIG_SND_AZT2320 is not set
+# CONFIG_SND_CMI8330 is not set
+# CONFIG_SND_DT019X is not set
+# CONFIG_SND_OPL3SA2 is not set
+# CONFIG_SND_SGALAXY is not set
+# CONFIG_SND_SSCAPE is not set
+# CONFIG_REISERFS_FS is not set
+# CONFIG_XFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+# CONFIG_WAN_ROUTER is not set
+# CONFIG_ROMFS_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_BINFMT_AOUT is not set
+# CONFIG_DRM_TDFX is not set
+# CONFIG_DRM_GAMMA is not set
+# CONFIG_DRM_SIS is not set
+# CONFIG_BLK_DEV_UMEM is not set
+# CONFIG_MWAVE is not set
+# CONFIG_ROCKETPORT is not set
+# CONFIG_R3964 is not set
+# CONFIG_TIPAR is not set
+# CONFIG_JOYSTICK_ANALOG is not set
+# CONFIG_JOYSTICK_A3D is not set
+# CONFIG_JOYSTICK_ADI is not set
+# CONFIG_JOYSTICK_COBRA is not set
+# CONFIG_JOYSTICK_GF2K is not set
+# CONFIG_JOYSTICK_GRIP is not set
+# CONFIG_JOYSTICK_GRIP_MP is not set
+# CONFIG_JOYSTICK_GUILLEMOT is not set
+# CONFIG_JOYSTICK_INTERACT is not set
+# CONFIG_JOYSTICK_SIDEWINDER is not set
+# CONFIG_JOYSTICK_TMDC is not set
+# CONFIG_JOYSTICK_IFORCE is not set
+# CONFIG_JOYSTICK_IFORCE_USB=y
+# CONFIG_JOYSTICK_IFORCE_232=y
+# CONFIG_JOYSTICK_WARRIOR is not set
+# CONFIG_JOYSTICK_MAGELLAN is not set
+# CONFIG_JOYSTICK_SPACEORB is not set
+# CONFIG_JOYSTICK_SPACEBALL is not set
+# CONFIG_JOYSTICK_STINGER is not set
+# CONFIG_JOYSTICK_TWIDDLER is not set
+# CONFIG_JOYSTICK_DB9 is not set
+# CONFIG_JOYSTICK_GAMECON is not set
+# CONFIG_JOYSTICK_TURBOGRAFX is not set
+# CONFIG_RADIO_CADET is not set
+# CONFIG_RADIO_RTRACK is not set
+# CONFIG_RADIO_RTRACK2 is not set
+# CONFIG_RADIO_AZTECH is not set
+# CONFIG_RADIO_GEMTEK is not set
+# CONFIG_RADIO_GEMTEK_PCI is not set
+# CONFIG_RADIO_MAXIRADIO is not set
+# CONFIG_RADIO_MAESTRO is not set
+# CONFIG_RADIO_MIROPCM20 is not set
+# CONFIG_RADIO_MIROPCM20_RDS is not set
+# CONFIG_RADIO_SF16FMI is not set
+# CONFIG_RADIO_SF16FMR2 is not set
+# CONFIG_RADIO_TERRATEC is not set
+# CONFIG_RADIO_TRUST is not set
+# CONFIG_RADIO_TYPHOON is not set
+# CONFIG_RADIO_TYPHOON_PROC_FS=y
+# CONFIG_RADIO_ZOLTRIX is not set
+# CONFIG_VIDEO_DEV is not set
+# CONFIG_PLIP is not set
+# CONFIG_FB_MATROX is not set
+# CONFIG_FB_3DFX is not set
+# CONFIG_FB_HGA is not set
+# CONFIG_FB_ATY is not set
+# CONFIG_FB_TRIDENT is not set
+# CONFIG_FB_VOODOO1 is not set
+# CONFIG_SCSI_ADVANSYS is not set
+# CONFIG_SCSI_AHA1542 is not set
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+# CONFIG_SCSI_IN2000 is not set
+# CONFIG_SCSI_QLOGIC_FAS is not set
+# CONFIG_SCSI_QLOGIC_ISP is not set
+# CONFIG_VIDEO_BT848 is not set
+# CONFIG_VIDEO_PMS is not set
+# CONFIG_VIDEO_BWQCAM is not set
+# CONFIG_VIDEO_CQCAM is not set
+# CONFIG_VIDEO_W9966 is not set
+# CONFIG_VIDEO_CPIA is not set
+# CONFIG_VIDEO_CPIA_PP is not set
+# CONFIG_VIDEO_CPIA_USB is not set
+# CONFIG_VIDEO_SAA5249 is not set
+# CONFIG_TUNER_3036 is not set
+# CONFIG_VIDEO_STRADIS is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN is not set
+# CONFIG_VIDEO_ZORAN_BUZ is not set
+# CONFIG_VIDEO_ZORAN_DC10 is not set
+# CONFIG_VIDEO_ZORAN_DC30 is not set
+# CONFIG_VIDEO_ZORAN_LML33 is not set
+# CONFIG_VIDEO_ZORAN_LML33R10 is not set
+# CONFIG_VIDEO_MEYE is not set
+# CONFIG_VIDEO_SAA7134 is not set
+# CONFIG_VIDEO_MXB is not set
+# CONFIG_VIDEO_DPC is not set
+# CONFIG_VIDEO_HEXIUM_ORION is not set
+# CONFIG_VIDEO_HEXIUM_GEMINI is not set
+# CONFIG_VIDEO_CX88 is not set
+# CONFIG_VIDEO_SAA5246A is not set
+# CONFIG_FB_ATY128 is not set
+# CONFIG_FB_RADEON is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_I82092 is not set
+# CONFIG_YELLOWFIN is not set
+# CONFIG_SUNDANCE is not set
+# CONFIG_ULTRA is not set
+# CONFIG_SKFP is not set
+# CONFIG_DE600 is not set
+# CONFIG_DE620 is not set
+# CONFIG_CS89x0 is not set
+# CONFIG_DGRS is not set
+# CONFIG_AC3200 is not set
+# CONFIG_NI52 is not set
+# CONFIG_NI65 is not set
+# CONFIG_LANCE is not set
+# CONFIG_ELPLUS is not set
+# CONFIG_EL16 is not set
+# CONFIG_EL3 is not set
+# CONFIG_3C515 is not set
+# CONFIG_HAMACHI is not set
+# CONFIG_HP100 is not set
+# CONFIG_EQUALIZER is not set
+# CONFIG_NET_SB1000 is not set
+# CONFIG_DEPCA is not set
+# CONFIG_ATP is not set
+# CONFIG_FB_NEOMAGIC is not set
+# CONFIG_INFTL is not set
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+# CONFIG_MTD_PMC551 is not set
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PCI is not set
+# CONFIG_PCMCIA_SYM53C500 is not set
+# CONFIG_FB_ASILIANT is not set
+# CONFIG_FB_HGA_ACCEL is not set
+# CONFIG_FB_3DFX_ACCEL is not set
+# CONFIG_FB_TRIDENT_ACCEL is not set
+# CONFIG_SCSI_DC390T is not set
+CONFIG_AUDIT=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_JFS_FS is not set
+# CONFIG_I2C_PCA_ISA is not set
+CONFIG_RAW_DRIVER=y
+# CONFIG_MTD_SCB2_FLASH is not set
+CONFIG_UID16=y
+# CONFIG_MK8 is not set
+# CONFIG_MPSC is not set
+CONFIG_GENERIC_CPU=y
+CONFIG_X86_MSR=y
+CONFIG_X86_CPUID=y
+CONFIG_MTRR=y
+CONFIG_NUMA=y
+CONFIG_K8_NUMA=y
+CONFIG_NR_CPUS=8
+CONFIG_GART_IOMMU=y
+CONFIG_X86_POWERNOW_K8=y
+CONFIG_IA32_EMULATION=y
+# CONFIG_IA32_AOUT is not set
+CONFIG_INIT_DEBUG=y
+# CONFIG_IOMMU_DEBUG is not set
+# CONFIG_CHECKING is not set
+CONFIG_MICROCODE=m 
+CONFIG_SWIOTLB=y
+CONFIG_X86_PM_TIMER=y
+CONFIG_I2O=m
+CONFIG_I2O_BLOCK=m
+CONFIG_I2O_SCSI=m
+CONFIG_I2O_PROC=m
+CONFIG_I2O_CONFIG=y
+CONFIG_TUX=m
+# CONFIG_UNORDERED_IO is not set
+# CONFIG_X86_SPEEDSTEP_CENTRINO is not set
+CONFIG_X86_ACPI_CPUFREQ=y
+# CONFIG_X86_ACPI_CPUFREQ_PROC_INTF is not set
+CONFIG_GENERIC_ISA_DMA=y
+CONFIG_SCHED_SMT=y
+# CONFIG_SOFTWARE_SUSPEND is not set
+# CONFIG_PM_DEBUG is not set
+CONFIG_CPU_FREQ=y
+# CONFIG_CPU_FREQ_PROC_INTF is not set
+# CONFIG_CPU_FREQ_DEFAULT_GOV_PERFORMANCE is not set
+CONFIG_CPU_FREQ_DEFAULT_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_PERFORMANCE=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=m
+CONFIG_CPU_FREQ_GOV_USERSPACE=m
+CONFIG_CPU_FREQ_GOV_ONDEMAND=m
+# CONFIG_CPU_FREQ_24_API is not set
+CONFIG_CPU_FREQ_TABLE=y
+CONFIG_ACPI=y
+CONFIG_ACPI_BOOT=y
+CONFIG_ACPI_INTERPRETER=y
+CONFIG_ACPI_SLEEP=y
+CONFIG_ACPI_AC=m
+CONFIG_ACPI_BATTERY=m
+CONFIG_ACPI_BUTTON=m
+CONFIG_ACPI_FAN=y
+CONFIG_ACPI_PROCESSOR=y
+CONFIG_ACPI_THERMAL=y
+CONFIG_ACPI_ASUS=m
+CONFIG_ACPI_TOSHIBA=m
+# CONFIG_ACPI_DEBUG is not set
+CONFIG_ACPI_BUS=y
+CONFIG_ACPI_EC=y
+CONFIG_ACPI_POWER=y
+CONFIG_ACPI_PCI=y
+CONFIG_ACPI_SYSTEM=y
+CONFIG_ACPI_NUMA=y
+CONFIG_ACPI_BLACKLIST_YEAR=2001
+# CONFIG_SCHEDSTATS is not set
+CONFIG_EDD=m
+CONFIG_PCI_BIOS=y
+CONFIG_PCI_MMCONFIG=y
+CONFIG_KEXEC=y
+CONFIG_NETDUMP=m
+CONFIG_CRASH=m
+CONFIG_HOTPLUG_PCI=y
+# CONFIG_HOTPLUG_PCI_FAKE is not set
+CONFIG_HOTPLUG_PCI_COMPAQ=m
+# CONFIG_HOTPLUG_PCI_COMPAQ_NVRAM is not set
+CONFIG_HOTPLUG_PCI_IBM=m
+CONFIG_HOTPLUG_PCI_ACPI=m 
+CONFIG_HOTPLUG_PCI_ACPI_IBM=m
+# CONFIG_HOTPLUG_PCI_CPCI is not set
+CONFIG_HOTPLUG_PCI_PCIE=m
+# CONFIG_HOTPLUG_PCI_PCIE_POLL_EVENT_MODE is not set
+CONFIG_HOTPLUG_PCI_SHPC=m
+# CONFIG_HOTPLUG_PCI_SHPC_POLL_EVENT_MODE is not set
+# CONFIG_HOTPLUG_PCI_SHPC_PHPRM_LEGACY is not set
+# CONFIG_HPET is not set
+CONFIG_PM=y
+CONFIG_IEEE80211=m
+# CONFIG_IEEE80211_DEBUG is not set
+CONFIG_IEEE80211_CRYPT=m
+CONFIG_IEEE80211_WPA=m
+CONFIG_IEEE80211_CRYPT_CCMP=m
+CONFIG_IEEE80211_CRYPT_TKIP=m
+CONFIG_IPW2100=m
+# CONFIG_IPW_DEBUG is not set
+CONFIG_IPW2100_PROMISC=y
+# CONFIG_IPW2100_LEGACY_FW_LOAD is not set
+CONFIG_IPW2200=m
+# CONFIG_SMP is not set
diff --git a/lustre/kernel_patches/patches/configurable-x86-stack-2.4.20-rh.patch b/lustre/kernel_patches/patches/configurable-x86-stack-2.4.20-rh.patch
deleted file mode 100644 (file)
index f70b0d4..0000000
+++ /dev/null
@@ -1,311 +0,0 @@
-Index: linux-2.4.20-rh-20.9/arch/i386/kernel/entry.S
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/kernel/entry.S 2003-09-13 19:34:35.000000000 +0400
-+++ linux-2.4.20-rh-20.9/arch/i386/kernel/entry.S      2003-12-01 18:02:14.000000000 +0300
-@@ -45,6 +45,7 @@
- #include <linux/linkage.h>
- #include <asm/segment.h>
- #include <asm/smp.h>
-+#include <asm/current.h>
- EBX           = 0x00
- ECX           = 0x04
-@@ -130,10 +131,6 @@
-       .long 3b,6b;    \
- .previous
--#define GET_CURRENT(reg) \
--      movl $-8192, reg; \
--      andl %esp, reg
--
- ENTRY(lcall7)
-       pushfl                  # We get a different stack layout with call gates,
-       pushl %eax              # which has to be cleaned up later..
-@@ -149,7 +146,7 @@
-       movl %ecx,CS(%esp)      #
-       movl %esp,%ebx
-       pushl %ebx
--      andl $-8192,%ebx        # GET_CURRENT
-+      andl $-THREAD_SIZE,%ebx # GET_CURRENT
-       movl exec_domain(%ebx),%edx     # Get the execution domain
-       movl 4(%edx),%edx       # Get the lcall7 handler for the domain
-       pushl $0x7
-@@ -173,7 +170,7 @@
-       movl %ecx,CS(%esp)      #
-       movl %esp,%ebx
-       pushl %ebx
--      andl $-8192,%ebx        # GET_CURRENT
-+      andl $-THREAD_SIZE,%ebx # GET_CURRENT
-       movl exec_domain(%ebx),%edx     # Get the execution domain
-       movl 4(%edx),%edx       # Get the lcall7 handler for the domain
-       pushl $0x27
-Index: linux-2.4.20-rh-20.9/arch/i386/kernel/smpboot.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/kernel/smpboot.c       2003-09-13 19:34:35.000000000 +0400
-+++ linux-2.4.20-rh-20.9/arch/i386/kernel/smpboot.c    2003-12-01 18:02:14.000000000 +0300
-@@ -811,7 +811,7 @@
-       /* So we see what's up   */
-       printk("Booting processor %d/%d eip %lx\n", cpu, apicid, start_eip);
--      stack_start.esp = (void *) (1024 + PAGE_SIZE + (char *)idle);
-+      stack_start.esp = (void *)idle->thread.esp;
-       /*
-        * This grunge runs the startup process for
-@@ -884,7 +884,7 @@
-                       Dprintk("CPU has booted.\n");
-               } else {
-                       boot_error= 1;
--                      if (*((volatile unsigned char *)phys_to_virt(8192))
-+                      if (*((volatile unsigned char *)phys_to_virt(THREAD_SIZE))
-                                       == 0xA5)
-                               /* trampoline started but...? */
-                               printk("Stuck ??\n");
-@@ -907,7 +907,7 @@
-       }
-       /* mark "stuck" area as not stuck */
--      *((volatile unsigned long *)phys_to_virt(8192)) = 0;
-+      *((volatile unsigned long *)phys_to_virt(THREAD_SIZE)) = 0;
-       if(clustered_apic_mode == CLUSTERED_APIC_NUMAQ) {
-               printk("Restoring NMI vector\n");
-Index: linux-2.4.20-rh-20.9/arch/i386/kernel/traps.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/kernel/traps.c 2003-09-13 19:34:35.000000000 +0400
-+++ linux-2.4.20-rh-20.9/arch/i386/kernel/traps.c      2003-12-01 18:02:14.000000000 +0300
-@@ -161,7 +161,7 @@
-       unsigned long esp = tsk->thread.esp;
-       /* User space on another CPU? */
--      if ((esp ^ (unsigned long)tsk) & (PAGE_MASK<<1))
-+      if ((esp ^ (unsigned long)tsk) & ~(THREAD_SIZE - 1))
-               return;
-       show_trace((unsigned long *)esp);
- }
-Index: linux-2.4.20-rh-20.9/arch/i386/kernel/head.S
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/kernel/head.S  2003-09-13 19:34:35.000000000 +0400
-+++ linux-2.4.20-rh-20.9/arch/i386/kernel/head.S       2003-12-01 18:02:14.000000000 +0300
-@@ -15,6 +15,7 @@
- #include <asm/page.h>
- #include <asm/pgtable.h>
- #include <asm/desc.h>
-+#include <asm/current.h>
- #define OLD_CL_MAGIC_ADDR     0x90020
- #define OLD_CL_MAGIC          0xA33F
-@@ -315,7 +316,7 @@
-       ret
- ENTRY(stack_start)
--      .long SYMBOL_NAME(init_task_union)+8192
-+      .long SYMBOL_NAME(init_task_union)+THREAD_SIZE
-       .long __KERNEL_DS
- /* This is the default interrupt "handler" :-) */
-Index: linux-2.4.20-rh-20.9/arch/i386/kernel/irq.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/kernel/irq.c   2003-12-01 17:42:59.000000000 +0300
-+++ linux-2.4.20-rh-20.9/arch/i386/kernel/irq.c        2003-12-01 18:02:14.000000000 +0300
-@@ -581,7 +581,10 @@
-       long esp;
-       /* Debugging check for stack overflow: is there less than 1KB free? */
--      __asm__ __volatile__("andl %%esp,%0" : "=r" (esp) : "0" (8191));
-+      __asm__ __volatile__(
-+              "andl %%esp,%0" 
-+              : "=r" (esp) : "0" (THREAD_SIZE-1));
-+
-       if (unlikely(esp < (sizeof(struct task_struct) + 1024))) {
-               extern void show_stack(unsigned long *);
-Index: linux-2.4.20-rh-20.9/arch/i386/lib/getuser.S
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/lib/getuser.S  1998-01-13 00:42:52.000000000 +0300
-+++ linux-2.4.20-rh-20.9/arch/i386/lib/getuser.S       2003-12-01 18:02:14.000000000 +0300
-@@ -21,6 +21,10 @@
-  * as they get called from within inline assembly.
-  */
-+/* Duplicated from asm/processor.h */
-+#include <asm/current.h>
-+#include <linux/config.h>
-+
- addr_limit = 12
- .text
-@@ -28,7 +32,7 @@
- .globl __get_user_1
- __get_user_1:
-       movl %esp,%edx
--      andl $0xffffe000,%edx
-+      andl $~(THREAD_SIZE - 1),%edx
-       cmpl addr_limit(%edx),%eax
-       jae bad_get_user
- 1:    movzbl (%eax),%edx
-@@ -41,7 +45,7 @@
-       addl $1,%eax
-       movl %esp,%edx
-       jc bad_get_user
--      andl $0xffffe000,%edx
-+      andl $~(THREAD_SIZE - 1),%edx
-       cmpl addr_limit(%edx),%eax
-       jae bad_get_user
- 2:    movzwl -1(%eax),%edx
-@@ -54,7 +58,7 @@
-       addl $3,%eax
-       movl %esp,%edx
-       jc bad_get_user
--      andl $0xffffe000,%edx
-+      andl $~(THREAD_SIZE - 1),%edx
-       cmpl addr_limit(%edx),%eax
-       jae bad_get_user
- 3:    movl -3(%eax),%edx
-Index: linux-2.4.20-rh-20.9/arch/i386/config.in
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/config.in      2003-09-13 19:34:34.000000000 +0400
-+++ linux-2.4.20-rh-20.9/arch/i386/config.in   2003-12-01 18:02:14.000000000 +0300
-@@ -266,6 +266,29 @@
- if [ "$CONFIG_SMP" = "y" -a "$CONFIG_X86_CMPXCHG" = "y" ]; then
-    define_bool CONFIG_HAVE_DEC_LOCK y
- fi
-+
-+choice 'Bigger Stack Size Support' \
-+     "off    CONFIG_NOBIGSTACK \
-+      16KB   CONFIG_STACK_SIZE_16KB \
-+      32KB   CONFIG_STACK_SIZE_32KB \
-+      64KB   CONFIG_STACK_SIZE_64KB" off
-+
-+if [ "$CONFIG_NOBIGSTACK" = "y" ]; then
-+   define_int CONFIG_STACK_SIZE_SHIFT 1
-+else
-+  if [ "$CONFIG_STACK_SIZE_16KB" = "y" ]; then
-+     define_int CONFIG_STACK_SIZE_SHIFT 2
-+  else
-+    if [ "$CONFIG_STACK_SIZE_32KB" = "y" ]; then
-+      define_int CONFIG_STACK_SIZE_SHIFT 3
-+    else
-+      if [ "$CONFIG_STACK_SIZE_64KB" = "y" ]; then
-+        define_int CONFIG_STACK_SIZE_SHIFT 4
-+      fi
-+    fi
-+  fi
-+fi
-+ 
- endmenu
- mainmenu_option next_comment
-Index: linux-2.4.20-rh-20.9/arch/i386/vmlinux.lds
-===================================================================
---- linux-2.4.20-rh-20.9.orig/arch/i386/vmlinux.lds    2003-09-13 19:34:24.000000000 +0400
-+++ linux-2.4.20-rh-20.9/arch/i386/vmlinux.lds 2003-12-01 18:02:14.000000000 +0300
-@@ -38,7 +38,8 @@
-   _edata = .;                 /* End of data section */
--  . = ALIGN(8192);            /* init_task */
-+/* chose the biggest of the possible stack sizes here? */
-+  . = ALIGN(65536);           /* init_task */
-   .data.init_task : { *(.data.init_task) }
-   . = ALIGN(4096);            /* Init code and data */
-Index: linux-2.4.20-rh-20.9/include/asm-i386/current.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/asm-i386/current.h       1998-08-15 03:35:22.000000000 +0400
-+++ linux-2.4.20-rh-20.9/include/asm-i386/current.h    2003-12-01 18:03:28.000000000 +0300
-@@ -1,15 +1,43 @@
- #ifndef _I386_CURRENT_H
- #define _I386_CURRENT_H
-+#include <asm/page.h>
-+
-+/*
-+ * Configurable page sizes on i386, mainly for debugging purposes.
-+ * (c) Balbir Singh
-+ */
-+
-+#ifdef __ASSEMBLY__
-+
-+#define PAGE_SIZE      4096    /* as cannot handle 1UL << 12 */
-+#define THREAD_SIZE ((1 << CONFIG_STACK_SIZE_SHIFT) * PAGE_SIZE)
-+
-+#define GET_CURRENT(reg) \
-+        movl $-THREAD_SIZE, reg; \
-+        andl %esp, reg
-+
-+#else  /* __ASSEMBLY__ */
-+
-+#define THREAD_SIZE ((1 << CONFIG_STACK_SIZE_SHIFT) * PAGE_SIZE)
-+#define __alloc_task_struct() \
-+  ((struct task_struct *) __get_free_pages(GFP_KERNEL,CONFIG_STACK_SIZE_SHIFT))
-+
-+#define __free_task_struct(p) \
-+  free_pages((unsigned long) (p), CONFIG_STACK_SIZE_SHIFT)
-+
-+#define INIT_TASK_SIZE THREAD_SIZE
- struct task_struct;
- static inline struct task_struct * get_current(void)
- {
-       struct task_struct *current;
--      __asm__("andl %%esp,%0; ":"=r" (current) : "0" (~8191UL));
-+      __asm__("andl %%esp,%0; ":"=r" (current) : "0" (~(THREAD_SIZE - 1)));
-       return current;
-  }
-  
- #define current get_current()
-+#endif /* __ASSEMBLY__ */
-+
- #endif /* !(_I386_CURRENT_H) */
-Index: linux-2.4.20-rh-20.9/include/asm-i386/hw_irq.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/asm-i386/hw_irq.h        2003-11-13 17:35:48.000000000 +0300
-+++ linux-2.4.20-rh-20.9/include/asm-i386/hw_irq.h     2003-12-01 18:02:14.000000000 +0300
-@@ -116,10 +116,6 @@
- #define IRQ_NAME2(nr) nr##_interrupt(void)
- #define IRQ_NAME(nr) IRQ_NAME2(IRQ##nr)
--#define GET_CURRENT \
--      "movl %esp, %ebx\n\t" \
--      "andl $-8192, %ebx\n\t"
--
- /*
-  *    SMP has a few special interrupts for IPI messages
-  */
-Index: linux-2.4.20-rh-20.9/include/asm-i386/processor.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/asm-i386/processor.h     2003-10-08 12:29:57.000000000 +0400
-+++ linux-2.4.20-rh-20.9/include/asm-i386/processor.h  2003-12-01 18:02:14.000000000 +0300
-@@ -14,6 +14,7 @@
- #include <asm/types.h>
- #include <asm/sigcontext.h>
- #include <asm/cpufeature.h>
-+#include <asm/current.h>
- #include <linux/cache.h>
- #include <linux/config.h>
- #include <linux/threads.h>
-@@ -469,10 +470,6 @@
- #define KSTK_EIP(tsk) (((unsigned long *)(4096+(unsigned long)(tsk)))[1019])
- #define KSTK_ESP(tsk) (((unsigned long *)(4096+(unsigned long)(tsk)))[1022])
--#define THREAD_SIZE (2*PAGE_SIZE)
--#define __alloc_task_struct() ((struct task_struct *) __get_free_pages(GFP_KERNEL,1))
--#define __free_task_struct(p) do { BUG_ON((p)->state < TASK_ZOMBIE); free_pages((unsigned long) (p), 1); } while (0)
--
- #define init_task     (init_task_union.task)
- #define init_stack    (init_task_union.stack)
-Index: linux-2.4.20-rh-20.9/include/linux/sched.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/linux/sched.h    2003-11-13 17:35:48.000000000 +0300
-+++ linux-2.4.20-rh-20.9/include/linux/sched.h 2003-12-01 18:02:14.000000000 +0300
-@@ -2,6 +2,7 @@
- #define _LINUX_SCHED_H
- #include <asm/param.h>        /* for HZ */
-+#include <asm/current.h>      /* maybe for INIT_TASK_SIZE */
- extern unsigned long event;
diff --git a/lustre/kernel_patches/patches/configurable-x86-stack-2.4.22-rh.patch b/lustre/kernel_patches/patches/configurable-x86-stack-2.4.22-rh.patch
deleted file mode 100644 (file)
index 856425a..0000000
+++ /dev/null
@@ -1,311 +0,0 @@
-Index: linux-2.4.22-ac1/arch/i386/kernel/entry.S
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/kernel/entry.S     2003-09-25 14:16:34.000000000 +0400
-+++ linux-2.4.22-ac1/arch/i386/kernel/entry.S  2003-12-01 18:34:08.000000000 +0300
-@@ -46,6 +46,7 @@
- #include <asm/segment.h>
- #include <asm/smp.h>
- #include <asm/unistd.h>
-+#include <asm/current.h>
- EBX           = 0x00
- ECX           = 0x04
-@@ -131,10 +132,6 @@
-       .long 3b,6b;    \
- .previous
--#define GET_CURRENT(reg) \
--      movl $-8192, reg; \
--      andl %esp, reg
--
- ENTRY(lcall7)
-       pushfl                  # We get a different stack layout with call gates,
-       pushl %eax              # which has to be cleaned up later..
-@@ -150,7 +147,7 @@
-       movl %ecx,CS(%esp)      #
-       movl %esp,%ebx
-       pushl %ebx
--      andl $-8192,%ebx        # GET_CURRENT
-+      andl $-THREAD_SIZE,%ebx # GET_CURRENT
-       movl exec_domain(%ebx),%edx     # Get the execution domain
-       movl 4(%edx),%edx       # Get the lcall7 handler for the domain
-       pushl $0x7
-@@ -174,7 +171,7 @@
-       movl %ecx,CS(%esp)      #
-       movl %esp,%ebx
-       pushl %ebx
--      andl $-8192,%ebx        # GET_CURRENT
-+      andl $-THREAD_SIZE,%ebx # GET_CURRENT
-       movl exec_domain(%ebx),%edx     # Get the execution domain
-       movl 4(%edx),%edx       # Get the lcall7 handler for the domain
-       pushl $0x27
-Index: linux-2.4.22-ac1/arch/i386/kernel/smpboot.c
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/kernel/smpboot.c   2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1/arch/i386/kernel/smpboot.c        2003-12-01 18:34:08.000000000 +0300
-@@ -814,7 +814,7 @@
-       /* So we see what's up   */
-       printk("Booting processor %d/%d eip %lx\n", cpu, apicid, start_eip);
--      stack_start.esp = (void *) (1024 + PAGE_SIZE + (char *)idle);
-+      stack_start.esp = (void *)idle->thread.esp;
-       /*
-        * This grunge runs the startup process for
-@@ -887,7 +887,7 @@
-                       Dprintk("CPU has booted.\n");
-               } else {
-                       boot_error= 1;
--                      if (*((volatile unsigned char *)phys_to_virt(8192))
-+                      if (*((volatile unsigned char *)phys_to_virt(THREAD_SIZE))
-                                       == 0xA5)
-                               /* trampoline started but...? */
-                               printk("Stuck ??\n");
-@@ -910,7 +910,7 @@
-       }
-       /* mark "stuck" area as not stuck */
--      *((volatile unsigned long *)phys_to_virt(8192)) = 0;
-+      *((volatile unsigned long *)phys_to_virt(THREAD_SIZE)) = 0;
-       if(clustered_apic_mode == CLUSTERED_APIC_NUMAQ) {
-               printk("Restoring NMI vector\n");
-Index: linux-2.4.22-ac1/arch/i386/kernel/traps.c
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/kernel/traps.c     2003-09-25 14:16:29.000000000 +0400
-+++ linux-2.4.22-ac1/arch/i386/kernel/traps.c  2003-12-01 18:34:08.000000000 +0300
-@@ -161,7 +161,7 @@
-       unsigned long esp = tsk->thread.esp;
-       /* User space on another CPU? */
--      if ((esp ^ (unsigned long)tsk) & (PAGE_MASK<<1))
-+      if ((esp ^ (unsigned long)tsk) & ~(THREAD_SIZE - 1))
-               return;
-       show_trace((unsigned long *)esp);
- }
-Index: linux-2.4.22-ac1/arch/i386/kernel/head.S
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/kernel/head.S      2003-09-25 14:16:27.000000000 +0400
-+++ linux-2.4.22-ac1/arch/i386/kernel/head.S   2003-12-01 18:34:08.000000000 +0300
-@@ -15,6 +15,7 @@
- #include <asm/page.h>
- #include <asm/pgtable.h>
- #include <asm/desc.h>
-+#include <asm/current.h>
- #define OLD_CL_MAGIC_ADDR     0x90020
- #define OLD_CL_MAGIC          0xA33F
-@@ -315,7 +316,7 @@
-       ret
- ENTRY(stack_start)
--      .long SYMBOL_NAME(init_task_union)+8192
-+      .long SYMBOL_NAME(init_task_union)+THREAD_SIZE
-       .long __KERNEL_DS
- /* This is the default interrupt "handler" :-) */
-Index: linux-2.4.22-ac1/arch/i386/kernel/irq.c
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/kernel/irq.c       2003-09-25 14:16:18.000000000 +0400
-+++ linux-2.4.22-ac1/arch/i386/kernel/irq.c    2003-12-01 18:34:08.000000000 +0300
-@@ -581,7 +581,10 @@
-       long esp;
-       /* Debugging check for stack overflow: is there less than 1KB free? */
--      __asm__ __volatile__("andl %%esp,%0" : "=r" (esp) : "0" (8191));
-+      __asm__ __volatile__(
-+              "andl %%esp,%0" 
-+              : "=r" (esp) : "0" (THREAD_SIZE-1));
-+
-       if (unlikely(esp < (sizeof(struct task_struct) + 1024))) {
-               extern void show_stack(unsigned long *);
-Index: linux-2.4.22-ac1/arch/i386/lib/getuser.S
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/lib/getuser.S      1998-01-13 00:42:52.000000000 +0300
-+++ linux-2.4.22-ac1/arch/i386/lib/getuser.S   2003-12-01 18:34:08.000000000 +0300
-@@ -21,6 +21,10 @@
-  * as they get called from within inline assembly.
-  */
-+/* Duplicated from asm/processor.h */
-+#include <asm/current.h>
-+#include <linux/config.h>
-+
- addr_limit = 12
- .text
-@@ -28,7 +32,7 @@
- .globl __get_user_1
- __get_user_1:
-       movl %esp,%edx
--      andl $0xffffe000,%edx
-+      andl $~(THREAD_SIZE - 1),%edx
-       cmpl addr_limit(%edx),%eax
-       jae bad_get_user
- 1:    movzbl (%eax),%edx
-@@ -41,7 +45,7 @@
-       addl $1,%eax
-       movl %esp,%edx
-       jc bad_get_user
--      andl $0xffffe000,%edx
-+      andl $~(THREAD_SIZE - 1),%edx
-       cmpl addr_limit(%edx),%eax
-       jae bad_get_user
- 2:    movzwl -1(%eax),%edx
-@@ -54,7 +58,7 @@
-       addl $3,%eax
-       movl %esp,%edx
-       jc bad_get_user
--      andl $0xffffe000,%edx
-+      andl $~(THREAD_SIZE - 1),%edx
-       cmpl addr_limit(%edx),%eax
-       jae bad_get_user
- 3:    movl -3(%eax),%edx
-Index: linux-2.4.22-ac1/arch/i386/config.in
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/config.in  2003-09-25 14:16:34.000000000 +0400
-+++ linux-2.4.22-ac1/arch/i386/config.in       2003-12-01 18:34:08.000000000 +0300
-@@ -304,6 +304,29 @@
- if [ "$CONFIG_SMP" = "y" -a "$CONFIG_X86_CMPXCHG" = "y" ]; then
-    define_bool CONFIG_HAVE_DEC_LOCK y
- fi
-+
-+choice 'Bigger Stack Size Support' \
-+     "off    CONFIG_NOBIGSTACK \
-+      16KB   CONFIG_STACK_SIZE_16KB \
-+      32KB   CONFIG_STACK_SIZE_32KB \
-+      64KB   CONFIG_STACK_SIZE_64KB" off
-+
-+if [ "$CONFIG_NOBIGSTACK" = "y" ]; then
-+   define_int CONFIG_STACK_SIZE_SHIFT 1
-+else
-+  if [ "$CONFIG_STACK_SIZE_16KB" = "y" ]; then
-+     define_int CONFIG_STACK_SIZE_SHIFT 2
-+  else
-+    if [ "$CONFIG_STACK_SIZE_32KB" = "y" ]; then
-+      define_int CONFIG_STACK_SIZE_SHIFT 3
-+    else
-+      if [ "$CONFIG_STACK_SIZE_64KB" = "y" ]; then
-+        define_int CONFIG_STACK_SIZE_SHIFT 4
-+      fi
-+    fi
-+  fi
-+fi
-+ 
- endmenu
- mainmenu_option next_comment
-Index: linux-2.4.22-ac1/arch/i386/vmlinux.lds
-===================================================================
---- linux-2.4.22-ac1.orig/arch/i386/vmlinux.lds        2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1/arch/i386/vmlinux.lds     2003-12-01 18:34:08.000000000 +0300
-@@ -38,7 +38,8 @@
-   _edata = .;                 /* End of data section */
--  . = ALIGN(8192);            /* init_task */
-+/* chose the biggest of the possible stack sizes here? */
-+  . = ALIGN(65536);           /* init_task */
-   .data.init_task : { *(.data.init_task) }
-   . = ALIGN(4096);            /* Init code and data */
-Index: linux-2.4.22-ac1/include/asm-i386/current.h
-===================================================================
---- linux-2.4.22-ac1.orig/include/asm-i386/current.h   1998-08-15 03:35:22.000000000 +0400
-+++ linux-2.4.22-ac1/include/asm-i386/current.h        2003-12-01 18:34:16.000000000 +0300
-@@ -1,15 +1,43 @@
- #ifndef _I386_CURRENT_H
- #define _I386_CURRENT_H
-+#include <asm/page.h>
-+
-+/*
-+ * Configurable page sizes on i386, mainly for debugging purposes.
-+ * (c) Balbir Singh
-+ */
-+
-+#ifdef __ASSEMBLY__
-+
-+#define PAGE_SIZE      4096    /* as cannot handle 1UL << 12 */
-+#define THREAD_SIZE ((1 << CONFIG_STACK_SIZE_SHIFT) * PAGE_SIZE)
-+
-+#define GET_CURRENT(reg) \
-+        movl $-THREAD_SIZE, reg; \
-+        andl %esp, reg
-+
-+#else  /* __ASSEMBLY__ */
-+
-+#define THREAD_SIZE ((1 << CONFIG_STACK_SIZE_SHIFT) * PAGE_SIZE)
-+#define __alloc_task_struct() \
-+  ((struct task_struct *) __get_free_pages(GFP_KERNEL,CONFIG_STACK_SIZE_SHIFT))
-+
-+#define __free_task_struct(p) \
-+  free_pages((unsigned long) (p), CONFIG_STACK_SIZE_SHIFT)
-+
-+#define INIT_TASK_SIZE THREAD_SIZE
- struct task_struct;
- static inline struct task_struct * get_current(void)
- {
-       struct task_struct *current;
--      __asm__("andl %%esp,%0; ":"=r" (current) : "0" (~8191UL));
-+      __asm__("andl %%esp,%0; ":"=r" (current) : "0" (~(THREAD_SIZE - 1)));
-       return current;
-  }
-  
- #define current get_current()
-+#endif /* __ASSEMBLY__ */
-+
- #endif /* !(_I386_CURRENT_H) */
-Index: linux-2.4.22-ac1/include/asm-i386/hw_irq.h
-===================================================================
---- linux-2.4.22-ac1.orig/include/asm-i386/hw_irq.h    2003-09-26 00:54:45.000000000 +0400
-+++ linux-2.4.22-ac1/include/asm-i386/hw_irq.h 2003-12-01 18:34:08.000000000 +0300
-@@ -114,10 +114,6 @@
- #define IRQ_NAME2(nr) nr##_interrupt(void)
- #define IRQ_NAME(nr) IRQ_NAME2(IRQ##nr)
--#define GET_CURRENT \
--      "movl %esp, %ebx\n\t" \
--      "andl $-8192, %ebx\n\t"
--
- /*
-  *    SMP has a few special interrupts for IPI messages
-  */
-Index: linux-2.4.22-ac1/include/asm-i386/processor.h
-===================================================================
---- linux-2.4.22-ac1.orig/include/asm-i386/processor.h 2003-09-26 00:54:44.000000000 +0400
-+++ linux-2.4.22-ac1/include/asm-i386/processor.h      2003-12-01 18:34:08.000000000 +0300
-@@ -14,6 +14,7 @@
- #include <asm/types.h>
- #include <asm/sigcontext.h>
- #include <asm/cpufeature.h>
-+#include <asm/current.h>
- #include <linux/cache.h>
- #include <linux/config.h>
- #include <linux/threads.h>
-@@ -465,10 +466,6 @@
- #define KSTK_EIP(tsk) (((unsigned long *)(4096+(unsigned long)(tsk)))[1019])
- #define KSTK_ESP(tsk) (((unsigned long *)(4096+(unsigned long)(tsk)))[1022])
--#define THREAD_SIZE (2*PAGE_SIZE)
--#define __alloc_task_struct() ((struct task_struct *) __get_free_pages(GFP_KERNEL,1))
--#define __free_task_struct(p) do { BUG_ON((p)->state < TASK_ZOMBIE); free_pages((unsigned long) (p), 1); } while (0)
--
- #define init_task     (init_task_union.task)
- #define init_stack    (init_task_union.stack)
-Index: linux-2.4.22-ac1/include/linux/sched.h
-===================================================================
---- linux-2.4.22-ac1.orig/include/linux/sched.h        2003-11-13 18:21:42.000000000 +0300
-+++ linux-2.4.22-ac1/include/linux/sched.h     2003-12-01 18:34:08.000000000 +0300
-@@ -2,6 +2,7 @@
- #define _LINUX_SCHED_H
- #include <asm/param.h>        /* for HZ */
-+#include <asm/current.h>      /* maybe for INIT_TASK_SIZE */
- extern unsigned long event;
diff --git a/lustre/kernel_patches/patches/dev_read_only-2.6-lnxi.patch b/lustre/kernel_patches/patches/dev_read_only-2.6-lnxi.patch
new file mode 100644 (file)
index 0000000..75062ea
--- /dev/null
@@ -0,0 +1,150 @@
+--- linux-2.6.5.orig/drivers/block/ll_rw_blk.c 2005-03-16 10:09:28.000000000 -0800
++++ linux-2.6.5/drivers/block/ll_rw_blk.c      2005-03-16 10:57:38.197357003 -0800
+@@ -2458,7 +2458,7 @@ static inline void blk_partition_remap(s
+       }
+ }
+-int dev_check_rdonly(dev_t dev);
++int dev_check_rdonly(struct block_device *bdev);
+ /**
+  * generic_make_request: hand a buffer to its device driver for I/O
+@@ -2550,9 +2550,9 @@ end_io:
+               /* this is cfs's dev_rdonly check */
+               if (bio->bi_rw == WRITE &&
+-                              dev_check_rdonly(bio->bi_bdev->bd_dev)) {
+-                      bio_endio(bio, bio->bi_size, 0);
+-                      break;
++                              dev_check_rdonly(bio->bi_bdev)) {
++                      bio_endio(bio, bio->bi_size, 0);
++                      break;
+               }
+               /*
+@@ -3086,53 +3086,85 @@ void swap_io_context(struct io_context *
+       *ioc2 = temp;
+ }
+-#define MAX_RDONLY_DEVS               16
+-
+-static dev_t rdonly_devs[MAX_RDONLY_DEVS] = {0, };
+-
+ /*
+  * Debug code for turning block devices "read-only" (will discard writes
+  * silently).  This is for filesystem crash/recovery testing.
+  */
+-void dev_set_rdonly(struct block_device *bdev, int no_write)
+-{
+-      if (no_write >= MAX_RDONLY_DEVS) {
+-              printk(KERN_ALERT "%s:%d illegal arg %d (max %d)\n",
+-                              __FILE__, __LINE__, no_write, MAX_RDONLY_DEVS);
+-              return;
+-      }
+-
+-      if (bdev) {
+-              printk(KERN_WARNING "Turning device %s read-only at %d\n",
+-                              bdev->bd_disk ? bdev->bd_disk->disk_name : "?",
+-                              no_write);
+-              rdonly_devs[no_write] = bdev->bd_dev;
+-      }
+-}
++struct deventry {
++        dev_t dev;
++        struct deventry *next;
++};
+-void dev_clear_rdonly(int no_write)
+-{
+-      if (no_write >= MAX_RDONLY_DEVS) {
+-              printk(KERN_ALERT "%s:%d illegal arg %d (max %d)\n",
+-                              __FILE__, __LINE__, no_write, MAX_RDONLY_DEVS);
+-              return;
+-      }
++static struct deventry *devlist = NULL;
++static spinlock_t devlock = SPIN_LOCK_UNLOCKED; 
+-      if (rdonly_devs[no_write] == 0)
+-              return;
+-      
+-      printk(KERN_WARNING "Clearing read-only at %d\n", no_write);
+-      rdonly_devs[no_write] = 0;
+-}
+-
+-int dev_check_rdonly(dev_t dev)
++int dev_check_rdonly(struct block_device *bdev) 
+ {
+-      int i;
+-
+-      for (i = 0; i < MAX_RDONLY_DEVS; i++)
+-              if (rdonly_devs[i] == dev)
+-                      return 1;
+-      return 0;
++        struct deventry *cur;
++        if (!bdev) return 0;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (bdev->bd_dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        return 1;
++                }
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
++        return 0;
++}
++
++void dev_set_rdonly(struct block_device *bdev)
++{
++        struct deventry *newdev, *cur;
++
++        if (!bdev) 
++              return;
++        newdev = kmalloc(sizeof(struct deventry), GFP_KERNEL);
++        if (!newdev) 
++              return;
++
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (bdev->bd_dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        kfree(newdev);
++                        return;
++                }
++                cur = cur->next;
++        }
++        newdev->dev = bdev->bd_dev;
++        newdev->next = devlist;
++        devlist = newdev;
++        spin_unlock(&devlock);
++        printk(KERN_WARNING "Turning device %s read-only\n",
++               bdev->bd_disk ? bdev->bd_disk->disk_name : "?");
++}
++
++void dev_clear_rdonly(struct block_device *bdev) 
++{
++        struct deventry *cur, *last = NULL;
++        if (!bdev) return;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (bdev->bd_dev == cur->dev) {
++                        if (last) 
++                                last->next = cur->next;
++                        else
++                                devlist = cur->next;
++                        spin_unlock(&devlock);
++                        kfree(cur);
++                        printk(KERN_WARNING "Removing read-only on %s\n",
++                             bdev->bd_disk ? bdev->bd_disk->disk_name : "?");
++                      return;
++                }
++                last = cur;
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
+ }
+ EXPORT_SYMBOL(dev_set_rdonly);
index 9639f28..db6b72d 100644 (file)
- drivers/block/ll_rw_blk.c |   49 ++++++++++++++++++++++++++++++++++++++++++++++
- include/linux/blkdev.h    |    1 
- 2 files changed, 50 insertions(+)
-
-Index: linux-2.6.0/drivers/block/ll_rw_blk.c
-===================================================================
---- linux-2.6.0.orig/drivers/block/ll_rw_blk.c 2004-01-04 15:27:35.000000000 +0300
-+++ linux-2.6.0/drivers/block/ll_rw_blk.c      2004-01-07 17:35:57.000000000 +0300
-@@ -2298,6 +2298,13 @@
+--- linux-2.6.5.orig/drivers/block/ll_rw_blk.c 2005-03-16 11:08:47.404935605 -0800
++++ linux-2.6.5/drivers/block/ll_rw_blk.c      2005-03-16 10:57:38.197357003 -0800
+@@ -2458,6 +2458,8 @@ static inline void blk_partition_remap(s
+       }
+ }
++int dev_check_rdonly(struct block_device *bdev);
++
+ /**
+  * generic_make_request: hand a buffer to its device driver for I/O
+  * @bio:  The bio describing the location in memory and on the device.
+@@ -2546,6 +2548,13 @@ end_io:
                if (test_bit(QUEUE_FLAG_DEAD, &q->queue_flags))
                        goto end_io;
  
 +              /* this is cfs's dev_rdonly check */
 +              if (bio->bi_rw == WRITE &&
-+                              dev_check_rdonly(bio->bi_bdev->bd_dev)) {
-+                      bio_endio(bio, bio->bi_size, 0);
-+                      break;
++                              dev_check_rdonly(bio->bi_bdev)) {
++                      bio_endio(bio, bio->bi_size, 0);
++                      break;
 +              }
 +
                /*
                 * If this device has partitions, remap block n
                 * of partition p to block n+start(p) of the disk.
-@@ -2805,6 +2812,58 @@
-       *ioc2 = temp;
+@@ -3078,6 +3087,91 @@ void swap_io_context(struct io_context *
  }
  
-+#define MAX_RDONLY_DEVS               16
-+
-+static dev_t rdonly_devs[MAX_RDONLY_DEVS] = {0, };
-+
-+/*
+ /*
 + * Debug code for turning block devices "read-only" (will discard writes
 + * silently).  This is for filesystem crash/recovery testing.
 + */
-+void dev_set_rdonly(struct block_device *bdev, int no_write)
-+{
-+      if (no_write >= MAX_RDONLY_DEVS) {
-+              printk(KERN_ALERT "%s:%d illegal arg %d (max %d)\n",
-+                              __FILE__, __LINE__, no_write, MAX_RDONLY_DEVS);
-+              return;
-+      }
++struct deventry {
++        dev_t dev;
++        struct deventry *next;
++};
 +
-+      if (bdev) {
-+              printk(KERN_WARNING "Turning device %s read-only at %d\n",
-+                              bdev->bd_disk ? bdev->bd_disk->disk_name : "?",
-+                              no_write);
-+              rdonly_devs[no_write] = bdev->bd_dev;
-+      }
++static struct deventry *devlist = NULL;
++static spinlock_t devlock = SPIN_LOCK_UNLOCKED; 
++
++int dev_check_rdonly(struct block_device *bdev) 
++{
++        struct deventry *cur;
++        if (!bdev) return 0;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (bdev->bd_dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        return 1;
++                }
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
++        return 0;
 +}
 +
-+void dev_clear_rdonly(int no_write)
++void dev_set_rdonly(struct block_device *bdev)
 +{
-+      if (no_write >= MAX_RDONLY_DEVS) {
-+              printk(KERN_ALERT "%s:%d illegal arg %d (max %d)\n",
-+                              __FILE__, __LINE__, no_write, MAX_RDONLY_DEVS);
-+              return;
-+      }
++        struct deventry *newdev, *cur;
 +
-+      if (rdonly_devs[no_write] == 0)
-+              return;
-+      
-+      printk(KERN_WARNING "Clearing read-only at %d\n", no_write);
-+      rdonly_devs[no_write] = 0;
++        if (!bdev) 
++              return;
++        newdev = kmalloc(sizeof(struct deventry), GFP_KERNEL);
++        if (!newdev) 
++              return;
++
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (bdev->bd_dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        kfree(newdev);
++                        return;
++                }
++                cur = cur->next;
++        }
++        newdev->dev = bdev->bd_dev;
++        newdev->next = devlist;
++        devlist = newdev;
++        spin_unlock(&devlock);
++        printk(KERN_WARNING "Turning device %s read-only\n",
++               bdev->bd_disk ? bdev->bd_disk->disk_name : "?");
 +}
 +
-+int dev_check_rdonly(dev_t dev)
++void dev_clear_rdonly(struct block_device *bdev) 
 +{
-+      int i;
-+
-+      for (i = 0; i < MAX_RDONLY_DEVS; i++)
-+              if (rdonly_devs[i] == dev)
-+                      return 1;
-+      return 0;
++        struct deventry *cur, *last = NULL;
++        if (!bdev) return;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (bdev->bd_dev == cur->dev) {
++                        if (last) 
++                                last->next = cur->next;
++                        else
++                                devlist = cur->next;
++                        spin_unlock(&devlock);
++                        kfree(cur);
++                        printk(KERN_WARNING "Removing read-only on %s\n",
++                             bdev->bd_disk ? bdev->bd_disk->disk_name : "?");
++                      return;
++                }
++                last = cur;
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
 +}
 +
 +EXPORT_SYMBOL(dev_set_rdonly);
 +EXPORT_SYMBOL(dev_clear_rdonly);
 +EXPORT_SYMBOL(dev_check_rdonly);
- /*
++
++/*
   * sysfs parts below
+  */
+ struct queue_sysfs_entry {
index d3fa230..b411c92 100644 (file)
@@ -1,51 +1,93 @@
-Index: linux-2.4.20-rh/drivers/block/blkpg.c
-===================================================================
---- linux-2.4.20-rh.orig/drivers/block/blkpg.c 2003-07-22 16:02:29.000000000 +0800
-+++ linux-2.4.20-rh/drivers/block/blkpg.c      2003-12-09 17:33:09.000000000 +0800
-@@ -297,3 +297,38 @@
+--- linux-2.4.20-rh.orig/drivers/block/ll_rw_blk.c     2005-01-19 10:59:48.000000000 -0800
++++ linux-2.4.20-rh/drivers/block/ll_rw_blk.c  2005-01-19 12:13:39.325347995 -0800
+@@ -645,6 +645,86 @@ void set_device_ro(kdev_t dev,int flag)
+       else ro_bits[major][minor >> 5] &= ~(1 << (minor & 31));
  }
  
- EXPORT_SYMBOL(blk_ioctl);
-+
-+#define NUM_DEV_NO_WRITE 16
-+static int dev_no_write[NUM_DEV_NO_WRITE];
 +
 +/*
-+ * Debug code for turning block devices "read-only" (will discard writes
-+ * silently).  This is for filesystem crash/recovery testing.
++ * Debug code for turning block devices read-only *silently* (will 
++ * discard writes silently).  This is only for filesystem crash/recovery
++ * testing.
 + */
-+void dev_set_rdonly(kdev_t dev, int no_write)
-+{
-+      if (dev) {
-+              printk(KERN_WARNING "Turning device %s read-only\n",
-+                     bdevname(dev));
-+              dev_no_write[no_write] = 0xdead0000 + dev;
-+      }
-+}
++struct deventry {
++        kdev_t dev;
++        struct deventry *next;
++};
++
++static struct deventry *devlist = NULL;
++static spinlock_t devlock = SPIN_LOCK_UNLOCKED; 
 +
 +int dev_check_rdonly(kdev_t dev) {
-+      int i;
-+
-+      for (i = 0; i < NUM_DEV_NO_WRITE; i++) {
-+              if ((dev_no_write[i] & 0xffff0000) == 0xdead0000 &&
-+                  dev == (dev_no_write[i] & 0xffff))
-+                      return 1;
-+      }
-+      return 0;
++        struct deventry *cur;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        return 1;
++                }
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
++        return 0;
 +}
 +
-+void dev_clear_rdonly(int no_write) {
-+      dev_no_write[no_write] = 0;
++void dev_set_rdonly(kdev_t dev)
++{
++        struct deventry *newdev, *cur;
++        newdev = kmalloc(sizeof(struct deventry), GFP_KERNEL);
++        if (!newdev) return;
++
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        kfree(newdev);
++                        return;
++                }
++                cur = cur->next;
++        }
++        newdev->dev = dev;
++        newdev->next = devlist;
++        devlist = newdev;
++        spin_unlock(&devlock);
++        printk(KERN_WARNING "Turning device %s read-only\n",
++               bdevname(dev));
++}
++
++void dev_clear_rdonly(kdev_t dev) {
++        struct deventry *cur, *last = NULL;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (dev == cur->dev) {
++                        if (last) 
++                                last->next = cur->next;
++                        else
++                                devlist = cur->next;
++                        spin_unlock(&devlock);
++                        kfree(cur);
++                        printk(KERN_WARNING "Removing read-only on %s\n",
++                               bdevname(dev));
++                        return;
++                }
++                last = cur;
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
 +}
 +
 +EXPORT_SYMBOL(dev_set_rdonly);
 +EXPORT_SYMBOL(dev_check_rdonly);
 +EXPORT_SYMBOL(dev_clear_rdonly);
-Index: linux-2.4.20-rh/drivers/block/ll_rw_blk.c
-===================================================================
---- linux-2.4.20-rh.orig/drivers/block/ll_rw_blk.c     2003-07-22 16:02:34.000000000 +0800
-+++ linux-2.4.20-rh/drivers/block/ll_rw_blk.c  2003-12-09 17:39:38.000000000 +0800
-@@ -1183,6 +1183,10 @@
++
++
+ inline void drive_stat_acct (kdev_t dev, int rw,
+                               unsigned long nr_sectors, int new_io)
+ {
+@@ -1183,6 +1263,10 @@ void generic_make_request (int rw, struc
                        buffer_IO_error(bh);
                        break;
                }
index 801431c..5ec75ce 100644 (file)
- drivers/block/blkpg.c  |   35 +++++++++++++++++++++++++++++++++++
- drivers/block/loop.c   |    3 +++
- drivers/ide/ide-disk.c |    5 +++++
- 3 files changed, 43 insertions(+)
-
-Index: linux-2.4.21-chaos/drivers/block/blkpg.c
-===================================================================
---- linux-2.4.21-chaos.orig/drivers/block/blkpg.c      2003-09-19 03:49:42.000000000 +0400
-+++ linux-2.4.21-chaos/drivers/block/blkpg.c   2003-12-12 16:17:49.000000000 +0300
-@@ -535,3 +535,38 @@
+--- linux-2.4.21-p4smp-75chaos/drivers/block/ll_rw_blk.c.orig  2004-10-28 14:41:07.000000000 -0700
++++ linux-2.4.21-p4smp-75chaos/drivers/block/ll_rw_blk.c       2005-01-19 12:24:53.946853178 -0800
+@@ -679,6 +679,86 @@ void set_device_ro(kdev_t dev,int flag)
+       else ro_bits[major][minor >> 5] &= ~(1 << (minor & 31));
+ }
  
- #endif /* CONFIG_IA64 */
-+
-+#define NUM_DEV_NO_WRITE 16
-+static int dev_no_write[NUM_DEV_NO_WRITE];
 +
 +/*
-+ * Debug code for turning block devices "read-only" (will discard writes
-+ * silently).  This is for filesystem crash/recovery testing.
++ * Debug code for turning block devices read-only *silently* (will 
++ * discard writes silently).  This is only for filesystem crash/recovery
++ * testing.
 + */
-+void dev_set_rdonly(kdev_t dev, int no_write)
-+{
-+      if (dev) {
-+              printk(KERN_WARNING "Turning device %s read-only\n",
-+                     bdevname(dev));
-+              dev_no_write[no_write] = 0xdead0000 + dev;
-+      }
-+}
++struct deventry {
++        kdev_t dev;
++        struct deventry *next;
++};
++
++static struct deventry *devlist = NULL;
++static spinlock_t devlock = SPIN_LOCK_UNLOCKED; 
 +
 +int dev_check_rdonly(kdev_t dev) {
-+      int i;
++        struct deventry *cur;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        return 1;
++                }
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
++        return 0;
++}
 +
-+      for (i = 0; i < NUM_DEV_NO_WRITE; i++) {
-+              if ((dev_no_write[i] & 0xffff0000) == 0xdead0000 &&
-+                  dev == (dev_no_write[i] & 0xffff))
-+                      return 1;
-+      }
-+      return 0;
++void dev_set_rdonly(kdev_t dev)
++{
++        struct deventry *newdev, *cur;
++        newdev = kmalloc(sizeof(struct deventry), GFP_KERNEL);
++        if (!newdev) return;
++
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (dev == cur->dev) {
++                        spin_unlock(&devlock);
++                        kfree(newdev);
++                        return;
++                }
++                cur = cur->next;
++        }
++        newdev->dev = dev;
++        newdev->next = devlist;
++        devlist = newdev;
++        spin_unlock(&devlock);
++        printk(KERN_WARNING "Turning device %s read-only\n",
++               bdevname(dev));
 +}
 +
-+void dev_clear_rdonly(int no_write) {
-+      dev_no_write[no_write] = 0;
++void dev_clear_rdonly(kdev_t dev) {
++        struct deventry *cur, *last = NULL;
++        spin_lock(&devlock);
++        cur = devlist;
++        while(cur) {
++                if (dev == cur->dev) {
++                        if (last) 
++                                last->next = cur->next;
++                        else
++                                devlist = cur->next;
++                        spin_unlock(&devlock);
++                        kfree(cur);
++                        printk(KERN_WARNING "Removing read-only on %s\n",
++                               bdevname(dev));
++                        return;
++                }
++                last = cur;
++                cur = cur->next;
++        }
++        spin_unlock(&devlock);
 +}
 +
 +EXPORT_SYMBOL(dev_set_rdonly);
 +EXPORT_SYMBOL(dev_check_rdonly);
 +EXPORT_SYMBOL(dev_clear_rdonly);
-Index: linux-2.4.21-chaos/drivers/block/loop.c
-===================================================================
---- linux-2.4.21-chaos.orig/drivers/block/loop.c       2003-09-19 03:49:42.000000000 +0400
-+++ linux-2.4.21-chaos/drivers/block/loop.c    2003-12-12 16:17:49.000000000 +0300
-@@ -491,6 +491,9 @@
-       spin_unlock_irq(&lo->lo_lock);
-       if (rw == WRITE) {
-+              if (dev_check_rdonly(rbh->b_rdev))
-+                      goto err;
 +
-               if (lo->lo_flags & LO_FLAGS_READ_ONLY)
-                       goto err;
-       } else if (rw == READA) {
-Index: linux-2.4.21-chaos/drivers/ide/ide-disk.c
-===================================================================
---- linux-2.4.21-chaos.orig/drivers/ide/ide-disk.c     2003-07-15 02:08:42.000000000 +0400
-+++ linux-2.4.21-chaos/drivers/ide/ide-disk.c  2003-12-12 16:17:49.000000000 +0300
-@@ -371,6 +371,11 @@
-       if (driver_blocked)
-               panic("Request while ide driver is blocked?");
-+      if (rq->cmd == WRITE && dev_check_rdonly(rq->rq_dev)) {
-+              ide_end_request(drive, 1);
-+              return ide_stopped;
-+      }
 +
-       if (IDE_CONTROL_REG)
-               hwif->OUTB(drive->ctl, IDE_CONTROL_REG);
+ inline void drive_stat_acct (kdev_t dev, int rw,
+                               unsigned long nr_sectors, int new_io)
+ {
+@@ -1257,6 +1337,10 @@ void generic_make_request (int rw, struc
+                       break;
+               }
++              if ((rw & WRITE)&&(dev_check_rdonly(bh->b_rdev))) {
++                bh->b_end_io(bh, 0);
++                break;
++              }
+       } while (q->make_request_fn(q, rw, bh));
+ }
  
diff --git a/lustre/kernel_patches/patches/dev_read_only_hp_2.4.20.patch b/lustre/kernel_patches/patches/dev_read_only_hp_2.4.20.patch
deleted file mode 100644 (file)
index 60081db..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
- drivers/block/blkpg.c  |   36 ++++++++++++++++++++++++++++++++++++
- drivers/block/loop.c   |    3 +++
- drivers/ide/ide-disk.c |    4 ++++
- 3 files changed, 43 insertions(+)
-
---- linux/drivers/block/blkpg.c~dev_read_only_hp_2.4.20        Mon May 19 07:07:52 2003
-+++ linux-mmonroe/drivers/block/blkpg.c        Mon May 19 07:37:22 2003
-@@ -310,6 +310,42 @@ int blk_ioctl(kdev_t dev, unsigned int c
- EXPORT_SYMBOL(blk_ioctl);
-+
-+#define NUM_DEV_NO_WRITE 16
-+static int dev_no_write[NUM_DEV_NO_WRITE];
-+/*
-+ * Debug code for turning block devices "read-only" (will discard writes
-+ * silently).  This is for filesystem crash/recovery testing.
-+ */
-+void dev_set_rdonly(kdev_t dev, int no_write)
-+{
-+      if (dev) {
-+              printk(KERN_WARNING "Turning device %s read-only\n",
-+                     bdevname(dev));
-+              dev_no_write[no_write] = 0xdead0000 + dev;
-+      }
-+}
-+
-+int dev_check_rdonly(kdev_t dev) {
-+      int i;
-+
-+      for (i = 0; i < NUM_DEV_NO_WRITE; i++) {
-+      if ((dev_no_write[i] & 0xffff0000) == 0xdead0000 &&
-+              dev == (dev_no_write[i] & 0xffff))
-+              return 1;
-+      }
-+      return 0;
-+}
-+
-+void dev_clear_rdonly(int no_write) {
-+      dev_no_write[no_write] = 0;
-+}
-+
-+EXPORT_SYMBOL(dev_set_rdonly);
-+EXPORT_SYMBOL(dev_check_rdonly);
-+EXPORT_SYMBOL(dev_clear_rdonly);
-+
-+
- /**
-  * get_last_sector()
-  *  
---- linux/drivers/block/loop.c~dev_read_only_hp_2.4.20 Thu Nov 28 15:53:12 2002
-+++ linux-mmonroe/drivers/block/loop.c Mon May 19 07:28:29 2003
-@@ -474,6 +474,9 @@ static int loop_make_request(request_que
-       spin_unlock_irq(&lo->lo_lock);
-       if (rw == WRITE) {
-+              if (dev_check_rdonly(rbh->b_rdev))
-+                      goto err;
-+
-               if (lo->lo_flags & LO_FLAGS_READ_ONLY)
-                       goto err;
-       } else if (rw == READA) {
---- linux/drivers/ide/ide-disk.c~dev_read_only_hp_2.4.20       Thu Nov 28 15:53:13 2002
-+++ linux-mmonroe/drivers/ide/ide-disk.c       Mon May 19 07:28:29 2003
-@@ -558,6 +558,10 @@ static ide_startstop_t lba_48_rw_disk (i
-  */
- static ide_startstop_t do_rw_disk (ide_drive_t *drive, struct request *rq, unsigned long block)
- {
-+      if (rq->cmd == WRITE && dev_check_rdonly(rq->rq_dev)) {
-+              ide_end_request(1, HWGROUP(drive));
-+              return ide_stopped;
-+      }
-       if (IDE_CONTROL_REG)
-               OUT_BYTE(drive->ctl,IDE_CONTROL_REG);
-
-_
diff --git a/lustre/kernel_patches/patches/dsp.patch b/lustre/kernel_patches/patches/dsp.patch
deleted file mode 100644 (file)
index d072af9..0000000
+++ /dev/null
@@ -1,142 +0,0 @@
- arch/i386/kernel/crash.c |   24 +++++++++++++++++-------
- arch/i386/kernel/nmi.c   |    2 +-
- include/asm-i386/apic.h  |    1 +
- include/linux/crash.h    |    2 +-
- kernel/bootimg.c         |   13 ++++++++++++-
- kernel/bootimg_pic.c     |    6 ++++--
- 6 files changed, 36 insertions(+), 12 deletions(-)
-
-Index: linux-2.4.20-rh/kernel/bootimg.c
-===================================================================
---- linux-2.4.20-rh.orig/kernel/bootimg.c      2003-10-29 23:56:02.000000000 +0800
-+++ linux-2.4.20-rh/kernel/bootimg.c   2003-10-29 23:56:17.000000000 +0800
-@@ -238,9 +238,20 @@
-       int error = -ENOMEM;
-       if (bootimg_checksum(__va(bootimg_dsc.page_dir),bootimg_dsc.pages) 
--              != bootimg_dsc.csum)
-+              != bootimg_dsc.csum) {
-               printk("Checksum of kernel image failed.  Rebooting via BIOS\n");
-+              /* Before calling machine_restart(), make sure it will not
-+               * simply call this function recursively.
-+               */
-+              bootimg_dsc.page_dir = NULL;
-+              machine_restart(NULL);
-+
-+              /* We should never get here, but just in case... */
-+              for (; ; )
-+                      __asm__ __volatile__ ("hlt");
-+      }
-+
-       code_page = get_identity_mapped_page();
-       if (!code_page) goto out3;
-       code = (relocate_and_jump_t) virt_to_phys((void *) code_page);
-Index: linux-2.4.20-rh/kernel/bootimg_pic.c
-===================================================================
---- linux-2.4.20-rh.orig/kernel/bootimg_pic.c  2003-10-29 23:56:02.000000000 +0800
-+++ linux-2.4.20-rh/kernel/bootimg_pic.c       2003-10-29 23:56:17.000000000 +0800
-@@ -69,7 +69,8 @@
-                       for (j = i+1; j < dsc.pages; j++) {
-                               table = dsc.page_dir+FROM_TABLE(j);
-                               if (((unsigned long) *table) == to) {
--                                      copy_and_swap(*table,dsc.scratch);
-+                                      copy_and_swap((unsigned long) (*table),
-+                                                    dsc.scratch);
-                                       break;
-                               }
-                               if ((*table)[PAGE_NR(j)] == to) {
-@@ -79,7 +80,8 @@
-                               }
-                               table = dsc.page_dir+TO_TABLE(j);
-                               if (((unsigned long) *table) == to) {
--                                      copy_and_swap(*table,dsc.scratch);
-+                                      copy_and_swap((unsigned long) (*table),
-+                                                    dsc.scratch);
-                                       break;
-                               }
-                       }
-Index: linux-2.4.20-rh/include/asm-i386/apic.h
-===================================================================
---- linux-2.4.20-rh.orig/include/asm-i386/apic.h       2003-10-29 23:58:49.000000000 +0800
-+++ linux-2.4.20-rh/include/asm-i386/apic.h    2003-10-29 23:59:40.000000000 +0800
-@@ -86,6 +86,9 @@
- extern void apic_pm_unregister(struct pm_dev*);
- extern int check_nmi_watchdog (void);
-+extern void disable_apic_nmi_watchdog(void);
-+
-+
- extern unsigned int nmi_watchdog;
- #define NMI_NONE      0
-Index: linux-2.4.20-rh/include/linux/crash.h
-===================================================================
---- linux-2.4.20-rh.orig/include/linux/crash.h 2003-10-29 23:56:02.000000000 +0800
-+++ linux-2.4.20-rh/include/linux/crash.h      2003-10-29 23:56:17.000000000 +0800
-@@ -71,7 +71,7 @@
- #define CRASH_ZALLOC_PAGES 16*5*2     /* 2 to handle crash in crash */
- #define CRASH_LOW_WATER_PAGES 100
--#define CRASH_CPU_TIMEOUT 5000        /* 5 sec wait for other cpus to stop */
-+#define CRASH_CPU_TIMEOUT 15000       /* 15 sec wait for other cpus to stop */
- #define CRASH_MARK_RESERVED(addr) (set_bit(PG_reserved,&mem_map[MAP_NR(addr)].flags))
- #define CRASH_CLEAR_RESERVED(addr) (clear_bit(PG_reserved,&mem_map[MAP_NR(addr)].flags))
-Index: linux-2.4.20-rh/arch/i386/kernel/crash.c
-===================================================================
---- linux-2.4.20-rh.orig/arch/i386/kernel/crash.c      2003-10-29 23:56:02.000000000 +0800
-+++ linux-2.4.20-rh/arch/i386/kernel/crash.c   2003-10-29 23:56:17.000000000 +0800
-@@ -9,6 +9,8 @@
- #include <linux/crash.h>
- #include <linux/reboot.h>
- #include <linux/bootimg.h>
-+#include <asm/fixmap.h>
-+#include <asm/apic.h>
- inline void crash_save_regs(void) {
-       static unsigned long regs[8];
-@@ -30,15 +32,23 @@
-  */
- void crash_save_current_state(struct task_struct *tp)
- {
-+      if (tp != NULL) {
-+              /*
-+               *  Here we save ebp instead of esp just in case the compiler
-+               *  decides to put an extra push in before we execute this
-+               *  instruction (thus invalidating our frame pointer).
-+               */
-+              asm volatile("movl %%ebp,%0":"=m" (*(u_long *)&tp->thread.esp));
-+              tp->thread.eip = (u_long)crash_save_current_state;
-+              panic_ksp[smp_processor_id()] = tp->thread.esp;
-+              mb();
-+      }
-+
-       /*
--       *  Here we save ebp instead of esp just in case the compiler
--       *  decides to put an extra push in before we execute this
--       *  instruction (thus invalidating our frame pointer).
-+       * Just to be safe, disable the NMI watchdog on the calling CPU so it
-+       * doesn't get in the way while we are trying to save a dump.
-        */
--      asm volatile("movl %%ebp,%0":"=m" (*(u_long *)&tp->thread.esp));
--      tp->thread.eip = (u_long)crash_save_current_state;
--      panic_ksp[smp_processor_id()] = tp->thread.esp;
--      mb();
-+      disable_apic_nmi_watchdog();
-       save_core();
-Index: linux-2.4.20-rh/arch/i386/kernel/nmi.c
-===================================================================
---- linux-2.4.20-rh.orig/arch/i386/kernel/nmi.c        2003-10-29 23:56:02.000000000 +0800
-+++ linux-2.4.20-rh/arch/i386/kernel/nmi.c     2003-10-29 23:56:17.000000000 +0800
-@@ -138,7 +138,7 @@
- struct pm_dev *nmi_pmdev;
--static void disable_apic_nmi_watchdog(void)
-+void disable_apic_nmi_watchdog(void)
- {
-       switch (boot_cpu_data.x86_vendor) {
-       case X86_VENDOR_AMD:
diff --git a/lustre/kernel_patches/patches/dynamic-locks-2.4.20-rh.patch b/lustre/kernel_patches/patches/dynamic-locks-2.4.20-rh.patch
deleted file mode 100644 (file)
index 59f0a3e..0000000
+++ /dev/null
@@ -1,217 +0,0 @@
- include/linux/dynlocks.h |   33 ++++++++++
- lib/Makefile             |    4 -
- lib/dynlocks.c           |  152 +++++++++++++++++++++++++++++++++++++++++++++++
- 3 files changed, 187 insertions(+), 2 deletions(-)
-
-Index: linux-2.4.20-rh/include/linux/dynlocks.h
-===================================================================
---- linux-2.4.20-rh.orig/include/linux/dynlocks.h      2003-09-04 18:25:49.000000000 +0800
-+++ linux-2.4.20-rh/include/linux/dynlocks.h   2003-09-04 18:25:49.000000000 +0800
-@@ -0,0 +1,33 @@
-+#ifndef _LINUX_DYNLOCKS_H
-+#define _LINUX_DYNLOCKS_H
-+
-+#include <linux/list.h>
-+#include <linux/wait.h>
-+
-+struct dynlock_member {
-+      struct list_head        dl_list;
-+      unsigned long           dl_value;       /* lock value */
-+      int                     dl_refcount;    /* number of users */
-+      int                     dl_readers;
-+      int                     dl_writers;
-+      int                     dl_pid;         /* holder of the lock */
-+      wait_queue_head_t       dl_wait;
-+};
-+
-+/*
-+ * lock's namespace:
-+ *   - list of locks
-+ *   - lock to protect this list
-+ */
-+struct dynlock {
-+      struct list_head dl_list;
-+      spinlock_t dl_list_lock;
-+};
-+
-+void dynlock_init(struct dynlock *dl);
-+void *dynlock_lock(struct dynlock *dl, unsigned long value, int rw, int gfp);
-+void dynlock_unlock(struct dynlock *dl, void *lock);
-+
-+
-+#endif
-+
-Index: linux-2.4.20-rh/lib/dynlocks.c
-===================================================================
---- linux-2.4.20-rh.orig/lib/dynlocks.c        2003-09-04 18:25:49.000000000 +0800
-+++ linux-2.4.20-rh/lib/dynlocks.c     2003-09-04 18:25:49.000000000 +0800
-@@ -0,0 +1,152 @@
-+/*
-+ * Dynamic Locks
-+ *
-+ * struct dynlock is lockspace
-+ * one may request lock (exclusive or shared) for some value
-+ * in that lockspace
-+ *
-+ */
-+
-+#include <linux/dynlocks.h>
-+#include <linux/module.h>
-+#include <linux/slab.h>
-+#include <linux/sched.h>
-+
-+/*
-+ * dynlock_init
-+ *
-+ * initialize lockspace
-+ *
-+ */
-+void dynlock_init(struct dynlock *dl)
-+{
-+      spin_lock_init(&dl->dl_list_lock);
-+      INIT_LIST_HEAD(&dl->dl_list);
-+}
-+
-+/*
-+ * dynlock_lock
-+ *
-+ * acquires lock (exclusive or shared) in specified lockspace
-+ * each lock in lockspace is allocated separately, so user have
-+ * to specify GFP flags.
-+ * routine returns pointer to lock. this pointer is intended to
-+ * be passed to dynlock_unlock
-+ *
-+ */
-+void *dynlock_lock(struct dynlock *dl, unsigned long value, int rw, int gfp)
-+{
-+      struct dynlock_member *nhl = NULL; 
-+      struct dynlock_member *hl; 
-+      struct list_head *cur;
-+
-+repeat:
-+      /* find requested lock in lockspace */
-+      spin_lock(&dl->dl_list_lock);
-+      list_for_each(cur, &dl->dl_list) {
-+              hl = list_entry(cur, struct dynlock_member, dl_list);
-+              if (hl->dl_value == value) {
-+                      /* lock is found */
-+                      if (nhl) {
-+                              /* someone else just allocated
-+                               * lock we didn't find and just created
-+                               * so, we drop our lock
-+                               */
-+                              kfree(nhl);
-+                              nhl = NULL;
-+                      }
-+                      hl->dl_refcount++;
-+                      goto found;
-+              }
-+      }
-+      /* lock not found */
-+      if (nhl) {
-+              /* we already have allocated lock. use it */
-+              hl = nhl;
-+              nhl = NULL;
-+              list_add(&hl->dl_list, &dl->dl_list);
-+              goto found;
-+      }
-+      spin_unlock(&dl->dl_list_lock);
-+      
-+      /* lock not found and we haven't allocated lock yet. allocate it */
-+      nhl = kmalloc(sizeof(struct dynlock_member), gfp);
-+      if (nhl == NULL)
-+              return NULL;
-+      nhl->dl_refcount = 1;
-+      nhl->dl_value = value;
-+      nhl->dl_readers = 0;
-+      nhl->dl_writers = 0;
-+      init_waitqueue_head(&nhl->dl_wait);
-+
-+      /* while lock is being allocated, someone else may allocate it
-+       * and put onto to list. check this situation
-+       */
-+      goto repeat;
-+
-+found:
-+      if (rw) {
-+              /* exclusive lock: user don't want to share lock at all
-+               * NOTE: one process may take the same lock several times
-+               * this functionaly is useful for rename operations */
-+              while ((hl->dl_writers && hl->dl_pid != current->pid) ||
-+                              hl->dl_readers) {
-+                      spin_unlock(&dl->dl_list_lock);
-+                      wait_event(hl->dl_wait,
-+                              hl->dl_writers == 0 && hl->dl_readers == 0);
-+                      spin_lock(&dl->dl_list_lock);
-+              }
-+              hl->dl_writers++;
-+      } else {
-+              /* shared lock: user do not want to share lock with writer */
-+              while (hl->dl_writers) {
-+                      spin_unlock(&dl->dl_list_lock);
-+                      wait_event(hl->dl_wait, hl->dl_writers == 0);
-+                      spin_lock(&dl->dl_list_lock);
-+              }
-+              hl->dl_readers++;
-+      }
-+      hl->dl_pid = current->pid;
-+      spin_unlock(&dl->dl_list_lock);
-+
-+      return hl;
-+}
-+
-+
-+/*
-+ * dynlock_unlock
-+ *
-+ * user have to specify lockspace (dl) and pointer to lock structure
-+ * returned by dynlock_lock()
-+ *
-+ */
-+void dynlock_unlock(struct dynlock *dl, void *lock)
-+{
-+      struct dynlock_member *hl = lock;
-+      int wakeup = 0;
-+      
-+      spin_lock(&dl->dl_list_lock);
-+      if (hl->dl_writers) {
-+              hl->dl_writers--;
-+              if (hl->dl_writers == 0)
-+                      wakeup = 1;
-+      } else {
-+              hl->dl_readers--;
-+              if (hl->dl_readers == 0)
-+                      wakeup = 1;
-+      }
-+      if (wakeup) {
-+              hl->dl_pid = 0;
-+              wake_up(&hl->dl_wait);
-+      }
-+      if (--(hl->dl_refcount) == 0) 
-+              list_del(&hl->dl_list);
-+      spin_unlock(&dl->dl_list_lock);
-+      if (hl->dl_refcount == 0)
-+              kfree(hl);
-+}
-+
-+EXPORT_SYMBOL(dynlock_init);
-+EXPORT_SYMBOL(dynlock_lock);
-+EXPORT_SYMBOL(dynlock_unlock);
-+
-Index: linux-2.4.20-rh/lib/Makefile
-===================================================================
---- linux-2.4.20-rh.orig/lib/Makefile  2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-rh/lib/Makefile       2003-09-04 18:27:26.000000000 +0800
-@@ -8,10 +8,10 @@
- L_TARGET := lib.a
--export-objs := cmdline.o dec_and_lock.o rwsem-spinlock.o rwsem.o rbtree.o
-+export-objs := cmdline.o dec_and_lock.o rwsem-spinlock.o rwsem.o rbtree.o dynlocks.o
- obj-y := errno.o ctype.o string.o vsprintf.o brlock.o cmdline.o \
--       bust_spinlocks.o rbtree.o dump_stack.o
-+       bust_spinlocks.o rbtree.o dump_stack.o dynlocks.o
- obj-$(CONFIG_RWSEM_GENERIC_SPINLOCK) += rwsem-spinlock.o
- obj-$(CONFIG_RWSEM_XCHGADD_ALGORITHM) += rwsem.o
diff --git a/lustre/kernel_patches/patches/exports.patch b/lustre/kernel_patches/patches/exports.patch
deleted file mode 100644 (file)
index 33e0b6c..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-
-
-
- fs/ext3/Makefile   |    2 ++
- fs/ext3/super.c    |    2 +-
- include/linux/fs.h |    1 +
- kernel/ksyms.c     |    5 +++++
- 4 files changed, 9 insertions(+), 1 deletion(-)
-
---- linux-2.4.18-18/fs/ext3/Makefile~exports   Sat Apr  5 02:51:27 2003
-+++ linux-2.4.18-18-braam/fs/ext3/Makefile     Sat Apr  5 02:54:45 2003
-@@ -9,6 +9,8 @@
- O_TARGET := ext3.o
-+export-objs :=        super.o inode.o
-+
- obj-y    := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o \
-               ioctl.o namei.o super.o symlink.o
- obj-m    := $(O_TARGET)
---- linux-2.4.18-18/fs/ext3/super.c~exports    Sat Apr  5 02:51:27 2003
-+++ linux-2.4.18-18-braam/fs/ext3/super.c      Sat Apr  5 02:54:28 2003
-@@ -1746,7 +1746,7 @@ static void __exit exit_ext3_fs(void)
-       unregister_filesystem(&ext3_fs_type);
- }
--EXPORT_NO_SYMBOLS;
-+EXPORT_SYMBOL(ext3_bread);
- MODULE_AUTHOR("Remy Card, Stephen Tweedie, Andrew Morton, Andreas Dilger, Theodore Ts'o and others");
- MODULE_DESCRIPTION("Second Extended Filesystem with journaling extensions");
---- linux-2.4.18-18/include/linux/fs.h~exports Sat Apr  5 02:51:27 2003
-+++ linux-2.4.18-18-braam/include/linux/fs.h   Sat Apr  5 02:54:29 2003
-@@ -1046,6 +1046,7 @@ extern int unregister_filesystem(struct 
- extern struct vfsmount *kern_mount(struct file_system_type *);
- extern int may_umount(struct vfsmount *);
- extern long do_mount(char *, char *, char *, unsigned long, void *);
-+struct vfsmount *do_kern_mount(const char *type, int flags, char *name, void *data);
- extern void umount_tree(struct vfsmount *);
- #define kern_umount mntput
---- linux-2.4.18-18/kernel/ksyms.c~exports     Sat Apr  5 02:51:27 2003
-+++ linux-2.4.18-18-braam/kernel/ksyms.c       Sat Apr  5 02:54:29 2003
-@@ -306,6 +306,11 @@ EXPORT_SYMBOL_GPL(buffermem_pages);
- EXPORT_SYMBOL_GPL(nr_free_pages);
- EXPORT_SYMBOL_GPL(page_cache_size);
-+/* lustre */
-+EXPORT_SYMBOL(panic_notifier_list);
-+EXPORT_SYMBOL(pagecache_lock_cacheline);
-+EXPORT_SYMBOL(do_kern_mount);
-+
- /* for stackable file systems (lofs, wrapfs, cryptfs, etc.) */
- EXPORT_SYMBOL(default_llseek);
- EXPORT_SYMBOL(dentry_open);
-
-_
diff --git a/lustre/kernel_patches/patches/ext3-delete_thread-suse.patch b/lustre/kernel_patches/patches/ext3-delete_thread-suse.patch
deleted file mode 100644 (file)
index f3d7f3c..0000000
+++ /dev/null
@@ -1,496 +0,0 @@
- fs/ext3/file.c             |    4 
- fs/ext3/inode.c            |  116 ++++++++++++++++++++++
- fs/ext3/super.c            |  230 +++++++++++++++++++++++++++++++++++++++++++++
- include/linux/ext3_fs.h    |    5 
- include/linux/ext3_fs_sb.h |   10 +
- 5 files changed, 365 insertions(+)
-
-Index: linux-2.4.21-suse/fs/ext3/super.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/super.c     2004-01-12 19:49:25.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/super.c  2004-01-13 17:39:59.000000000 +0300
-@@ -400,6 +400,221 @@
-       }
- }
-+#ifdef EXT3_DELETE_THREAD
-+/*
-+ * Delete inodes in a loop until there are no more to be deleted.
-+ * Normally, we run in the background doing the deletes and sleeping again,
-+ * and clients just add new inodes to be deleted onto the end of the list.
-+ * If someone is concerned about free space (e.g. block allocation or similar)
-+ * then they can sleep on s_delete_waiter_queue and be woken up when space
-+ * has been freed.
-+ */
-+int ext3_delete_thread(void *data)
-+{
-+      struct super_block *sb = data;
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      struct task_struct *tsk = current;
-+
-+      /* Almost like daemonize, but not quite */
-+      exit_mm(current);
-+      tsk->session = 1;
-+      tsk->pgrp = 1;
-+      tsk->tty = NULL;
-+      exit_files(current);
-+      reparent_to_init();
-+
-+      sprintf(tsk->comm, "kdelext3-%s", kdevname(sb->s_dev));
-+      sigfillset(&tsk->blocked);
-+
-+      /*tsk->flags |= PF_KERNTHREAD;*/
-+
-+      INIT_LIST_HEAD(&sbi->s_delete_list);
-+      wake_up(&sbi->s_delete_waiter_queue);
-+      ext3_debug("delete thread on %s started\n", kdevname(sb->s_dev));
-+
-+      /* main loop */
-+      for (;;) {
-+              wait_event_interruptible(sbi->s_delete_thread_queue,
-+                                       !list_empty(&sbi->s_delete_list) ||
-+                                       !test_opt(sb, ASYNCDEL));
-+              ext3_debug("%s woken up: %lu inodes, %lu blocks\n",
-+                         tsk->comm,sbi->s_delete_inodes,sbi->s_delete_blocks);
-+
-+              spin_lock(&sbi->s_delete_lock);
-+              if (list_empty(&sbi->s_delete_list)) {
-+                      clear_opt(sbi->s_mount_opt, ASYNCDEL);
-+                      memset(&sbi->s_delete_list, 0,
-+                             sizeof(sbi->s_delete_list));
-+                      spin_unlock(&sbi->s_delete_lock);
-+                      ext3_debug("delete thread on %s exiting\n",
-+                                 kdevname(sb->s_dev));
-+                      wake_up(&sbi->s_delete_waiter_queue);
-+                      break;
-+              }
-+
-+              while (!list_empty(&sbi->s_delete_list)) {
-+                      struct inode *inode=list_entry(sbi->s_delete_list.next,
-+                                                     struct inode, i_dentry);
-+                      unsigned long blocks = inode->i_blocks >>
-+                                                      (inode->i_blkbits - 9);
-+
-+                      list_del_init(&inode->i_dentry);
-+                      spin_unlock(&sbi->s_delete_lock);
-+                      ext3_debug("%s delete ino %lu blk %lu\n",
-+                                 tsk->comm, inode->i_ino, blocks);
-+
-+                      iput(inode);
-+
-+                      spin_lock(&sbi->s_delete_lock);
-+                      sbi->s_delete_blocks -= blocks;
-+                      sbi->s_delete_inodes--;
-+              }
-+              if (sbi->s_delete_blocks != 0 || sbi->s_delete_inodes != 0) {
-+                      ext3_warning(sb, __FUNCTION__,
-+                                   "%lu blocks, %lu inodes on list?\n",
-+                                   sbi->s_delete_blocks,sbi->s_delete_inodes);
-+                      sbi->s_delete_blocks = 0;
-+                      sbi->s_delete_inodes = 0;
-+              }
-+              spin_unlock(&sbi->s_delete_lock);
-+              wake_up(&sbi->s_delete_waiter_queue);
-+      }
-+
-+      return 0;
-+}
-+
-+static void ext3_start_delete_thread(struct super_block *sb)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      int rc;
-+
-+      spin_lock_init(&sbi->s_delete_lock);
-+      init_waitqueue_head(&sbi->s_delete_thread_queue);
-+      init_waitqueue_head(&sbi->s_delete_waiter_queue);
-+
-+      if (!test_opt(sb, ASYNCDEL))
-+              return;
-+
-+      rc = kernel_thread(ext3_delete_thread, sb, CLONE_VM | CLONE_FILES);
-+      if (rc < 0)
-+              printk(KERN_ERR "EXT3-fs: cannot start delete thread: rc %d\n",
-+                     rc);
-+      else
-+              wait_event(sbi->s_delete_waiter_queue, sbi->s_delete_list.next);
-+}
-+
-+static void ext3_stop_delete_thread(struct ext3_sb_info *sbi)
-+{
-+      if (sbi->s_delete_list.next == 0)       /* thread never started */
-+              return;
-+
-+      clear_opt(sbi->s_mount_opt, ASYNCDEL);
-+      wake_up(&sbi->s_delete_thread_queue);
-+      wait_event(sbi->s_delete_waiter_queue,
-+                      sbi->s_delete_list.next == 0 && sbi->s_delete_inodes == 0);
-+}
-+
-+/* Instead of playing games with the inode flags, destruction, etc we just
-+ * create a new inode locally and put it on a list for the truncate thread.
-+ * We need large parts of the inode struct in order to complete the
-+ * truncate and unlink, so we may as well just have a real inode to do it.
-+ *
-+ * If we have any problem deferring the delete, just delete it right away.
-+ * If we defer it, we also mark how many blocks it would free, so that we
-+ * can keep the statfs data correct, and we know if we should sleep on the
-+ * delete thread when we run out of space.
-+ */
-+static void ext3_delete_inode_thread(struct inode *old_inode)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(old_inode->i_sb);
-+      struct ext3_inode_info *nei, *oei = EXT3_I(old_inode);
-+      struct inode *new_inode;
-+      unsigned long blocks = old_inode->i_blocks >> (old_inode->i_blkbits-9);
-+
-+      if (is_bad_inode(old_inode)) {
-+              clear_inode(old_inode);
-+              return;
-+      }
-+
-+      if (!test_opt(old_inode->i_sb, ASYNCDEL) || !sbi->s_delete_list.next)
-+              goto out_delete;
-+
-+      /* We may want to delete the inode immediately and not defer it */
-+      if (IS_SYNC(old_inode) || blocks <= EXT3_NDIR_BLOCKS)
-+              goto out_delete;
-+
-+      /* We can't use the delete thread as-is during real orphan recovery,
-+       * as we add to the orphan list here, causing ext3_orphan_cleanup()
-+       * to loop endlessly.  It would be nice to do so, but needs work.
-+       */
-+      if (oei->i_state & EXT3_STATE_DELETE ||
-+          sbi->s_mount_state & EXT3_ORPHAN_FS) {
-+              ext3_debug("doing deferred inode %lu delete (%lu blocks)\n",
-+                         old_inode->i_ino, blocks);
-+              goto out_delete;
-+      }
-+
-+      /* We can iget this inode again here, because our caller has unhashed
-+       * old_inode, so new_inode will be in a different inode struct.
-+       *
-+       * We need to ensure that the i_orphan pointers in the other inodes
-+       * point at the new inode copy instead of the old one so the orphan
-+       * list doesn't get corrupted when the old orphan inode is freed.
-+       */
-+      down(&sbi->s_orphan_lock);
-+
-+      sbi->s_mount_state |= EXT3_ORPHAN_FS;
-+      new_inode = iget(old_inode->i_sb, old_inode->i_ino);
-+      sbi->s_mount_state &= ~EXT3_ORPHAN_FS;
-+      if (is_bad_inode(new_inode)) {
-+              printk(KERN_WARNING "read bad inode %lu\n", old_inode->i_ino);
-+              iput(new_inode);
-+              new_inode = NULL;
-+      }
-+      if (!new_inode) {
-+              up(&sbi->s_orphan_lock);
-+              ext3_debug("delete inode %lu directly (bad read)\n",
-+                         old_inode->i_ino);
-+              goto out_delete;
-+      }
-+      J_ASSERT(new_inode != old_inode);
-+
-+      J_ASSERT(!list_empty(&oei->i_orphan));
-+
-+      nei = EXT3_I(new_inode);
-+      /* Ugh.  We need to insert new_inode into the same spot on the list
-+       * as old_inode was, to ensure the in-memory orphan list is still
-+       * in the same order as the on-disk orphan list (badness otherwise).
-+       */
-+      nei->i_orphan = oei->i_orphan;
-+      nei->i_orphan.next->prev = &nei->i_orphan;
-+      nei->i_orphan.prev->next = &nei->i_orphan;
-+      nei->i_state |= EXT3_STATE_DELETE;
-+      up(&sbi->s_orphan_lock);
-+
-+      clear_inode(old_inode);
-+
-+      spin_lock(&sbi->s_delete_lock);
-+      J_ASSERT(list_empty(&new_inode->i_dentry));
-+      list_add_tail(&new_inode->i_dentry, &sbi->s_delete_list);
-+      sbi->s_delete_blocks += blocks;
-+      sbi->s_delete_inodes++;
-+      spin_unlock(&sbi->s_delete_lock);
-+
-+      ext3_debug("delete inode %lu (%lu blocks) by thread\n",
-+                 new_inode->i_ino, blocks);
-+
-+      wake_up(&sbi->s_delete_thread_queue);
-+      return;
-+
-+out_delete:
-+      ext3_delete_inode(old_inode);
-+}
-+#else
-+#define ext3_start_delete_thread(sbi) do {} while(0)
-+#define ext3_stop_delete_thread(sbi) do {} while(0)
-+#endif /* EXT3_DELETE_THREAD */
-+
- void ext3_put_super (struct super_block * sb)
- {
-       struct ext3_sb_info *sbi = EXT3_SB(sb);
-@@ -407,6 +622,7 @@
-       kdev_t j_dev = sbi->s_journal->j_dev;
-       int i;
-+      J_ASSERT(sbi->s_delete_inodes == 0);
-       ext3_xattr_put_super(sb);
-       journal_destroy(sbi->s_journal);
-       if (!(sb->s_flags & MS_RDONLY)) {
-@@ -455,7 +671,11 @@
-       write_inode:    ext3_write_inode,       /* BKL not held.  Don't need */
-       dirty_inode:    ext3_dirty_inode,       /* BKL not held.  We take it */
-       put_inode:      ext3_put_inode,         /* BKL not held.  Don't need */
-+#ifdef EXT3_DELETE_THREAD
-+      delete_inode:   ext3_delete_inode_thread,/* BKL not held. We take it */
-+#else
-       delete_inode:   ext3_delete_inode,      /* BKL not held.  We take it */
-+#endif
-       put_super:      ext3_put_super,         /* BKL held */
-       write_super:    ext3_write_super,       /* BKL held */
-       sync_fs:        ext3_sync_fs,
-@@ -524,6 +744,13 @@
-                       clear_opt (*mount_options, XATTR_USER);
-               else
- #endif
-+#ifdef EXT3_DELETE_THREAD
-+              if (!strcmp(this_char, "asyncdel"))
-+                      set_opt(*mount_options, ASYNCDEL);
-+              else if (!strcmp(this_char, "noasyncdel"))
-+                      clear_opt(*mount_options, ASYNCDEL);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -1223,6 +1450,7 @@
-       }
-       ext3_setup_super (sb, es, sb->s_flags & MS_RDONLY);
-+      ext3_start_delete_thread(sb);
-       /*
-        * akpm: core read_super() calls in here with the superblock locked.
-        * That deadlocks, because orphan cleanup needs to lock the superblock
-@@ -1614,7 +1842,12 @@
- static int ext3_sync_fs(struct super_block *sb)
- {
-       tid_t target;
--      
-+
-+      if (atomic_read(&sb->s_active) == 0) {
-+              /* fs is being umounted: time to stop delete thread */
-+              ext3_stop_delete_thread(EXT3_SB(sb));
-+      }
-+
-       sb->s_dirt = 0;
-       target = log_start_commit(EXT3_SB(sb)->s_journal, NULL);
-       log_wait_commit(EXT3_SB(sb)->s_journal, target);
-@@ -1678,6 +1911,9 @@
-       if (!parse_options(data, &tmp, sbi, &tmp, 1))
-               return -EINVAL;
-+      if (!test_opt(sb, ASYNCDEL) || (*flags & MS_RDONLY))
-+              ext3_stop_delete_thread(sbi);
-+
-       if (sbi->s_mount_opt & EXT3_MOUNT_ABORT)
-               ext3_abort(sb, __FUNCTION__, "Abort forced by user");
-Index: linux-2.4.21-suse/fs/ext3/inode.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/inode.c     2004-01-13 17:38:09.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/inode.c  2004-01-13 17:38:10.000000000 +0300
-@@ -2552,6 +2552,118 @@
-       return err;
- }
-+#ifdef EXT3_DELETE_THREAD
-+/* Move blocks from to-be-truncated inode over to a new inode, and delete
-+ * that one from the delete thread instead.  This avoids a lot of latency
-+ * when truncating large files.
-+ *
-+ * If we have any problem deferring the truncate, just truncate it right away.
-+ * If we defer it, we also mark how many blocks it would free, so that we
-+ * can keep the statfs data correct, and we know if we should sleep on the
-+ * delete thread when we run out of space.
-+ */
-+void ext3_truncate_thread(struct inode *old_inode)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(old_inode->i_sb);
-+      struct ext3_inode_info *nei, *oei = EXT3_I(old_inode);
-+      struct inode *new_inode;
-+      handle_t *handle;
-+      unsigned long blocks = old_inode->i_blocks >> (old_inode->i_blkbits-9);
-+
-+      if (!test_opt(old_inode->i_sb, ASYNCDEL) || !sbi->s_delete_list.next)
-+              goto out_truncate;
-+
-+      /* XXX This is a temporary limitation for code simplicity.
-+       *     We could truncate to arbitrary sizes at some later time.
-+       */
-+      if (old_inode->i_size != 0)
-+              goto out_truncate;
-+
-+      /* We may want to truncate the inode immediately and not defer it */
-+      if (IS_SYNC(old_inode) || blocks <= EXT3_NDIR_BLOCKS ||
-+          old_inode->i_size > oei->i_disksize)
-+              goto out_truncate;
-+
-+      /* We can't use the delete thread as-is during real orphan recovery,
-+       * as we add to the orphan list here, causing ext3_orphan_cleanup()
-+       * to loop endlessly.  It would be nice to do so, but needs work.
-+       */
-+      if (oei->i_state & EXT3_STATE_DELETE ||
-+          sbi->s_mount_state & EXT3_ORPHAN_FS) {
-+              ext3_debug("doing deferred inode %lu delete (%lu blocks)\n",
-+                         old_inode->i_ino, blocks);
-+              goto out_truncate;
-+      }
-+
-+      ext3_discard_prealloc(old_inode);
-+
-+      /* old_inode   = 1
-+       * new_inode   = sb + GDT + ibitmap
-+       * orphan list = 1 inode/superblock for add, 2 inodes for del
-+       * quota files = 2 * EXT3_SINGLEDATA_TRANS_BLOCKS
-+       */
-+      handle = ext3_journal_start(old_inode, 7);
-+      if (IS_ERR(handle))
-+              goto out_truncate;
-+
-+      new_inode = ext3_new_inode(handle, old_inode, old_inode->i_mode);
-+      if (IS_ERR(new_inode)) {
-+              ext3_debug("truncate inode %lu directly (no new inodes)\n",
-+                         old_inode->i_ino);
-+              goto out_journal;
-+      }
-+
-+      nei = EXT3_I(new_inode);
-+
-+      down_write(&oei->truncate_sem);
-+      new_inode->i_size = old_inode->i_size;
-+      new_inode->i_blocks = old_inode->i_blocks;
-+      new_inode->i_uid = old_inode->i_uid;
-+      new_inode->i_gid = old_inode->i_gid;
-+      new_inode->i_nlink = 0;
-+
-+      /* FIXME when we do arbitrary truncates */
-+      old_inode->i_blocks = oei->i_file_acl ? old_inode->i_blksize / 512 : 0;
-+      old_inode->i_mtime = old_inode->i_ctime = CURRENT_TIME;
-+
-+      memcpy(nei->i_data, oei->i_data, sizeof(nei->i_data));
-+      memset(oei->i_data, 0, sizeof(oei->i_data));
-+
-+      nei->i_disksize = oei->i_disksize;
-+      nei->i_state |= EXT3_STATE_DELETE;
-+      up_write(&oei->truncate_sem);
-+
-+      if (ext3_orphan_add(handle, new_inode) < 0)
-+              goto out_journal;
-+
-+      if (ext3_orphan_del(handle, old_inode) < 0) {
-+              ext3_orphan_del(handle, new_inode);
-+              iput(new_inode);
-+              goto out_journal;
-+      }
-+
-+      ext3_journal_stop(handle, old_inode);
-+
-+      spin_lock(&sbi->s_delete_lock);
-+      J_ASSERT(list_empty(&new_inode->i_dentry));
-+      list_add_tail(&new_inode->i_dentry, &sbi->s_delete_list);
-+      sbi->s_delete_blocks += blocks;
-+      sbi->s_delete_inodes++;
-+      spin_unlock(&sbi->s_delete_lock);
-+
-+      ext3_debug("delete inode %lu (%lu blocks) by thread\n",
-+                 new_inode->i_ino, blocks);
-+
-+      wake_up(&sbi->s_delete_thread_queue);
-+      return;
-+
-+out_journal:
-+      ext3_journal_stop(handle, old_inode);
-+out_truncate:
-+      ext3_truncate(old_inode);
-+}
-+#endif /* EXT3_DELETE_THREAD */
-+
- /* 
-  * On success, We end up with an outstanding reference count against
-  * iloc->bh.  This _must_ be cleaned up later. 
-Index: linux-2.4.21-suse/fs/ext3/file.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/file.c      2004-01-12 19:49:25.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/file.c   2004-01-13 17:38:10.000000000 +0300
-@@ -125,7 +125,11 @@
- };
- struct inode_operations ext3_file_inode_operations = {
-+#ifdef EXT3_DELETE_THREAD
-+      truncate:       ext3_truncate_thread,   /* BKL held */
-+#else
-       truncate:       ext3_truncate,          /* BKL held */
-+#endif
-       setattr:        ext3_setattr,           /* BKL held */
-       setxattr:       ext3_setxattr,          /* BKL held */
-       getxattr:       ext3_getxattr,          /* BKL held */
-Index: linux-2.4.21-suse/include/linux/ext3_fs.h
-===================================================================
---- linux-2.4.21-suse.orig/include/linux/ext3_fs.h     2004-01-13 17:38:09.000000000 +0300
-+++ linux-2.4.21-suse/include/linux/ext3_fs.h  2004-01-13 17:38:10.000000000 +0300
-@@ -193,6 +193,7 @@
-  */
- #define EXT3_STATE_JDATA              0x00000001 /* journaled data exists */
- #define EXT3_STATE_NEW                        0x00000002 /* inode is newly created */
-+#define EXT3_STATE_DELETE             0x00000010 /* deferred delete inode */
- /*
-  * ioctl commands
-@@ -320,6 +321,7 @@
- #define EXT3_MOUNT_UPDATE_JOURNAL     0x1000  /* Update the journal format */
- #define EXT3_MOUNT_NO_UID32           0x2000  /* Disable 32-bit UIDs */
- #define EXT3_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
-+#define EXT3_MOUNT_ASYNCDEL           0x20000 /* Delayed deletion */
- /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
- #ifndef _LINUX_EXT2_FS_H
-@@ -697,6 +699,9 @@
- extern void ext3_dirty_inode(struct inode *);
- extern int ext3_change_inode_journal_flag(struct inode *, int);
- extern void ext3_truncate (struct inode *);
-+#ifdef EXT3_DELETE_THREAD
-+extern void ext3_truncate_thread(struct inode *inode);
-+#endif
- extern void ext3_set_inode_flags(struct inode *);
- /* ioctl.c */
-Index: linux-2.4.21-suse/include/linux/ext3_fs_sb.h
-===================================================================
---- linux-2.4.21-suse.orig/include/linux/ext3_fs_sb.h  2004-01-12 19:49:25.000000000 +0300
-+++ linux-2.4.21-suse/include/linux/ext3_fs_sb.h       2004-01-13 17:38:10.000000000 +0300
-@@ -29,6 +29,8 @@
- #define EXT3_MAX_GROUP_LOADED 8
-+#define EXT3_DELETE_THREAD
-+
- /*
-  * third extended-fs super-block data in memory
-  */
-@@ -76,6 +78,14 @@
-       struct timer_list turn_ro_timer;        /* For turning read-only (crash simulation) */
-       wait_queue_head_t ro_wait_queue;        /* For people waiting for the fs to go read-only */
- #endif
-+#ifdef EXT3_DELETE_THREAD
-+      spinlock_t s_delete_lock;
-+      struct list_head s_delete_list;
-+      unsigned long s_delete_blocks;
-+      unsigned long s_delete_inodes;
-+      wait_queue_head_t s_delete_thread_queue;
-+      wait_queue_head_t s_delete_waiter_queue;
-+#endif
- };
- #endif        /* _LINUX_EXT3_FS_SB */
diff --git a/lustre/kernel_patches/patches/ext3-ea-in-inode-2.4.21-suse2.patch b/lustre/kernel_patches/patches/ext3-ea-in-inode-2.4.21-suse2.patch
new file mode 100644 (file)
index 0000000..5980fd9
--- /dev/null
@@ -0,0 +1,760 @@
+ fs/ext3/ialloc.c          |    6 
+ fs/ext3/inode.c           |   12 
+ fs/ext3/super.c           |    6 
+ fs/ext3/xattr.c           |  597 +++++++++++++++++++++++++++++++++++++++++++++-
+ include/linux/ext3_fs.h   |    2 
+ include/linux/ext3_fs_i.h |    3 
+ 6 files changed, 615 insertions(+), 11 deletions(-)
+
+Index: linux-2.4.21-chaos/fs/ext3/ialloc.c
+===================================================================
+--- linux-2.4.21-chaos.orig/fs/ext3/ialloc.c   2003-12-12 17:39:10.000000000 +0300
++++ linux-2.4.21-chaos/fs/ext3/ialloc.c        2003-12-12 17:39:55.000000000 +0300
+@@ -580,6 +580,12 @@
+       insert_inode_hash(inode);
+       inode->i_generation = sbi->s_next_generation++;
++      if (EXT3_INODE_SIZE(inode->i_sb) > EXT3_GOOD_OLD_INODE_SIZE) {
++              EXT3_I(inode)->i_extra_isize = sizeof(__u16)    /* i_extra_isize */
++                              + sizeof(__u16);        /* i_pad1 */
++      } else
++              EXT3_I(inode)->i_extra_isize = 0;
++
+       inode->u.ext3_i.i_state = EXT3_STATE_NEW;
+       err = ext3_get_inode_loc_new(inode, &iloc, 1);
+       if (err) goto fail;
+Index: linux-2.4.21-chaos/fs/ext3/inode.c
+===================================================================
+--- linux-2.4.21-chaos.orig/fs/ext3/inode.c    2003-12-12 17:39:11.000000000 +0300
++++ linux-2.4.21-chaos/fs/ext3/inode.c 2003-12-12 17:39:55.000000000 +0300
+@@ -2502,6 +2502,12 @@
+               ei->i_data[block] = iloc.raw_inode->i_block[block];
+       INIT_LIST_HEAD(&ei->i_orphan);
++      if (EXT3_INODE_SIZE(inode->i_sb) > EXT3_GOOD_OLD_INODE_SIZE)
++              EXT3_I(inode)->i_extra_isize =
++                      le16_to_cpu(raw_inode->i_extra_isize);
++      else
++              EXT3_I(inode)->i_extra_isize = 0;
++
+       if (S_ISREG(inode->i_mode)) {
+               inode->i_op = &ext3_file_inode_operations;
+               inode->i_fop = &ext3_file_operations;
+@@ -2564,6 +2570,8 @@
+               if (err)
+                       goto out_brelse;
+       }
++      if (EXT3_I(inode)->i_state & EXT3_STATE_NEW)
++              memset(raw_inode, 0, EXT3_INODE_SIZE(inode->i_sb));
+       raw_inode->i_mode = cpu_to_le16(inode->i_mode);
+       if(!(test_opt(inode->i_sb, NO_UID32))) {
+               raw_inode->i_uid_low = cpu_to_le16(low_16_bits(inode->i_uid));
+@@ -2646,6 +2654,10 @@
+       else for (block = 0; block < EXT3_N_BLOCKS; block++)
+               raw_inode->i_block[block] = ei->i_data[block];
++      if (EXT3_INODE_SIZE(inode->i_sb) > EXT3_GOOD_OLD_INODE_SIZE)
++              raw_inode->i_extra_isize =
++                      cpu_to_le16(EXT3_I(inode)->i_extra_isize);
++
+       BUFFER_TRACE(bh, "call ext3_journal_dirty_metadata");
+       rc = ext3_journal_dirty_metadata(handle, bh);
+       if (!err)
+Index: linux-2.4.21-chaos/fs/ext3/xattr.c
+===================================================================
+--- linux-2.4.21-chaos.orig/fs/ext3/xattr.c    2003-12-12 17:38:44.000000000 +0300
++++ linux-2.4.21-chaos/fs/ext3/xattr.c 2003-12-12 17:42:58.000000000 +0300
+@@ -88,6 +88,9 @@
+                                 struct buffer_head *,
+                                 struct ext3_xattr_header *);
++int ext3_xattr_block_set(handle_t *, struct inode *, int, const char *,
++                      const void *, size_t, int);
++
+ #ifdef CONFIG_EXT3_FS_XATTR_SHARING
+ static int ext3_xattr_cache_insert(struct buffer_head *);
+@@ -256,17 +259,12 @@
+ }
+ /*
+- * ext3_xattr_get()
+- *
+- * Copy an extended attribute into the buffer
+- * provided, or compute the buffer size required.
+- * Buffer is NULL to compute the size of the buffer required.
++ * ext3_xattr_block_get()
+  *
+- * Returns a negative error number on failure, or the number of bytes
+- * used / required on success.
++ * routine looks for attribute in EA block and returns it's value and size
+  */
+ int
+-ext3_xattr_get(struct inode *inode, int name_index, const char *name,
++ext3_xattr_block_get(struct inode *inode, int name_index, const char *name,
+              void *buffer, size_t buffer_size)
+ {
+       struct buffer_head *bh = NULL;
+@@ -359,6 +357,94 @@
+ }
+ /*
++ * ext3_xattr_ibody_get()
++ *
++ * routine looks for attribute in inode body and returns it's value and size
++ */
++int
++ext3_xattr_ibody_get(struct inode *inode, int name_index, const char *name,
++             void *buffer, size_t buffer_size)
++{
++      int size, name_len = strlen(name), storage_size;
++      struct ext3_xattr_entry *last;
++      struct ext3_inode *raw_inode;
++      struct ext3_iloc iloc;
++      char *start, *end;
++      int ret = -ENOENT;
++      
++      if (EXT3_SB(inode->i_sb)->s_inode_size <= EXT3_GOOD_OLD_INODE_SIZE)
++              return -ENOENT;
++
++      ret = ext3_get_inode_loc(inode, &iloc);
++      if (ret)
++              return ret;
++      raw_inode = iloc.raw_inode;
++
++      storage_size = EXT3_SB(inode->i_sb)->s_inode_size -
++                              EXT3_GOOD_OLD_INODE_SIZE -
++                              EXT3_I(inode)->i_extra_isize -
++                              sizeof(__u32);
++      start = (char *) raw_inode + EXT3_GOOD_OLD_INODE_SIZE +
++                      EXT3_I(inode)->i_extra_isize;
++      if (le32_to_cpu((*(__u32*) start)) != EXT3_XATTR_MAGIC) {
++              brelse(iloc.bh);
++              return -ENOENT;
++      }
++      start += sizeof(__u32);
++      end = (char *) raw_inode + EXT3_SB(inode->i_sb)->s_inode_size;
++
++      last = (struct ext3_xattr_entry *) start;
++      while (!IS_LAST_ENTRY(last)) {
++              struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(last);
++              if (le32_to_cpu(last->e_value_size) > storage_size ||
++                              (char *) next >= end) {
++                      ext3_error(inode->i_sb, "ext3_xattr_ibody_get",
++                              "inode %ld", inode->i_ino);
++                      brelse(iloc.bh);
++                      return -EIO;
++              }
++              if (name_index == last->e_name_index &&
++                  name_len == last->e_name_len &&
++                  !memcmp(name, last->e_name, name_len))
++                      goto found;
++              last = next;
++      }
++
++      /* can't find EA */
++      brelse(iloc.bh);
++      return -ENOENT;
++      
++found:
++      size = le32_to_cpu(last->e_value_size);
++      if (buffer) {
++              ret = -ERANGE;
++              if (buffer_size >= size) {
++                      memcpy(buffer, start + le16_to_cpu(last->e_value_offs),
++                      size);
++                      ret = size;
++              }
++      } else
++              ret = size;
++      brelse(iloc.bh);
++      return ret;
++}
++
++int ext3_xattr_get(struct inode *inode, int name_index, const char *name,
++                      void *buffer, size_t buffer_size)
++{
++      int err;
++
++      /* try to find attribute in inode body */
++      err = ext3_xattr_ibody_get(inode, name_index, name,
++                                      buffer, buffer_size);
++      if (err < 0)
++              /* search was unsuccessful, try to find EA in dedicated block */
++              err = ext3_xattr_block_get(inode, name_index, name,
++                              buffer, buffer_size);
++      return err;
++}
++
++/*
+  * ext3_xattr_list()
+  *
+  * Copy a list of attribute names into the buffer
+@@ -369,7 +455,7 @@
+  * used / required on success.
+  */
+ int
+-ext3_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
++ext3_xattr_block_list(struct inode *inode, char *buffer, size_t buffer_size)
+ {
+       struct buffer_head *bh = NULL;
+       struct ext3_xattr_entry *entry;
+@@ -446,6 +532,131 @@
+       return error;
+ }
++/* ext3_xattr_ibody_list()
++ *
++ * generate list of attributes stored in inode body
++ */
++int
++ext3_xattr_ibody_list(struct inode *inode, char *buffer, size_t buffer_size)
++{
++      struct ext3_xattr_entry *last;
++      struct ext3_inode *raw_inode;
++      char *start, *end, *buf;
++      struct ext3_iloc iloc;
++      int storage_size;
++      int ret;
++      int size = 0;
++      
++      if (EXT3_SB(inode->i_sb)->s_inode_size <= EXT3_GOOD_OLD_INODE_SIZE)
++              return 0;
++
++      ret = ext3_get_inode_loc(inode, &iloc);
++      if (ret)
++              return ret;
++      raw_inode = iloc.raw_inode;
++
++      storage_size = EXT3_SB(inode->i_sb)->s_inode_size -
++                              EXT3_GOOD_OLD_INODE_SIZE -
++                              EXT3_I(inode)->i_extra_isize -
++                              sizeof(__u32);
++      start = (char *) raw_inode + EXT3_GOOD_OLD_INODE_SIZE +
++                      EXT3_I(inode)->i_extra_isize;
++      if (le32_to_cpu((*(__u32*) start)) != EXT3_XATTR_MAGIC) {
++              brelse(iloc.bh);
++              return 0;
++      }
++      start += sizeof(__u32);
++      end = (char *) raw_inode + EXT3_SB(inode->i_sb)->s_inode_size;
++
++      last = (struct ext3_xattr_entry *) start;
++      while (!IS_LAST_ENTRY(last)) {
++              struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(last);
++              struct ext3_xattr_handler *handler;
++              if (le32_to_cpu(last->e_value_size) > storage_size ||
++                              (char *) next >= end) {
++                      ext3_error(inode->i_sb, "ext3_xattr_ibody_list",
++                              "inode %ld", inode->i_ino);
++                      brelse(iloc.bh);
++                      return -EIO;
++              }
++              handler = ext3_xattr_handler(last->e_name_index);
++              if (handler)
++                      size += handler->list(NULL, inode, last->e_name,
++                                            last->e_name_len);
++              last = next;
++      }
++
++      if (!buffer) {
++              ret = size;
++              goto cleanup;
++      } else {
++              ret = -ERANGE;
++              if (size > buffer_size)
++                      goto cleanup;
++      }
++
++      last = (struct ext3_xattr_entry *) start;
++      buf = buffer;
++      while (!IS_LAST_ENTRY(last)) {
++              struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(last);
++              struct ext3_xattr_handler *handler;
++              handler = ext3_xattr_handler(last->e_name_index);
++              if (handler)
++                      buf += handler->list(buf, inode, last->e_name,
++                                            last->e_name_len);
++              last = next;
++      }
++      ret = size;
++cleanup:
++      brelse(iloc.bh);
++      return ret;
++}
++
++/*
++ * ext3_xattr_list()
++ *
++ * Copy a list of attribute names into the buffer
++ * provided, or compute the buffer size required.
++ * Buffer is NULL to compute the size of the buffer required.
++ *
++ * Returns a negative error number on failure, or the number of bytes
++ * used / required on success.
++ */
++int
++ext3_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
++{
++      int error;
++      int size = buffer_size;
++
++      /* get list of attributes stored in inode body */
++      error = ext3_xattr_ibody_list(inode, buffer, buffer_size);
++      if (error < 0) {
++              /* some error occured while collecting
++               * attributes in inode body */
++              size = 0;
++              goto cleanup;
++      }
++      size = error;
++
++      /* get list of attributes stored in dedicated block */
++      if (buffer) {
++              buffer_size -= error;
++              if (buffer_size <= 0) {
++                      buffer = NULL;
++                      buffer_size = 0;
++              } else
++                      buffer += error;
++      }
++
++      error = ext3_xattr_block_list(inode, buffer, buffer_size);
++      if (error < 0)
++              /* listing was successful, so we return len */
++              size = 0;
++
++cleanup:
++      return error + size;
++}
++
+ /*
+  * If the EXT3_FEATURE_COMPAT_EXT_ATTR feature of this file system is
+  * not set, set it.
+@@ -480,6 +691,102 @@
+  */
+ int
+ ext3_xattr_set_handle(handle_t *handle, struct inode *inode, int name_index,
++                      const char *name, const void *value, size_t value_len,
++                      int flags)
++{
++      struct ext3_xattr_entry entry;
++      int err, where = 0, found = 0, total;
++      int free1 = -1, free2 = -1;
++      int name_len;
++      
++      ea_idebug(inode, "name=%d.%s, value=%p, value_len=%ld",
++                name_index, name, value, (long)value_len);
++
++      if (IS_RDONLY(inode))
++              return -EROFS;
++      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
++              return -EPERM;
++      if (value == NULL)
++              value_len = 0;
++      if (name == NULL)
++              return -EINVAL;
++      name_len = strlen(name);
++      if (name_len > 255 || value_len > inode->i_sb->s_blocksize)
++              return -ERANGE;
++
++      /* try to find attribute in inode body */
++      err = ext3_xattr_ibody_find(inode, name_index, name, &entry, &free1);
++      if (err == 0) {
++              /* found EA in inode */
++              found = 1;
++              where = 0;
++      } else if (err == -ENOENT) {
++              /* there is no such attribute in inode body */
++              /* try to find attribute in dedicated block */
++              err = ext3_xattr_block_find(inode, name_index, name,
++                                              &entry, &free2);
++              if (err != 0 && err != -ENOENT) {
++                      /* not found EA in block */
++                      goto finish;    
++              } else if (err == 0) {
++                      /* found EA in block */
++                      where = 1;
++                      found = 1;
++              }
++      } else
++              goto finish;
++
++      /* check flags: may replace? may create ? */
++      if (found && (flags & XATTR_CREATE)) {
++              err = -EEXIST;
++              goto finish;
++      } else if (!found && (flags & XATTR_REPLACE)) {
++              err = -ENODATA;
++              goto finish;
++      }
++
++      /* check if we have enough space to store attribute */
++      total = EXT3_XATTR_LEN(strlen(name)) + value_len;
++      if (free1 >= 0 && total > free1 && free2 >= 0 && total > free2) {
++              /* have no enough space */
++              err = -ENOSPC;
++              goto finish;
++      }
++      
++      /* time to remove attribute */
++      if (found) {
++              if (where == 0) {
++                      /* EA is stored in inode body */
++                      ext3_xattr_ibody_set(handle, inode, name_index, name,
++                                      NULL, 0, flags);
++              } else {
++                      /* EA is stored in separated block */
++                      ext3_xattr_block_set(handle, inode, name_index, name,
++                                      NULL, 0, flags);
++              }
++      }
++
++      /* try to store EA in inode body */
++      err = ext3_xattr_ibody_set(handle, inode, name_index, name,
++                              value, value_len, flags);
++      if (err) {
++              /* can't store EA in inode body */
++              /* try to store in block */
++              err = ext3_xattr_block_set(handle, inode, name_index,
++                                      name, value, value_len, flags); 
++      }
++
++finish:       
++      return err;
++}
++
++/*
++ * ext3_xattr_block_set()
++ *
++ * this routine add/remove/replace attribute in EA block
++ */
++int
++ext3_xattr_block_set(handle_t *handle, struct inode *inode, int name_index,
+                     const char *name, const void *value, size_t value_len,
+                     int flags)
+ {
+@@ -868,6 +1174,279 @@
+ }
+ /*
++ * ext3_xattr_ibody_find()
++ *
++ * search attribute and calculate free space in inode body
++ * NOTE: free space includes space our attribute hold
++ */
++int
++ext3_xattr_ibody_find(struct inode *inode, int name_index,
++              const char *name, struct ext3_xattr_entry *rentry, int *free)
++{
++      struct ext3_xattr_entry *last;
++      struct ext3_inode *raw_inode;
++      int name_len = strlen(name);
++      int err, storage_size;
++      struct ext3_iloc iloc;
++      char *start, *end;
++      int ret = -ENOENT;
++      
++      if (EXT3_SB(inode->i_sb)->s_inode_size <= EXT3_GOOD_OLD_INODE_SIZE)
++              return ret;
++
++      err = ext3_get_inode_loc(inode, &iloc);
++      if (err)
++              return -EIO;
++      raw_inode = iloc.raw_inode;
++
++      storage_size = EXT3_SB(inode->i_sb)->s_inode_size -
++                              EXT3_GOOD_OLD_INODE_SIZE -
++                              EXT3_I(inode)->i_extra_isize -
++                              sizeof(__u32);
++      *free = storage_size - sizeof(__u32);
++      start = (char *) raw_inode + EXT3_GOOD_OLD_INODE_SIZE +
++                      EXT3_I(inode)->i_extra_isize;
++      if (le32_to_cpu((*(__u32*) start)) != EXT3_XATTR_MAGIC) {
++              brelse(iloc.bh);
++              return -ENOENT;
++      }
++      start += sizeof(__u32);
++      end = (char *) raw_inode + EXT3_SB(inode->i_sb)->s_inode_size;
++
++      last = (struct ext3_xattr_entry *) start;
++      while (!IS_LAST_ENTRY(last)) {
++              struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(last);
++              if (le32_to_cpu(last->e_value_size) > storage_size ||
++                              (char *) next >= end) {
++                      ext3_error(inode->i_sb, "ext3_xattr_ibody_find",
++                              "inode %ld", inode->i_ino);
++                      brelse(iloc.bh);
++                      return -EIO;
++              }
++
++              if (name_index == last->e_name_index &&
++                  name_len == last->e_name_len &&
++                  !memcmp(name, last->e_name, name_len)) {
++                      memcpy(rentry, last, sizeof(struct ext3_xattr_entry));
++                      ret = 0;
++              } else {
++                      *free -= EXT3_XATTR_LEN(last->e_name_len);
++                      *free -= le32_to_cpu(last->e_value_size);
++              }
++              last = next;
++      }
++      
++      brelse(iloc.bh);
++      return ret;
++}
++
++/*
++ * ext3_xattr_block_find()
++ *
++ * search attribute and calculate free space in EA block (if it allocated)
++ * NOTE: free space includes space our attribute hold
++ */
++int
++ext3_xattr_block_find(struct inode *inode, int name_index, const char *name,
++             struct ext3_xattr_entry *rentry, int *free)
++{
++      struct buffer_head *bh = NULL;
++      struct ext3_xattr_entry *entry;
++      char *end;
++      int name_len, error = -ENOENT;
++
++      if (!EXT3_I(inode)->i_file_acl) {
++              *free = inode->i_sb->s_blocksize -
++                      sizeof(struct ext3_xattr_header) -
++                      sizeof(__u32);
++              return -ENOENT;
++      }
++      ea_idebug(inode, "reading block %d", EXT3_I(inode)->i_file_acl);
++      bh = sb_bread(inode->i_sb, EXT3_I(inode)->i_file_acl);
++      if (!bh)
++              return -EIO;
++      ea_bdebug(bh, "b_count=%d, refcount=%d",
++              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
++      end = bh->b_data + bh->b_size;
++      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
++          HDR(bh)->h_blocks != cpu_to_le32(1)) {
++bad_block:    ext3_error(inode->i_sb, "ext3_xattr_get",
++                      "inode %ld: bad block %d", inode->i_ino,
++                      EXT3_I(inode)->i_file_acl);
++              brelse(bh);
++              return -EIO;
++      }
++      /* find named attribute */
++      name_len = strlen(name);
++      *free = bh->b_size - sizeof(__u32);
++
++      entry = FIRST_ENTRY(bh);
++      while (!IS_LAST_ENTRY(entry)) {
++              struct ext3_xattr_entry *next =
++                      EXT3_XATTR_NEXT(entry);
++              if ((char *)next >= end)
++                      goto bad_block;
++              if (name_index == entry->e_name_index &&
++                  name_len == entry->e_name_len &&
++                  memcmp(name, entry->e_name, name_len) == 0) {
++                      memcpy(rentry, entry, sizeof(struct ext3_xattr_entry));
++                      error = 0;
++              } else {
++                      *free -= EXT3_XATTR_LEN(entry->e_name_len);
++                      *free -= le32_to_cpu(entry->e_value_size);
++              }
++              entry = next;
++      }
++      brelse(bh);
++
++      return error;
++}
++
++/*
++ * ext3_xattr_inode_set()
++ *
++ * this routine add/remove/replace attribute in inode body
++ */
++int
++ext3_xattr_ibody_set(handle_t *handle, struct inode *inode, int name_index,
++                    const char *name, const void *value, size_t value_len,
++                    int flags)
++{
++      struct ext3_xattr_entry *last, *next, *here = NULL;
++      struct ext3_inode *raw_inode;
++      int name_len = strlen(name);
++      int esize = EXT3_XATTR_LEN(name_len);
++      struct buffer_head *bh;
++      int err, storage_size;
++      struct ext3_iloc iloc;
++      int free, min_offs;
++      char *start, *end;
++      
++      if (EXT3_SB(inode->i_sb)->s_inode_size <= EXT3_GOOD_OLD_INODE_SIZE)
++              return -ENOSPC;
++
++      err = ext3_get_inode_loc(inode, &iloc);
++      if (err)
++              return err;
++      raw_inode = iloc.raw_inode;
++      bh = iloc.bh;
++
++      storage_size = EXT3_SB(inode->i_sb)->s_inode_size -
++                              EXT3_GOOD_OLD_INODE_SIZE -
++                              EXT3_I(inode)->i_extra_isize -
++                              sizeof(__u32);
++      start = (char *) raw_inode + EXT3_GOOD_OLD_INODE_SIZE +
++                      EXT3_I(inode)->i_extra_isize;
++      if ((*(__u32*) start) != EXT3_XATTR_MAGIC) {
++              /* inode had no attributes before */
++              *((__u32*) start) = cpu_to_le32(EXT3_XATTR_MAGIC);
++      }
++      start += sizeof(__u32);
++      end = (char *) raw_inode + EXT3_SB(inode->i_sb)->s_inode_size;
++      min_offs = storage_size;
++      free = storage_size - sizeof(__u32);
++
++      last = (struct ext3_xattr_entry *) start;       
++      while (!IS_LAST_ENTRY(last)) {
++              next = EXT3_XATTR_NEXT(last);
++              if (le32_to_cpu(last->e_value_size) > storage_size ||
++                              (char *) next >= end) {
++                      ext3_error(inode->i_sb, "ext3_xattr_ibody_set",
++                              "inode %ld", inode->i_ino);
++                      brelse(bh);
++                      return -EIO;
++              }
++              
++              if (last->e_value_size) {
++                      int offs = le16_to_cpu(last->e_value_offs);
++                      if (offs < min_offs)
++                              min_offs = offs;
++              }
++              if (name_index == last->e_name_index &&
++                      name_len == last->e_name_len &&
++                      !memcmp(name, last->e_name, name_len))
++                      here = last;
++              else {
++                      /* we calculate all but our attribute
++                       * because it will be removed before changing */
++                      free -= EXT3_XATTR_LEN(last->e_name_len);
++                      free -= le32_to_cpu(last->e_value_size);
++              }
++              last = next;
++      }
++
++      if (value && (esize + value_len > free)) {
++              brelse(bh);
++              return -ENOSPC;
++      }
++      
++      err = ext3_reserve_inode_write(handle, inode, &iloc);
++      if (err) {
++              brelse(bh);     
++              return err;
++      }
++
++      if (here) {
++              /* time to remove old value */
++              struct ext3_xattr_entry *e;
++              int size = le32_to_cpu(here->e_value_size);
++              int border = le16_to_cpu(here->e_value_offs);
++              char *src;
++
++              /* move tail */
++              memmove(start + min_offs + size, start + min_offs,
++                              border - min_offs);
++
++              /* recalculate offsets */
++              e = (struct ext3_xattr_entry *) start;
++              while (!IS_LAST_ENTRY(e)) {
++                      struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(e);
++                      int offs = le16_to_cpu(e->e_value_offs);
++                      if (offs < border)
++                              e->e_value_offs =
++                                      cpu_to_le16(offs + size);
++                      e = next;
++              }
++              min_offs += size;
++
++              /* remove entry */
++              border = EXT3_XATTR_LEN(here->e_name_len);
++              src = (char *) here + EXT3_XATTR_LEN(here->e_name_len);
++              size = (char *) last - src;
++              if ((char *) here + size > end)
++                      printk("ALERT at %s:%d: 0x%p + %d > 0x%p\n",
++                                      __FILE__, __LINE__, here, size, end);
++              memmove(here, src, size);
++              last = (struct ext3_xattr_entry *) ((char *) last - border);
++              *((__u32 *) last) = 0;
++      }
++      
++      if (value) {
++              int offs = min_offs - value_len;
++              /* use last to create new entry */
++              last->e_name_len = strlen(name);
++              last->e_name_index = name_index;
++              last->e_value_offs = cpu_to_le16(offs);
++              last->e_value_size = cpu_to_le32(value_len);
++              last->e_hash = last->e_value_block = 0;
++              memset(last->e_name, 0, esize);
++              memcpy(last->e_name, name, last->e_name_len);
++              if (start + offs + value_len > end)
++                      printk("ALERT at %s:%d: 0x%p + %d + %d > 0x%p\n",
++                                      __FILE__, __LINE__, start, offs,
++                                      value_len, end);
++              memcpy(start + offs, value, value_len);
++              last = EXT3_XATTR_NEXT(last);
++              *((__u32 *) last) = 0;
++      }
++      
++      ext3_mark_iloc_dirty(handle, inode, &iloc);
++      brelse(bh);
++
++      return 0;
++}
++
++/*
+  * ext3_xattr_set_trans()
+  *
+  * Like ext3_xattr_set_handle, but start from an inode. This extended
+Index: linux-2.4.21-chaos/fs/ext3/super.c
+===================================================================
+--- linux-2.4.21-chaos.orig/fs/ext3/super.c    2003-12-12 17:39:11.000000000 +0300
++++ linux-2.4.21-chaos/fs/ext3/super.c 2003-12-12 17:39:55.000000000 +0300
+@@ -1354,8 +1354,10 @@
+       } else {
+               sbi->s_inode_size = le16_to_cpu(es->s_inode_size);
+               sbi->s_first_ino = le32_to_cpu(es->s_first_ino);
+-              if (sbi->s_inode_size != EXT3_GOOD_OLD_INODE_SIZE) {
+-                      printk (KERN_ERR
++              if ((sbi->s_inode_size < EXT3_GOOD_OLD_INODE_SIZE) ||
++                              (sbi->s_inode_size & (sbi->s_inode_size - 1)) ||
++                              (sbi->s_inode_size > blocksize)) {
++                      printk (KERN_ERR
+                               "EXT3-fs: unsupported inode size: %d\n",
+                               sbi->s_inode_size);
+                       goto failed_mount;
+Index: linux-2.4.21-chaos/include/linux/ext3_fs.h
+===================================================================
+--- linux-2.4.21-chaos.orig/include/linux/ext3_fs.h    2003-12-12 17:39:10.000000000 +0300
++++ linux-2.4.21-chaos/include/linux/ext3_fs.h 2003-12-12 17:39:55.000000000 +0300
+@@ -268,6 +268,8 @@
+                       __u32   m_i_reserved2[2];
+               } masix2;
+       } osd2;                         /* OS dependent 2 */
++      __u16   i_extra_isize;
++      __u16   i_pad1;
+ };
+ #define i_size_high   i_dir_acl
+Index: linux-2.4.21-chaos/include/linux/ext3_fs_i.h
+===================================================================
+--- linux-2.4.21-chaos.orig/include/linux/ext3_fs_i.h  2003-12-05 16:54:33.000000000 +0300
++++ linux-2.4.21-chaos/include/linux/ext3_fs_i.h       2003-12-12 17:39:55.000000000 +0300
+@@ -76,6 +76,9 @@
+        */
+       loff_t  i_disksize;
++      /* on-disk additional length */
++      __u16 i_extra_isize;
++
+       /*
+        * truncate_sem is for serialising ext3_truncate() against
+        * ext3_getblock().  In the 2.4 ext2 design, great chunks of inode's
diff --git a/lustre/kernel_patches/patches/ext3-extents-2.4.20-rh.patch b/lustre/kernel_patches/patches/ext3-extents-2.4.20-rh.patch
deleted file mode 100644 (file)
index c5af18c..0000000
+++ /dev/null
@@ -1,2807 +0,0 @@
-Index: linux-2.4.20-rh-20.9/fs/ext3/extents.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/extents.c        2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/extents.c     2004-11-03 00:31:41.927134640 +0300
-@@ -0,0 +1,2269 @@
-+/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
-+ * Written by Alex Tomas <alex@clusterfs.com>
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ *
-+ * This program is distributed in the hope that it will be useful,
-+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
-+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-+ * GNU General Public License for more details.
-+ *
-+ * You should have received a copy of the GNU General Public Licens
-+ * along with this program; if not, write to the Free Software
-+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-
-+ */
-+
-+/*
-+ * Extents support for EXT3
-+ *
-+ * TODO:
-+ *   - ext3_ext_walk_space() sould not use ext3_ext_find_extent()
-+ *   - ext3_ext_calc_credits() could take 'mergable' into account
-+ *   - ext3*_error() should be used in some situations
-+ *   - find_goal() [to be tested and improved]
-+ *   - smart tree reduction
-+ *   - arch-independence
-+ *     common on-disk format for big/little-endian arch
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/fs.h>
-+#include <linux/time.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/jbd.h>
-+#include <linux/locks.h>
-+#include <linux/smp_lock.h>
-+#include <linux/highuid.h>
-+#include <linux/pagemap.h>
-+#include <linux/quotaops.h>
-+#include <linux/string.h>
-+#include <linux/slab.h>
-+#include <linux/ext3_extents.h>
-+#include <asm/uaccess.h>
-+
-+static handle_t *ext3_ext_journal_restart(handle_t *handle, int needed)
-+{
-+      int err;
-+
-+      if (handle->h_buffer_credits > needed)
-+              return handle;
-+      if (!ext3_journal_extend(handle, needed))
-+              return handle;
-+      err = ext3_journal_restart(handle, needed);
-+      
-+      return handle;
-+}
-+
-+static int inline
-+ext3_ext_get_access_for_root(handle_t *h, struct ext3_extents_tree *tree)
-+{
-+      if (tree->ops->get_write_access)
-+              return tree->ops->get_write_access(h,tree->buffer);
-+      else
-+              return 0;
-+}
-+
-+static int inline
-+ext3_ext_mark_root_dirty(handle_t *h, struct ext3_extents_tree *tree)
-+{
-+      if (tree->ops->mark_buffer_dirty)
-+              return tree->ops->mark_buffer_dirty(h,tree->buffer);
-+      else
-+              return 0;
-+}
-+
-+/*
-+ * could return:
-+ *  - EROFS
-+ *  - ENOMEM
-+ */
-+static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
-+{
-+      int err;
-+
-+      if (path->p_bh) {
-+              /* path points to block */
-+              err = ext3_journal_get_write_access(handle, path->p_bh);
-+      } else {
-+              /* path points to leaf/index in inode body */
-+              err = ext3_ext_get_access_for_root(handle, tree);
-+      }
-+      return err;
-+}
-+
-+/*
-+ * could return:
-+ *  - EROFS
-+ *  - ENOMEM
-+ *  - EIO
-+ */
-+static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
-+{
-+      int err;
-+      if (path->p_bh) {
-+              /* path points to block */
-+              err =ext3_journal_dirty_metadata(handle, path->p_bh);
-+      } else {
-+              /* path points to leaf/index in inode body */
-+              err = ext3_ext_mark_root_dirty(handle, tree);
-+      }
-+      return err;
-+}
-+
-+static int inline
-+ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
-+{
-+      int goal, depth, newblock;
-+      struct inode *inode;
-+
-+      EXT_ASSERT(tree);
-+      if (tree->ops->new_block)
-+              return tree->ops->new_block(handle, tree, path, ex, err);
-+
-+      inode = tree->inode;
-+      depth = EXT_DEPTH(tree);
-+      if (path && depth > 0) {
-+              goal = path[depth-1].p_block;
-+      } else {
-+              struct ext3_inode_info *ei = EXT3_I(inode);
-+              unsigned long bg_start;
-+              unsigned long colour;
-+
-+              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
-+                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
-+              colour = (current->pid % 16) *
-+                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
-+              goal = bg_start + colour;
-+      }
-+
-+      newblock = ext3_new_block(handle, inode, goal, 0, 0, err);
-+      return newblock;
-+}
-+
-+static inline void ext3_ext_tree_changed(struct ext3_extents_tree *tree)
-+{
-+      struct ext3_extent_header *neh;
-+      neh = EXT_ROOT_HDR(tree);
-+      neh->eh_generation++;
-+}
-+
-+static inline int ext3_ext_space_block(struct ext3_extents_tree *tree)
-+{
-+      int size;
-+
-+      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              / sizeof(struct ext3_extent);
-+#ifdef AGRESSIVE_TEST
-+      size = 6;
-+#endif
-+      return size;
-+}
-+
-+static inline int ext3_ext_space_block_idx(struct ext3_extents_tree *tree)
-+{
-+      int size;
-+
-+      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              / sizeof(struct ext3_extent_idx);
-+#ifdef AGRESSIVE_TEST
-+      size = 5;
-+#endif
-+      return size;
-+}
-+
-+static inline int ext3_ext_space_root(struct ext3_extents_tree *tree)
-+{
-+      int size;
-+
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent);
-+#ifdef AGRESSIVE_TEST
-+      size = 3;
-+#endif
-+      return size;
-+}
-+
-+static inline int ext3_ext_space_root_idx(struct ext3_extents_tree *tree)
-+{
-+      int size;
-+
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
-+#ifdef AGRESSIVE_TEST
-+      size = 4;
-+#endif
-+      return size;
-+}
-+
-+static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
-+{
-+#ifdef EXT_DEBUG
-+      int k, l = path->p_depth;
-+
-+      ext_debug(tree, "path:");
-+      for (k = 0; k <= l; k++, path++) {
-+              if (path->p_idx) {
-+                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
-+              } else if (path->p_ext) {
-+                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
-+              } else
-+                      ext_debug(tree, "  []");
-+      }
-+      ext_debug(tree, "\n");
-+#endif
-+}
-+
-+static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
-+{
-+#ifdef EXT_DEBUG
-+      int depth = EXT_DEPTH(tree);
-+      struct ext3_extent_header *eh;
-+      struct ext3_extent *ex;
-+      int i;
-+
-+      if (!path)
-+              return;
-+
-+      eh = path[depth].p_hdr;
-+      ex = EXT_FIRST_EXTENT(eh);
-+
-+      for (i = 0; i < eh->eh_entries; i++, ex++) {
-+              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
-+      }
-+      ext_debug(tree, "\n");
-+#endif
-+}
-+
-+static void ext3_ext_drop_refs(struct ext3_ext_path *path)
-+{
-+      int depth = path->p_depth;
-+      int i;
-+
-+      for (i = 0; i <= depth; i++, path++)
-+              if (path->p_bh) {
-+                      brelse(path->p_bh);
-+                      path->p_bh = NULL;
-+              }
-+}
-+
-+/*
-+ * binary search for closest index by given block
-+ */
-+static inline void
-+ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
-+{
-+      struct ext3_extent_header *eh = path->p_hdr;
-+      struct ext3_extent_idx *ix;
-+      int l = 0, k, r;
-+
-+      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(eh->eh_entries <= eh->eh_max);
-+      EXT_ASSERT(eh->eh_entries > 0);
-+
-+      ext_debug(tree, "binsearch for %d(idx):  ", block);
-+
-+      path->p_idx = ix = EXT_FIRST_INDEX(eh);
-+
-+      r = k = eh->eh_entries;
-+      while (k > 1) {
-+              k = (r - l) / 2;
-+              if (block < ix[l + k].ei_block)
-+                      r -= k;
-+              else
-+                      l += k;
-+              ext_debug(tree, "%d:%d:%d ", k, l, r);
-+      }
-+
-+      ix += l;
-+      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
-+
-+      while (l++ < r) {
-+              if (block < ix->ei_block) 
-+                      break;
-+              path->p_idx = ix++;
-+      }
-+      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
-+
-+#ifdef CHECK_BINSEARCH 
-+      {
-+              struct ext3_extent_idx *chix;
-+
-+              chix = ix = EXT_FIRST_INDEX(eh);
-+              for (k = 0; k < eh->eh_entries; k++, ix++) {
-+                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
-+                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
-+                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
-+                      }
-+                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
-+                      if (block < ix->ei_block) 
-+                              break;
-+                      chix = ix;
-+              }
-+              EXT_ASSERT(chix == path->p_idx);
-+      }
-+#endif
-+
-+}
-+
-+/*
-+ * binary search for closest extent by given block
-+ */
-+static inline void
-+ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
-+{
-+      struct ext3_extent_header *eh = path->p_hdr;
-+      struct ext3_extent *ex;
-+      int l = 0, k, r;
-+
-+      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(eh->eh_entries <= eh->eh_max);
-+
-+      if (eh->eh_entries == 0) {
-+              /*
-+               * this leaf is empty yet:
-+               *  we get such a leaf in split/add case
-+               */
-+              return;
-+      }
-+      
-+      ext_debug(tree, "binsearch for %d:  ", block);
-+
-+      path->p_ext = ex = EXT_FIRST_EXTENT(eh);
-+
-+      r = k = eh->eh_entries;
-+      while (k > 1) {
-+              k = (r - l) / 2;
-+              if (block < ex[l + k].ee_block)
-+                      r -= k;
-+              else
-+                      l += k;
-+              ext_debug(tree, "%d:%d:%d ", k, l, r);
-+      }
-+
-+      ex += l;
-+      path->p_ext = ex;
-+      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
-+
-+      while (l++ < r) {
-+              if (block < ex->ee_block) 
-+                      break;
-+              path->p_ext = ex++;
-+      }
-+      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
-+
-+#ifdef CHECK_BINSEARCH 
-+      {
-+              struct ext3_extent *chex;
-+
-+              chex = ex = EXT_FIRST_EXTENT(eh);
-+              for (k = 0; k < eh->eh_entries; k++, ex++) {
-+                      EXT_ASSERT(k == 0 || ex->ee_block > ex[-1].ee_block);
-+                      if (block < ex->ee_block) 
-+                              break;
-+                      chex = ex;
-+              }
-+              EXT_ASSERT(chex == path->p_ext);
-+      }
-+#endif
-+
-+}
-+
-+int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
-+{
-+      struct ext3_extent_header *eh;
-+
-+      BUG_ON(tree->buffer_len == 0);
-+      ext3_ext_get_access_for_root(handle, tree);
-+      eh = EXT_ROOT_HDR(tree);
-+      eh->eh_depth = 0;
-+      eh->eh_entries = 0;
-+      eh->eh_magic = EXT3_EXT_MAGIC;
-+      eh->eh_max = ext3_ext_space_root(tree);
-+      ext3_ext_mark_root_dirty(handle, tree);
-+      ext3_ext_invalidate_cache(tree);
-+      return 0;
-+}
-+
-+struct ext3_ext_path *
-+ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
-+{
-+      struct ext3_extent_header *eh;
-+      struct buffer_head *bh;
-+      int depth, i, ppos = 0;
-+
-+      EXT_ASSERT(tree);
-+      EXT_ASSERT(tree->inode);
-+      EXT_ASSERT(tree->root);
-+
-+      eh = EXT_ROOT_HDR(tree);
-+      EXT_ASSERT(eh);
-+      i = depth = EXT_DEPTH(tree);
-+      EXT_ASSERT(eh->eh_max);
-+      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(i == 0 || eh->eh_entries > 0);
-+      
-+      /* account possible depth increase */
-+      if (!path) {
-+              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
-+              if (!path)
-+                      return ERR_PTR(-ENOMEM);
-+      }
-+      memset(path, 0, sizeof(struct ext3_ext_path) * (depth + 1));
-+      path[0].p_hdr = eh;
-+
-+      /* walk through the tree */
-+      while (i) {
-+              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
-+              ext3_ext_binsearch_idx(tree, path + ppos, block);
-+              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
-+              path[ppos].p_depth = i;
-+              path[ppos].p_ext = NULL;
-+
-+              bh = sb_bread(tree->inode->i_sb, path[ppos].p_block);
-+              if (!bh) {
-+                      ext3_ext_drop_refs(path);
-+                      kfree(path);
-+                      return ERR_PTR(-EIO);
-+              }
-+              eh = EXT_BLOCK_HDR(bh);
-+              ppos++;
-+              EXT_ASSERT(ppos <= depth);
-+              path[ppos].p_bh = bh;
-+              path[ppos].p_hdr = eh;
-+              i--;
-+      }
-+
-+      path[ppos].p_depth = i;
-+      path[ppos].p_hdr = eh;
-+      path[ppos].p_ext = NULL;
-+
-+      /* find extent */
-+      ext3_ext_binsearch(tree, path + ppos, block);
-+
-+      ext3_ext_show_path(tree, path);
-+
-+      return path;
-+}
-+
-+/*
-+ * insert new index [logical;ptr] into the block at cupr
-+ * it check where to insert: before curp or after curp
-+ */
-+static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
-+{
-+      struct ext3_extent_idx *ix;
-+      int len, err;
-+
-+      if ((err = ext3_ext_get_access(handle, tree, curp)))
-+              return err;
-+
-+      EXT_ASSERT(logical != curp->p_idx->ei_block);
-+      len = EXT_MAX_INDEX(curp->p_hdr) - curp->p_idx;
-+      if (logical > curp->p_idx->ei_block) {
-+              /* insert after */
-+              if (curp->p_idx != EXT_LAST_INDEX(curp->p_hdr)) {
-+                      len = (len - 1) * sizeof(struct ext3_extent_idx);
-+                      len = len < 0 ? 0 : len;
-+                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
-+                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
-+              }
-+              ix = curp->p_idx + 1;
-+      } else {
-+              /* insert before */
-+              len = len * sizeof(struct ext3_extent_idx);
-+              len = len < 0 ? 0 : len;
-+              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
-+              memmove(curp->p_idx + 1, curp->p_idx, len);
-+              ix = curp->p_idx;
-+      }
-+
-+      ix->ei_block = logical;
-+      ix->ei_leaf = ptr;
-+      curp->p_hdr->eh_entries++;
-+
-+      EXT_ASSERT(curp->p_hdr->eh_entries <= curp->p_hdr->eh_max);
-+      EXT_ASSERT(ix <= EXT_LAST_INDEX(curp->p_hdr));
-+
-+      err = ext3_ext_dirty(handle, tree, curp);
-+      ext3_std_error(tree->inode->i_sb, err);
-+
-+      return err;
-+}
-+
-+/*
-+ * routine inserts new subtree into the path, using free index entry
-+ * at depth 'at:
-+ *  - allocates all needed blocks (new leaf and all intermediate index blocks)
-+ *  - makes decision where to split
-+ *  - moves remaining extens and index entries (right to the split point)
-+ *    into the newly allocated blocks
-+ *  - initialize subtree
-+ */
-+static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
-+{
-+      struct buffer_head *bh = NULL;
-+      int depth = EXT_DEPTH(tree);
-+      struct ext3_extent_header *neh;
-+      struct ext3_extent_idx *fidx;
-+      struct ext3_extent *ex;
-+      int i = at, k, m, a;
-+      unsigned long newblock, oldblock, border;
-+      int *ablocks = NULL; /* array of allocated blocks */
-+      int err = 0;
-+
-+      /* make decision: where to split? */
-+      /* FIXME: now desicion is simplest: at current extent */
-+
-+      /* if current leaf will be splitted, then we should use 
-+       * border from split point */
-+      EXT_ASSERT(path[depth].p_ext <= EXT_MAX_EXTENT(path[depth].p_hdr));
-+      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
-+              border = path[depth].p_ext[1].ee_block;
-+              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
-+      } else {
-+              border = newext->ee_block;
-+              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
-+      }
-+
-+      /* 
-+       * if error occurs, then we break processing
-+       * and turn filesystem read-only. so, index won't
-+       * be inserted and tree will be in consistent
-+       * state. next mount will repair buffers too
-+       */
-+
-+      /*
-+       * get array to track all allocated blocks
-+       * we need this to handle errors and free blocks
-+       * upon them
-+       */
-+      ablocks = kmalloc(sizeof(unsigned long) * depth, GFP_NOFS);
-+      if (!ablocks)
-+              return -ENOMEM;
-+      memset(ablocks, 0, sizeof(unsigned long) * depth);
-+
-+      /* allocate all needed blocks */
-+      ext_debug(tree, "allocate %d blocks for indexes/leaf\n", depth - at);
-+      for (a = 0; a < depth - at; a++) {
-+              newblock = ext3_ext_new_block(handle, tree, path, newext, &err);
-+              if (newblock == 0)
-+                      goto cleanup;
-+              ablocks[a] = newblock;
-+      }
-+
-+      /* initialize new leaf */
-+      newblock = ablocks[--a];
-+      EXT_ASSERT(newblock);
-+      bh = sb_getblk(tree->inode->i_sb, newblock);
-+      if (!bh) {
-+              err = -EIO;
-+              goto cleanup;
-+      }
-+      lock_buffer(bh);
-+
-+      if ((err = ext3_journal_get_create_access(handle, bh)))
-+              goto cleanup;
-+
-+      neh = EXT_BLOCK_HDR(bh);
-+      neh->eh_entries = 0;
-+      neh->eh_max = ext3_ext_space_block(tree);
-+      neh->eh_magic = EXT3_EXT_MAGIC;
-+      neh->eh_depth = 0;
-+      ex = EXT_FIRST_EXTENT(neh);
-+
-+      /* move remain of path[depth] to the new leaf */
-+      EXT_ASSERT(path[depth].p_hdr->eh_entries == path[depth].p_hdr->eh_max);
-+      /* start copy from next extent */
-+      /* TODO: we could do it by single memmove */
-+      m = 0;
-+      path[depth].p_ext++;
-+      while (path[depth].p_ext <=
-+                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
-+              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
-+              neh->eh_entries++;
-+              m++;
-+      }
-+      mark_buffer_uptodate(bh, 1);
-+      unlock_buffer(bh);
-+
-+      if ((err = ext3_journal_dirty_metadata(handle, bh)))
-+              goto cleanup;   
-+      brelse(bh);
-+      bh = NULL;
-+
-+      /* correct old leaf */
-+      if (m) {
-+              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
-+                      goto cleanup;
-+              path[depth].p_hdr->eh_entries -= m;
-+              if ((err = ext3_ext_dirty(handle, tree, path + depth)))
-+                      goto cleanup;
-+              
-+      }
-+
-+      /* create intermediate indexes */
-+      k = depth - at - 1;
-+      EXT_ASSERT(k >= 0);
-+      if (k)
-+              ext_debug(tree, "create %d intermediate indices\n", k);
-+      /* insert new index into current index block */
-+      /* current depth stored in i var */
-+      i = depth - 1;
-+      while (k--) {
-+              oldblock = newblock;
-+              newblock = ablocks[--a];
-+              bh = sb_getblk(tree->inode->i_sb, newblock);
-+              if (!bh) {
-+                      err = -EIO;
-+                      goto cleanup;
-+              }
-+              lock_buffer(bh);
-+
-+              if ((err = ext3_journal_get_create_access(handle, bh)))
-+                      goto cleanup;
-+
-+              neh = EXT_BLOCK_HDR(bh);
-+              neh->eh_entries = 1;
-+              neh->eh_magic = EXT3_EXT_MAGIC;
-+              neh->eh_max = ext3_ext_space_block_idx(tree);
-+              neh->eh_depth = depth - i; 
-+              fidx = EXT_FIRST_INDEX(neh);
-+              fidx->ei_block = border;
-+              fidx->ei_leaf = oldblock;
-+
-+              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
-+              /* copy indexes */
-+              m = 0;
-+              path[i].p_idx++;
-+
-+              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
-+              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
-+              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
-+                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
-+                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
-+                      neh->eh_entries++;
-+                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
-+                      m++;
-+              }
-+              mark_buffer_uptodate(bh, 1);
-+              unlock_buffer(bh);
-+
-+              if ((err = ext3_journal_dirty_metadata(handle, bh)))
-+                      goto cleanup;
-+              brelse(bh);
-+              bh = NULL;
-+
-+              /* correct old index */
-+              if (m) {
-+                      err = ext3_ext_get_access(handle, tree, path + i);
-+                      if (err)
-+                              goto cleanup;
-+                      path[i].p_hdr->eh_entries -= m;
-+                      err = ext3_ext_dirty(handle, tree, path + i);
-+                      if (err)
-+                              goto cleanup;
-+              }
-+
-+              i--;
-+      }
-+
-+      /* insert new index */
-+      if (!err)
-+              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
-+
-+cleanup:
-+      if (bh) {
-+              if (buffer_locked(bh))
-+                      unlock_buffer(bh);
-+              brelse(bh);
-+      }
-+
-+      if (err) {
-+              /* free all allocated blocks in error case */
-+              for (i = 0; i < depth; i++) {
-+                      if (!ablocks[i])
-+                              continue;
-+                      ext3_free_blocks(handle, tree->inode, ablocks[i], 1);
-+              }
-+      }
-+      kfree(ablocks);
-+
-+      return err;
-+}
-+
-+/*
-+ * routine implements tree growing procedure:
-+ *  - allocates new block
-+ *  - moves top-level data (index block or leaf) into the new block
-+ *  - initialize new top-level, creating index that points to the
-+ *    just created block
-+ */
-+static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
-+{
-+      struct ext3_ext_path *curp = path;
-+      struct ext3_extent_header *neh;
-+      struct ext3_extent_idx *fidx;
-+      struct buffer_head *bh;
-+      unsigned long newblock;
-+      int err = 0;
-+
-+      newblock = ext3_ext_new_block(handle, tree, path, newext, &err);
-+      if (newblock == 0)
-+              return err;
-+
-+      bh = sb_getblk(tree->inode->i_sb, newblock);
-+      if (!bh) {
-+              err = -EIO;
-+              ext3_std_error(tree->inode->i_sb, err);
-+              return err;
-+      }
-+      lock_buffer(bh);
-+
-+      if ((err = ext3_journal_get_create_access(handle, bh))) {
-+              unlock_buffer(bh);
-+              goto out;       
-+      }
-+
-+      /* move top-level index/leaf into new block */
-+      memmove(bh->b_data, curp->p_hdr, tree->buffer_len);
-+
-+      /* set size of new block */
-+      neh = EXT_BLOCK_HDR(bh);
-+      /* old root could have indexes or leaves
-+       * so calculate eh_max right way */
-+      if (EXT_DEPTH(tree))
-+              neh->eh_max = ext3_ext_space_block_idx(tree);
-+      else
-+              neh->eh_max = ext3_ext_space_block(tree);
-+      neh->eh_magic = EXT3_EXT_MAGIC;
-+      mark_buffer_uptodate(bh, 1);
-+      unlock_buffer(bh);
-+
-+      if ((err = ext3_journal_dirty_metadata(handle, bh)))
-+              goto out;
-+
-+      /* create index in new top-level index: num,max,pointer */
-+      if ((err = ext3_ext_get_access(handle, tree, curp)))
-+              goto out;
-+
-+      curp->p_hdr->eh_magic = EXT3_EXT_MAGIC;
-+      curp->p_hdr->eh_max = ext3_ext_space_root_idx(tree);
-+      curp->p_hdr->eh_entries = 1;
-+      curp->p_idx = EXT_FIRST_INDEX(curp->p_hdr);
-+      /* FIXME: it works, but actually path[0] can be index */
-+      curp->p_idx->ei_block = EXT_FIRST_EXTENT(path[0].p_hdr)->ee_block;
-+      curp->p_idx->ei_leaf = newblock;
-+
-+      neh = EXT_ROOT_HDR(tree);
-+      fidx = EXT_FIRST_INDEX(neh);
-+      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
-+
-+      neh->eh_depth = path->p_depth + 1;
-+      err = ext3_ext_dirty(handle, tree, curp);
-+out:
-+      brelse(bh);
-+
-+      return err;
-+}
-+
-+/*
-+ * routine finds empty index and adds new leaf. if no free index found
-+ * then it requests in-depth growing
-+ */
-+static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
-+{
-+      struct ext3_ext_path *curp;
-+      int depth, i, err = 0;
-+
-+repeat:
-+      i = depth = EXT_DEPTH(tree);
-+      
-+      /* walk up to the tree and look for free index entry */
-+      curp = path + depth;
-+      while (i > 0 && !EXT_HAS_FREE_INDEX(curp)) {
-+              i--;
-+              curp--;
-+      }
-+
-+      /* we use already allocated block for index block
-+       * so, subsequent data blocks should be contigoues */
-+      if (EXT_HAS_FREE_INDEX(curp)) {
-+              /* if we found index with free entry, then use that
-+               * entry: create all needed subtree and add new leaf */
-+              err = ext3_ext_split(handle, tree, path, newext, i);
-+
-+              /* refill path */
-+              ext3_ext_drop_refs(path);
-+              path = ext3_ext_find_extent(tree, newext->ee_block, path);
-+              if (IS_ERR(path))
-+                      err = PTR_ERR(path);
-+      } else {
-+              /* tree is full, time to grow in depth */
-+              err = ext3_ext_grow_indepth(handle, tree, path, newext);
-+
-+              /* refill path */
-+              ext3_ext_drop_refs(path);
-+              path = ext3_ext_find_extent(tree, newext->ee_block, path);
-+              if (IS_ERR(path))
-+                      err = PTR_ERR(path);
-+
-+              /*
-+               * only first (depth 0 -> 1) produces free space
-+               * in all other cases we have to split growed tree
-+               */
-+              depth = EXT_DEPTH(tree);
-+              if (path[depth].p_hdr->eh_entries == path[depth].p_hdr->eh_max) {
-+                      /* now we need split */
-+                      goto repeat;
-+              }
-+      }
-+
-+      if (err)
-+              return err;
-+
-+      return 0;
-+}
-+
-+/*
-+ * returns allocated block in subsequent extent or EXT_MAX_BLOCK
-+ * NOTE: it consider block number from index entry as
-+ * allocated block. thus, index entries have to be consistent
-+ * with leafs
-+ */
-+static unsigned long
-+ext3_ext_next_allocated_block(struct ext3_ext_path *path)
-+{
-+      int depth;
-+
-+      EXT_ASSERT(path != NULL);
-+      depth = path->p_depth;
-+
-+      if (depth == 0 && path->p_ext == NULL)
-+              return EXT_MAX_BLOCK;
-+
-+      /* FIXME: what if index isn't full ?! */
-+      while (depth >= 0) {
-+              if (depth == path->p_depth) {
-+                      /* leaf */
-+                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
-+                              return path[depth].p_ext[1].ee_block;
-+              } else {
-+                      /* index */
-+                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
-+                              return path[depth].p_idx[1].ei_block;
-+              }
-+              depth--;        
-+      }
-+
-+      return EXT_MAX_BLOCK;
-+}
-+
-+/*
-+ * returns first allocated block from next leaf or EXT_MAX_BLOCK
-+ */
-+static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
-+{
-+      int depth;
-+
-+      EXT_ASSERT(path != NULL);
-+      depth = path->p_depth;
-+
-+      /* zero-tree has no leaf blocks at all */
-+      if (depth == 0)
-+              return EXT_MAX_BLOCK;
-+
-+      /* go to index block */
-+      depth--;
-+      
-+      while (depth >= 0) {
-+              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
-+                      return path[depth].p_idx[1].ei_block;
-+              depth--;        
-+      }
-+
-+      return EXT_MAX_BLOCK;
-+}
-+
-+/*
-+ * if leaf gets modified and modified extent is first in the leaf
-+ * then we have to correct all indexes above
-+ * TODO: do we need to correct tree in all cases?
-+ */
-+int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
-+{
-+      struct ext3_extent_header *eh;
-+      int depth = EXT_DEPTH(tree);    
-+      struct ext3_extent *ex;
-+      unsigned long border;
-+      int k, err = 0;
-+      
-+      eh = path[depth].p_hdr;
-+      ex = path[depth].p_ext;
-+      EXT_ASSERT(ex);
-+      EXT_ASSERT(eh);
-+      
-+      if (depth == 0) {
-+              /* there is no tree at all */
-+              return 0;
-+      }
-+      
-+      if (ex != EXT_FIRST_EXTENT(eh)) {
-+              /* we correct tree if first leaf got modified only */
-+              return 0;
-+      }
-+      
-+      /*
-+       * TODO: we need correction if border is smaller then current one
-+       */
-+      k = depth - 1;
-+      border = path[depth].p_ext->ee_block;
-+      if ((err = ext3_ext_get_access(handle, tree, path + k)))
-+              return err;
-+      path[k].p_idx->ei_block = border;
-+      if ((err = ext3_ext_dirty(handle, tree, path + k)))
-+              return err;
-+
-+      while (k--) {
-+              /* change all left-side indexes */
-+              if (path[k+1].p_idx != EXT_FIRST_INDEX(path[k+1].p_hdr))
-+                      break;
-+              if ((err = ext3_ext_get_access(handle, tree, path + k)))
-+                      break;
-+              path[k].p_idx->ei_block = border;
-+              if ((err = ext3_ext_dirty(handle, tree, path + k)))
-+                      break;
-+      }
-+
-+      return err;
-+}
-+
-+static int inline
-+ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
-+{
-+      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
-+              return 0;
-+
-+#ifdef AGRESSIVE_TEST
-+      if (ex1->ee_len >= 4)
-+              return 0;
-+#endif
-+
-+      if (!tree->ops->mergable)
-+              return 1;
-+
-+      return tree->ops->mergable(ex1, ex2);
-+}
-+
-+/*
-+ * this routine tries to merge requsted extent into the existing
-+ * extent or inserts requested extent as new one into the tree,
-+ * creating new leaf in no-space case
-+ */
-+int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
-+{
-+      struct ext3_extent_header * eh;
-+      struct ext3_extent *ex, *fex;
-+      struct ext3_extent *nearex; /* nearest extent */
-+      struct ext3_ext_path *npath = NULL;
-+      int depth, len, err, next;
-+
-+      EXT_ASSERT(newext->ee_len > 0);
-+      EXT_ASSERT(newext->ee_len < EXT_CACHE_MARK);
-+      depth = EXT_DEPTH(tree);
-+      ex = path[depth].p_ext;
-+      EXT_ASSERT(path[depth].p_hdr);
-+
-+      /* try to insert block into found extent and return */
-+      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
-+              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
-+              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
-+                      return err;
-+              ex->ee_len += newext->ee_len;
-+              eh = path[depth].p_hdr;
-+              nearex = ex;
-+              goto merge;
-+      }
-+
-+repeat:
-+      depth = EXT_DEPTH(tree);
-+      eh = path[depth].p_hdr;
-+      if (eh->eh_entries < eh->eh_max)
-+              goto has_space;
-+
-+      /* probably next leaf has space for us? */
-+      fex = EXT_LAST_EXTENT(eh);
-+      next = ext3_ext_next_leaf_block(tree, path);
-+      if (newext->ee_block > fex->ee_block && next != EXT_MAX_BLOCK) {
-+              ext_debug(tree, "next leaf block - %d\n", next);
-+              EXT_ASSERT(!npath);
-+              npath = ext3_ext_find_extent(tree, next, NULL);
-+              if (IS_ERR(npath))
-+                      return PTR_ERR(npath);
-+              EXT_ASSERT(npath->p_depth == path->p_depth);
-+              eh = npath[depth].p_hdr;
-+              if (eh->eh_entries < eh->eh_max) {
-+                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
-+                      path = npath;
-+                      goto repeat;
-+              }
-+              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
-+      }
-+
-+      /*
-+       * there is no free space in found leaf
-+       * we're gonna add new leaf in the tree
-+       */
-+      err = ext3_ext_create_new_leaf(handle, tree, path, newext);
-+      if (err)
-+              goto cleanup;
-+      depth = EXT_DEPTH(tree);
-+      eh = path[depth].p_hdr;
-+
-+has_space:
-+      nearex = path[depth].p_ext;
-+
-+      if ((err = ext3_ext_get_access(handle, tree, path + depth)))
-+              goto cleanup;
-+
-+      if (!nearex) {
-+              /* there is no extent in this leaf, create first one */
-+              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
-+              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
-+      } else if (newext->ee_block > nearex->ee_block) {
-+              EXT_ASSERT(newext->ee_block != nearex->ee_block);
-+              if (nearex != EXT_LAST_EXTENT(eh)) {
-+                      len = EXT_MAX_EXTENT(eh) - nearex;
-+                      len = (len - 1) * sizeof(struct ext3_extent);
-+                      len = len < 0 ? 0 : len;
-+                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
-+                      memmove(nearex + 2, nearex + 1, len);
-+              }
-+              path[depth].p_ext = nearex + 1;
-+      } else {
-+              EXT_ASSERT(newext->ee_block != nearex->ee_block);
-+              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
-+              len = len < 0 ? 0 : len;
-+              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
-+              memmove(nearex + 1, nearex, len);
-+              path[depth].p_ext = nearex;
-+      }
-+
-+      eh->eh_entries++;
-+      nearex = path[depth].p_ext;
-+      nearex->ee_block = newext->ee_block;
-+      nearex->ee_start = newext->ee_start;
-+      nearex->ee_len = newext->ee_len;
-+      /* FIXME: support for large fs */
-+      nearex->ee_start_hi = 0;
-+
-+merge:
-+      /* try to merge extents to the right */
-+      while (nearex < EXT_LAST_EXTENT(eh)) {
-+              if (!ext3_can_extents_be_merged(tree, nearex, nearex + 1))
-+                      break;
-+              /* merge with next extent! */
-+              nearex->ee_len += nearex[1].ee_len;
-+              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
-+                      memmove(nearex + 1, nearex + 2, len);
-+              }
-+              eh->eh_entries--;
-+              EXT_ASSERT(eh->eh_entries > 0);
-+      }
-+
-+      /* try to merge extents to the left */
-+
-+      /* time to correct all indexes above */
-+      err = ext3_ext_correct_indexes(handle, tree, path);
-+      if (err)
-+              goto cleanup;
-+
-+      err = ext3_ext_dirty(handle, tree, path + depth);
-+
-+cleanup:
-+      if (npath) {
-+              ext3_ext_drop_refs(npath);
-+              kfree(npath);
-+      }
-+      ext3_ext_tree_changed(tree);
-+      ext3_ext_invalidate_cache(tree);
-+      return err;
-+}
-+
-+int ext3_ext_walk_space(struct ext3_extents_tree *tree, unsigned long block,
-+                      unsigned long num, ext_prepare_callback func)
-+{
-+      struct ext3_ext_path *path = NULL;
-+      struct ext3_extent *ex, cbex;
-+      unsigned long next, start = 0, end = 0;
-+      unsigned long last = block + num;
-+      int depth, exists, err = 0;
-+
-+      EXT_ASSERT(tree);
-+      EXT_ASSERT(func);
-+      EXT_ASSERT(tree->inode);
-+      EXT_ASSERT(tree->root);
-+
-+      while (block < last && block != EXT_MAX_BLOCK) {
-+              num = last - block;
-+              /* find extent for this block */
-+              path = ext3_ext_find_extent(tree, block, path);
-+              if (IS_ERR(path)) {
-+                      err = PTR_ERR(path);
-+                      path = NULL;
-+                      break;
-+              }
-+
-+              depth = EXT_DEPTH(tree);
-+              EXT_ASSERT(path[depth].p_hdr);
-+              ex = path[depth].p_ext;
-+              next = ext3_ext_next_allocated_block(path);
-+
-+              exists = 0;
-+              if (!ex) {
-+                      /* there is no extent yet, so try to allocate
-+                       * all requested space */
-+                      start = block;
-+                      end = block + num;
-+              } else if (ex->ee_block > block) {
-+                      /* need to allocate space before found extent */
-+                      start = block;
-+                      end = ex->ee_block;
-+                      if (block + num < end)
-+                              end = block + num;
-+              } else if (block >= ex->ee_block + ex->ee_len) {
-+                      /* need to allocate space after found extent */
-+                      start = block;
-+                      end = block + num;
-+                      if (end >= next)
-+                              end = next;
-+              } else if (block >= ex->ee_block) {
-+                      /* 
-+                       * some part of requested space is covered
-+                       * by found extent
-+                       */
-+                      start = block;
-+                      end = ex->ee_block + ex->ee_len;
-+                      if (block + num < end)
-+                              end = block + num;
-+                      exists = 1;
-+              } else {
-+                      BUG();
-+              }
-+              EXT_ASSERT(end > start);
-+
-+              if (!exists) {
-+                      cbex.ee_block = start;
-+                      cbex.ee_len = end - start;
-+                      cbex.ee_start = 0;
-+              } else
-+                      cbex = *ex;
-+
-+              EXT_ASSERT(path[depth].p_hdr);
-+              err = func(tree, path, &cbex, exists);
-+              ext3_ext_drop_refs(path);
-+
-+              if (err < 0)
-+                      break;
-+              if (err == EXT_REPEAT)
-+                      continue;
-+              else if (err == EXT_BREAK) {
-+                      err = 0;
-+                      break;
-+              }
-+
-+              if (EXT_DEPTH(tree) != depth) {
-+                      /* depth was changed. we have to realloc path */
-+                      kfree(path);
-+                      path = NULL;
-+              }
-+
-+              block = cbex.ee_block + cbex.ee_len;
-+      }
-+
-+      if (path) {
-+              ext3_ext_drop_refs(path);
-+              kfree(path);
-+      }
-+
-+      return err;
-+}
-+
-+static inline void
-+ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
-+{
-+      EXT_ASSERT(len > 0);
-+      if (tree->cex) {
-+              tree->cex->ec_type = type;
-+              tree->cex->ec_block = block;
-+              tree->cex->ec_len = len;
-+              tree->cex->ec_start = start;
-+      }
-+}
-+
-+/*
-+ * this routine calculate boundaries of the gap requested block fits into
-+ * and cache this gap
-+ */
-+static inline void
-+ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
-+{
-+      int depth = EXT_DEPTH(tree);
-+      unsigned long lblock, len;
-+      struct ext3_extent *ex;
-+
-+      if (!tree->cex)
-+              return;
-+
-+      ex = path[depth].p_ext;
-+      if (ex == NULL) {
-+              /* there is no extent yet, so gap is [0;-] */
-+              lblock = 0;
-+              len = EXT_MAX_BLOCK;
-+              ext_debug(tree, "cache gap(whole file):");
-+      } else if (block < ex->ee_block) {
-+              lblock = block;
-+              len = ex->ee_block - block;
-+              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
-+      } else if (block >= ex->ee_block + ex->ee_len) {
-+              lblock = ex->ee_block + ex->ee_len;
-+              len = ext3_ext_next_allocated_block(path);
-+              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
-+              EXT_ASSERT(len > lblock);
-+              len = len - lblock;
-+      } else {
-+              lblock = len = 0;
-+              BUG();
-+      }
-+
-+      ext_debug(tree, " -> %lu:%lu\n", (unsigned long) lblock, len);
-+      ext3_ext_put_in_cache(tree, lblock, len, 0, EXT3_EXT_CACHE_GAP);
-+}
-+
-+static inline int
-+ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
-+{
-+      struct ext3_ext_cache *cex = tree->cex;
-+
-+      /* is there cache storage at all? */
-+      if (!cex)
-+              return EXT3_EXT_CACHE_NO;
-+
-+      /* has cache valid data? */
-+      if (cex->ec_type == EXT3_EXT_CACHE_NO)
-+              return EXT3_EXT_CACHE_NO;
-+
-+      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
-+      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
-+              ex->ee_block = cex->ec_block;
-+              ex->ee_start = cex->ec_start;
-+              ex->ee_len = cex->ec_len;
-+              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
-+              return cex->ec_type;
-+      }
-+
-+      /* not in cache */
-+      return EXT3_EXT_CACHE_NO;
-+}
-+
-+/*
-+ * routine removes index from the index block
-+ * it's used in truncate case only. thus all requests are for
-+ * last index in the block only
-+ */
-+int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
-+{
-+      struct buffer_head *bh;
-+      int err;
-+      
-+      /* free index block */
-+      path--;
-+      EXT_ASSERT(path->p_hdr->eh_entries);
-+      if ((err = ext3_ext_get_access(handle, tree, path)))
-+              return err;
-+      path->p_hdr->eh_entries--;
-+      if ((err = ext3_ext_dirty(handle, tree, path)))
-+              return err;
-+      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
-+      bh = sb_get_hash_table(tree->inode->i_sb, path->p_idx->ei_leaf);
-+      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
-+      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
-+      return err;
-+}
-+
-+int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
-+{
-+      int depth = EXT_DEPTH(tree);
-+      int needed;
-+
-+      if (path) {
-+              /* probably there is space in leaf? */
-+              if (path[depth].p_hdr->eh_entries < path[depth].p_hdr->eh_max)
-+                      return 1;
-+      }
-+      
-+      /*
-+       * the worste case we're expecting is creation of the
-+       * new root (growing in depth) with index splitting
-+       * for splitting we have to consider depth + 1 because
-+       * previous growing could increase it
-+       */
-+      depth = depth + 1;
-+
-+      /* 
-+       * growing in depth:
-+       * block allocation + new root + old root
-+       */
-+      needed = EXT3_ALLOC_NEEDED + 2;
-+
-+      /* index split. we may need:
-+       *   allocate intermediate indexes and new leaf
-+       *   change two blocks at each level, but root
-+       *   modify root block (inode)
-+       */
-+      needed += (depth * EXT3_ALLOC_NEEDED) + (2 * depth) + 1;
-+
-+      return needed;
-+}
-+
-+static int
-+ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
-+{
-+      struct ext3_extent *ex, tex;
-+      struct ext3_ext_path *npath;
-+      int depth, creds, err;
-+
-+      depth = EXT_DEPTH(tree);
-+      ex = path[depth].p_ext;
-+      EXT_ASSERT(ex);
-+      EXT_ASSERT(end < ex->ee_block + ex->ee_len - 1);
-+      EXT_ASSERT(ex->ee_block < start);
-+
-+      /* calculate tail extent */
-+      tex.ee_block = end + 1;
-+      EXT_ASSERT(tex.ee_block < ex->ee_block + ex->ee_len);
-+      tex.ee_len = ex->ee_block + ex->ee_len - tex.ee_block;
-+
-+      creds = ext3_ext_calc_credits_for_insert(tree, path);
-+      handle = ext3_ext_journal_restart(handle, creds);
-+      if (IS_ERR(handle))
-+              return PTR_ERR(handle);
-+      
-+      /* calculate head extent. use primary extent */
-+      err = ext3_ext_get_access(handle, tree, path + depth);
-+      if (err)
-+              return err;
-+      ex->ee_len = start - ex->ee_block;
-+      err = ext3_ext_dirty(handle, tree, path + depth);
-+      if (err)
-+              return err;
-+
-+      /* FIXME: some callback to free underlying resource
-+       * and correct ee_start? */
-+      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
-+
-+      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
-+      if (IS_ERR(npath))
-+              return PTR_ERR(npath);
-+      depth = EXT_DEPTH(tree);
-+      EXT_ASSERT(npath[depth].p_ext->ee_block == ex->ee_block);
-+      EXT_ASSERT(npath[depth].p_ext->ee_len == ex->ee_len);
-+
-+      err = ext3_ext_insert_extent(handle, tree, npath, &tex);
-+      ext3_ext_drop_refs(npath);
-+      kfree(npath);
-+
-+      return err;
-+                      
-+}
-+
-+static int
-+ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
-+{
-+      struct ext3_extent *ex, *fu = NULL, *lu, *le;
-+      int err = 0, correct_index = 0;
-+      int depth = EXT_DEPTH(tree), credits;
-+      struct ext3_extent_header *eh;
-+      unsigned a, b, block, num;
-+
-+      ext_debug(tree, "remove [%lu:%lu] in leaf\n", start, end);
-+      if (!path[depth].p_hdr)
-+              path[depth].p_hdr = EXT_BLOCK_HDR(path[depth].p_bh);
-+      eh = path[depth].p_hdr;
-+      EXT_ASSERT(eh);
-+      EXT_ASSERT(eh->eh_entries <= eh->eh_max);
-+      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      
-+      /* find where to start removing */
-+      le = ex = EXT_LAST_EXTENT(eh);
-+      while (ex != EXT_FIRST_EXTENT(eh)) {
-+              if (ex->ee_block <= end)
-+                      break;
-+              ex--;
-+      }
-+
-+      if (start > ex->ee_block && end < ex->ee_block + ex->ee_len - 1) {
-+              /* removal of internal part of the extent requested
-+               * tail and head must be placed in different extent
-+               * so, we have to insert one more extent */
-+              path[depth].p_ext = ex;
-+              return ext3_ext_split_for_rm(handle, tree, path, start, end);
-+      }
-+      
-+      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
-+              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
-+              path[depth].p_ext = ex;
-+      
-+              a = ex->ee_block > start ? ex->ee_block : start;
-+              b = ex->ee_block + ex->ee_len - 1 < end ?
-+                      ex->ee_block + ex->ee_len - 1 : end;
-+              
-+              ext_debug(tree, "  border %u:%u\n", a, b);
-+
-+              if (a != ex->ee_block && b != ex->ee_block + ex->ee_len - 1) {
-+                      block = 0;
-+                      num = 0;
-+                      BUG();
-+              } else if (a != ex->ee_block) {
-+                      /* remove tail of the extent */
-+                      block = ex->ee_block;
-+                      num = a - block;
-+              } else if (b != ex->ee_block + ex->ee_len - 1) {
-+                      /* remove head of the extent */
-+                      block = a;
-+                      num = b - a;
-+              } else {
-+                      /* remove whole extent: excelent! */
-+                      block = ex->ee_block; 
-+                      num = 0;
-+                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
-+              }
-+
-+              if (ex == EXT_FIRST_EXTENT(eh))
-+                      correct_index = 1;
-+
-+              credits = 1;
-+              if (correct_index)
-+                      credits += (EXT_DEPTH(tree) * EXT3_ALLOC_NEEDED) + 1;
-+              if (tree->ops->remove_extent_credits)
-+                      credits+=tree->ops->remove_extent_credits(tree,ex,a,b);
-+              
-+              handle = ext3_ext_journal_restart(handle, credits);
-+              if (IS_ERR(handle)) {
-+                      err = PTR_ERR(handle);
-+                      goto out;
-+              }
-+
-+              err = ext3_ext_get_access(handle, tree, path + depth);
-+              if (err)
-+                      goto out;
-+
-+              if (tree->ops->remove_extent)
-+                      err = tree->ops->remove_extent(tree, ex, a, b);
-+              if (err)
-+                      goto out;
-+
-+              if (num == 0) {
-+                      /* this extent is removed entirely mark slot unused */
-+                      ex->ee_start = 0;
-+                      eh->eh_entries--;
-+                      fu = ex;
-+              }
-+
-+              ex->ee_block = block;
-+              ex->ee_len = num;
-+
-+              err = ext3_ext_dirty(handle, tree, path + depth);
-+              if (err)
-+                      goto out;
-+
-+              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
-+              ex--;
-+      }
-+
-+      if (fu) {
-+              /* reuse unused slots */
-+              while (lu < le) {
-+                      if (lu->ee_start) {
-+                              *fu = *lu;
-+                              lu->ee_start = 0;
-+                              fu++;
-+                      }
-+                      lu++;
-+              }
-+      }
-+
-+      if (correct_index && eh->eh_entries)
-+              err = ext3_ext_correct_indexes(handle, tree, path);
-+
-+      /* if this leaf is free, then we should
-+       * remove it from index block above */
-+      if (err == 0 && eh->eh_entries == 0 && path[depth].p_bh != NULL)
-+              err = ext3_ext_rm_idx(handle, tree, path + depth);
-+
-+out:
-+      return err;
-+}
-+
-+
-+static struct ext3_extent_idx *
-+ext3_ext_last_covered(struct ext3_extent_header *hdr, unsigned long block)
-+{
-+      struct ext3_extent_idx *ix;
-+      
-+      ix = EXT_LAST_INDEX(hdr);
-+      while (ix != EXT_FIRST_INDEX(hdr)) {
-+              if (ix->ei_block <= block)
-+                      break;
-+              ix--;
-+      }
-+      return ix;
-+}
-+
-+/*
-+ * returns 1 if current index have to be freed (even partial)
-+ */
-+static int inline
-+ext3_ext_more_to_rm(struct ext3_ext_path *path)
-+{
-+      EXT_ASSERT(path->p_idx);
-+
-+      if (path->p_idx < EXT_FIRST_INDEX(path->p_hdr))
-+              return 0;
-+
-+      /*
-+       * if truncate on deeper level happened it it wasn't partial
-+       * so we have to consider current index for truncation
-+       */
-+      if (path->p_hdr->eh_entries == path->p_block)
-+              return 0;
-+      return 1;
-+}
-+
-+int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
-+{
-+      struct inode *inode = tree->inode;
-+      struct super_block *sb = inode->i_sb;
-+      int depth = EXT_DEPTH(tree);
-+      struct ext3_ext_path *path;
-+      handle_t *handle;
-+      int i = 0, err = 0;
-+
-+      ext_debug(tree, "space to be removed: %lu:%lu\n", start, end);
-+
-+      /* probably first extent we're gonna free will be last in block */
-+      handle = ext3_journal_start(inode, depth + 1);
-+      if (IS_ERR(handle))
-+              return PTR_ERR(handle);
-+
-+      ext3_ext_invalidate_cache(tree);
-+
-+      /*
-+       * we start scanning from right side freeing all the blocks
-+       * after i_size and walking into the deep
-+       */
-+      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
-+      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
-+              ext3_journal_stop(handle, inode);
-+              return -ENOMEM;
-+      }
-+      memset(path, 0, sizeof(struct ext3_ext_path) * (depth + 1));
-+      path[i].p_hdr = EXT_ROOT_HDR(tree);
-+      
-+      while (i >= 0 && err == 0) {
-+              if (i == depth) {
-+                      /* this is leaf block */
-+                      err = ext3_ext_rm_leaf(handle, tree, path, start, end);
-+                      /* root level have p_bh == NULL, brelse() eats this */
-+                      brelse(path[i].p_bh);
-+                      i--;
-+                      continue;
-+              }
-+              
-+              /* this is index block */
-+              if (!path[i].p_hdr) {
-+                      ext_debug(tree, "initialize header\n");
-+                      path[i].p_hdr = EXT_BLOCK_HDR(path[i].p_bh);
-+              }
-+
-+              EXT_ASSERT(path[i].p_hdr->eh_entries <= path[i].p_hdr->eh_max);
-+              EXT_ASSERT(path[i].p_hdr->eh_magic == EXT3_EXT_MAGIC);
-+              
-+              if (!path[i].p_idx) {
-+                      /* this level hasn't touched yet */
-+                      path[i].p_idx =
-+                              ext3_ext_last_covered(path[i].p_hdr, end);
-+                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
-+                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
-+              } else {
-+                      /* we've already was here, see at next index */
-+                      path[i].p_idx--;
-+              }
-+
-+              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
-+              if (ext3_ext_more_to_rm(path + i)) {
-+                      /* go to the next level */
-+                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
-+                      memset(path + i + 1, 0, sizeof(*path));
-+                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
-+                      if (!path[i+1].p_bh) {
-+                              /* should we reset i_size? */
-+                              err = -EIO;
-+                              break;
-+                      }
-+                      /* put actual number of indexes to know is this
-+                       * number got changed at the next iteration */
-+                      path[i].p_block = path[i].p_hdr->eh_entries;
-+                      i++;
-+              } else {
-+                      /* we finish processing this index, go up */
-+                      if (path[i].p_hdr->eh_entries == 0 && i > 0) {
-+                              /* index is empty, remove it
-+                               * handle must be already prepared by the
-+                               * truncatei_leaf() */
-+                              err = ext3_ext_rm_idx(handle, tree, path + i);
-+                      }
-+                      /* root level have p_bh == NULL, brelse() eats this */
-+                      brelse(path[i].p_bh);
-+                      i--;
-+                      ext_debug(tree, "return to level %d\n", i);
-+              }
-+      }
-+
-+      /* TODO: flexible tree reduction should be here */
-+      if (path->p_hdr->eh_entries == 0) {
-+              /*
-+               * truncate to zero freed all the tree
-+               * so, we need to correct eh_depth
-+               */
-+              err = ext3_ext_get_access(handle, tree, path);
-+              if (err == 0) {
-+                      EXT_ROOT_HDR(tree)->eh_depth = 0;
-+                      EXT_ROOT_HDR(tree)->eh_max = ext3_ext_space_root(tree);
-+                      err = ext3_ext_dirty(handle, tree, path);
-+              }
-+      }
-+      ext3_ext_tree_changed(tree);
-+
-+      kfree(path);
-+      ext3_journal_stop(handle, inode);
-+
-+      return err;
-+}
-+
-+/*
-+ * called at mount time
-+ */
-+void ext3_ext_init(struct super_block *sb)
-+{
-+      /*
-+       * possible initialization would be here
-+       */
-+
-+      if (test_opt(sb, EXTENTS)) {
-+              printk("EXT3-fs: file extents enabled");
-+#ifdef AGRESSIVE_TEST
-+              printk(", agressive tests");
-+#endif
-+#ifdef CHECK_BINSEARCH
-+              printk(", check binsearch");
-+#endif
-+              printk("\n");
-+      }
-+}
-+
-+/*
-+ * called at umount time
-+ */
-+void ext3_ext_release(struct super_block *sb)
-+{
-+}
-+
-+/************************************************************************
-+ * VFS related routines
-+ ************************************************************************/
-+
-+static int ext3_get_inode_write_access(handle_t *handle, void *buffer)
-+{
-+      /* we use in-core data, not bh */
-+      return 0;
-+}
-+
-+static int ext3_mark_buffer_dirty(handle_t *handle, void *buffer)
-+{
-+      struct inode *inode = buffer;
-+      return ext3_mark_inode_dirty(handle, inode);
-+}
-+
-+static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
-+{
-+      /* FIXME: support for large fs */
-+      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
-+              return 1;
-+      return 0;
-+}
-+
-+static int
-+ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
-+{
-+      int needed;
-+      
-+      /* at present, extent can't cross block group */;
-+      needed = 4; /* bitmap + group desc + sb + inode */
-+
-+#ifdef CONFIG_QUOTA
-+      needed += 2 * EXT3_SINGLEDATA_TRANS_BLOCKS;
-+#endif
-+      return needed;
-+}
-+
-+static int
-+ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
-+{
-+      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
-+      handle_t *handle = ext3_journal_start(tree->inode, needed);
-+      struct buffer_head *bh;
-+      int i;
-+
-+      if (IS_ERR(handle))
-+              return PTR_ERR(handle);
-+      if (from >= ex->ee_block && to == ex->ee_block + ex->ee_len - 1) {
-+              /* tail removal */
-+              unsigned long num, start;
-+              num = ex->ee_block + ex->ee_len - from;
-+              start = ex->ee_start + ex->ee_len - num;
-+              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
-+              for (i = 0; i < num; i++) {
-+                      bh = sb_get_hash_table(tree->inode->i_sb, start + i);
-+                      ext3_forget(handle, 0, tree->inode, bh, start + i);
-+              }
-+              ext3_free_blocks(handle, tree->inode, start, num);
-+      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
-+              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
-+      } else {
-+              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
-+      }
-+      ext3_journal_stop(handle, tree->inode);
-+      return 0;
-+}
-+
-+int ext3_ext_find_goal(struct inode *inode, struct ext3_ext_path *path,
-+                      unsigned long block)
-+{
-+      struct ext3_inode_info *ei = EXT3_I(inode);
-+      unsigned long bg_start;
-+      unsigned long colour;
-+      int depth;
-+      
-+      if (path) {
-+              struct ext3_extent *ex;
-+              depth = path->p_depth;
-+              
-+              /* try to predict block placement */
-+              if ((ex = path[depth].p_ext))
-+                      return ex->ee_start + (block - ex->ee_block);
-+
-+              /* it looks index is empty
-+               * try to find starting from index itself */
-+              if (path[depth].p_bh)
-+                      return path[depth].p_bh->b_blocknr;
-+      }
-+
-+      /* OK. use inode's group */
-+      bg_start = (ei->i_block_group * EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
-+              le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
-+      colour = (current->pid % 16) *
-+                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
-+      return bg_start + colour + block;
-+}
-+
-+static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
-+{
-+      struct inode *inode = tree->inode;
-+      int newblock, goal;
-+      
-+      EXT_ASSERT(path);
-+      EXT_ASSERT(ex);
-+      EXT_ASSERT(ex->ee_start);
-+      EXT_ASSERT(ex->ee_len);
-+      
-+      /* reuse block from the extent to order data/metadata */
-+      newblock = ex->ee_start++;
-+      ex->ee_len--;
-+      if (ex->ee_len == 0) {
-+              ex->ee_len = 1;
-+              /* allocate new block for the extent */
-+              goal = ext3_ext_find_goal(inode, path, ex->ee_block);
-+              ex->ee_start = ext3_new_block(handle, inode, goal, 0, 0, err);
-+              if (ex->ee_start == 0) {
-+                      /* error occured: restore old extent */
-+                      ex->ee_start = newblock;
-+                      return 0;
-+              }
-+      }
-+      return newblock;
-+}
-+
-+static struct ext3_extents_helpers ext3_blockmap_helpers = {
-+      .get_write_access       = ext3_get_inode_write_access,
-+      .mark_buffer_dirty      = ext3_mark_buffer_dirty,
-+      .mergable               = ext3_ext_mergable,
-+      .new_block              = ext3_new_block_cb,
-+      .remove_extent          = ext3_remove_blocks,
-+      .remove_extent_credits  = ext3_remove_blocks_credits,
-+};
-+
-+void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
-+{
-+      tree->inode = inode;
-+      tree->root = (void *) EXT3_I(inode)->i_data;
-+      tree->buffer = (void *) inode;
-+      tree->buffer_len = sizeof(EXT3_I(inode)->i_data);
-+      tree->cex = (struct ext3_ext_cache *) &EXT3_I(inode)->i_cached_extent;
-+      tree->ops = &ext3_blockmap_helpers;
-+}
-+
-+int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result, int create)
-+{
-+      struct ext3_ext_path *path = NULL;
-+      struct ext3_extent newex;
-+      struct ext3_extent *ex;
-+      int goal, newblock, err = 0, depth;
-+      struct ext3_extents_tree tree;
-+
-+      clear_bit(BH_New, &bh_result->b_state);
-+      ext3_init_tree_desc(&tree, inode);
-+      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
-+      down_write(&EXT3_I(inode)->truncate_sem);
-+
-+      /* check in cache */
-+      if ((goal = ext3_ext_in_cache(&tree, iblock, &newex))) {
-+              if (goal == EXT3_EXT_CACHE_GAP) {
-+                      if (!create) {
-+                              /* block isn't allocated yet and
-+                               * user don't want to allocate it */
-+                              goto out2;
-+                      }
-+                      /* we should allocate requested block */
-+              } else if (goal == EXT3_EXT_CACHE_EXTENT) {
-+                      /* block is already allocated */
-+                      newblock = iblock - newex.ee_block + newex.ee_start;
-+                      goto out;
-+              } else {
-+                      EXT_ASSERT(0);
-+              }
-+      }
-+
-+      /* find extent for this block */
-+      path = ext3_ext_find_extent(&tree, iblock, NULL);
-+      if (IS_ERR(path)) {
-+              err = PTR_ERR(path);
-+              path = NULL;
-+              goto out2;
-+      }
-+
-+      depth = EXT_DEPTH(&tree);
-+
-+      /*
-+       * consistent leaf must not be empty
-+       * this situations is possible, though, _during_ tree modification
-+       * this is why assert can't be put in ext3_ext_find_extent()
-+       */
-+      EXT_ASSERT(path[depth].p_ext != NULL || depth == 0);
-+
-+      if ((ex = path[depth].p_ext)) {
-+              /* if found exent covers block, simple return it */
-+              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
-+                      newblock = iblock - ex->ee_block + ex->ee_start;
-+                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
-+                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
-+                      goto out;
-+              }
-+      }
-+
-+      /*
-+       * requested block isn't allocated yet
-+       * we couldn't try to create block if create flag is zero 
-+       */
-+      if (!create) {
-+              /* put just found gap into cache to speedup subsequest reqs */
-+              ext3_ext_put_gap_in_cache(&tree, path, iblock);
-+              goto out2;
-+      }
-+
-+      /* allocate new block */
-+      goal = ext3_ext_find_goal(inode, path, iblock);
-+      newblock = ext3_new_block(handle, inode, goal, 0, 0, &err);
-+      if (!newblock)
-+              goto out2;
-+      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
-+
-+      /* try to insert new extent into found leaf and return */
-+      newex.ee_block = iblock;
-+      newex.ee_start = newblock;
-+      newex.ee_len = 1;
-+      err = ext3_ext_insert_extent(handle, &tree, path, &newex);
-+      if (err)
-+              goto out2;
-+      
-+      if (inode->i_size > EXT3_I(inode)->i_disksize)
-+              EXT3_I(inode)->i_disksize = inode->i_size;
-+
-+      /* previous routine could use block we allocated */
-+      newblock = newex.ee_start;
-+      set_bit(BH_New, &bh_result->b_state);
-+
-+      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
-+out:
-+      ext3_ext_show_leaf(&tree, path);
-+      set_bit(BH_Mapped, &bh_result->b_state);
-+      bh_result->b_dev = inode->i_sb->s_dev;
-+      bh_result->b_blocknr = newblock;
-+out2:
-+      if (path) {
-+              ext3_ext_drop_refs(path);
-+              kfree(path);
-+      }
-+      up_write(&EXT3_I(inode)->truncate_sem);
-+
-+      return err;     
-+}
-+
-+void ext3_ext_truncate(struct inode * inode)
-+{
-+      struct address_space *mapping = inode->i_mapping;
-+      struct super_block *sb = inode->i_sb;
-+      struct ext3_extents_tree tree;
-+      unsigned long last_block;
-+      handle_t *handle;
-+      int err = 0;
-+
-+      ext3_init_tree_desc(&tree, inode);
-+
-+      /*
-+       * probably first extent we're gonna free will be last in block
-+       */
-+      err = ext3_writepage_trans_blocks(inode) + 3;
-+      handle = ext3_journal_start(inode, err);
-+      if (IS_ERR(handle))
-+              return;
-+
-+      ext3_block_truncate_page(handle, mapping, inode->i_size);
-+
-+      down_write(&EXT3_I(inode)->truncate_sem);
-+      ext3_ext_invalidate_cache(&tree);
-+
-+      /* 
-+       * TODO: optimization is possible here
-+       * probably we need not scaning at all,
-+       * because page truncation is enough
-+       */
-+      if (ext3_orphan_add(handle, inode))
-+              goto out_stop;
-+
-+      /* we have to know where to truncate from in crash case */
-+      EXT3_I(inode)->i_disksize = inode->i_size;
-+      ext3_mark_inode_dirty(handle, inode);
-+
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
-+      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
-+      
-+      /* In a multi-transaction truncate, we only make the final
-+       * transaction synchronous */
-+      if (IS_SYNC(inode))
-+              handle->h_sync = 1;
-+
-+out_stop:
-+      /*
-+       * If this was a simple ftruncate(), and the file will remain alive
-+       * then we need to clear up the orphan record which we created above.
-+       * However, if this was a real unlink then we were called by
-+       * ext3_delete_inode(), and we allow that function to clean up the
-+       * orphan info for us.
-+       */
-+      if (inode->i_nlink)
-+              ext3_orphan_del(handle, inode);
-+
-+      up_write(&EXT3_I(inode)->truncate_sem);
-+      ext3_journal_stop(handle, inode);
-+}
-+
-+/*
-+ * this routine calculate max number of blocks we could modify
-+ * in order to allocate new block for an inode
-+ */
-+int ext3_ext_writepage_trans_blocks(struct inode *inode, int num)
-+{
-+      struct ext3_extents_tree tree;
-+      int needed;
-+      
-+      ext3_init_tree_desc(&tree, inode);
-+      
-+      needed = ext3_ext_calc_credits_for_insert(&tree, NULL);
-+
-+      /* caller want to allocate num blocks */
-+      needed *= num;
-+      
-+#ifdef CONFIG_QUOTA
-+      /* 
-+       * FIXME: real calculation should be here
-+       * it depends on blockmap format of qouta file
-+       */
-+      needed += 2 * EXT3_SINGLEDATA_TRANS_BLOCKS;
-+#endif
-+
-+      return needed;
-+}
-+
-+void ext3_extents_initialize_blockmap(handle_t *handle, struct inode *inode)
-+{
-+      struct ext3_extents_tree tree;
-+
-+      ext3_init_tree_desc(&tree, inode);
-+      ext3_extent_tree_init(handle, &tree);
-+}
-+
-+static int
-+ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *newex, int exist)
-+{
-+      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
-+
-+      if (!exist)
-+              return EXT_CONTINUE;
-+      if (buf->err < 0)
-+              return EXT_BREAK;
-+      if (buf->cur - buf->buffer + sizeof(*newex) > buf->buflen)
-+              return EXT_BREAK;
-+
-+      if (!copy_to_user(buf->cur, newex, sizeof(*newex))) {
-+              buf->err++;
-+              buf->cur += sizeof(*newex);
-+      } else {
-+              buf->err = -EFAULT;
-+              return EXT_BREAK;
-+      }
-+      return EXT_CONTINUE;
-+}
-+
-+static int
-+ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *ex, int exist)
-+{
-+      struct ext3_extent_tree_stats *buf =
-+              (struct ext3_extent_tree_stats *) tree->private;
-+      int depth;
-+
-+      if (!exist)
-+              return EXT_CONTINUE;
-+
-+      depth = EXT_DEPTH(tree);
-+      buf->extents_num++;
-+      if (path[depth].p_ext == EXT_FIRST_EXTENT(path[depth].p_hdr))
-+              buf->leaf_num++;
-+      return EXT_CONTINUE;
-+}
-+
-+int ext3_ext_ioctl(struct inode *inode, struct file *filp, unsigned int cmd,
-+                 unsigned long arg)
-+{
-+      int err = 0;
-+
-+      if (!(EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL))
-+              return -EINVAL;
-+
-+      if (cmd == EXT3_IOC_GET_EXTENTS) {
-+              struct ext3_extent_buf buf;
-+              struct ext3_extents_tree tree;
-+
-+              if (copy_from_user(&buf, (void *) arg, sizeof(buf)))
-+                      return -EFAULT;
-+
-+              ext3_init_tree_desc(&tree, inode);
-+              buf.cur = buf.buffer;
-+              buf.err = 0;
-+              tree.private = &buf;
-+              down_write(&EXT3_I(inode)->truncate_sem);
-+              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
-+              up_write(&EXT3_I(inode)->truncate_sem);
-+              if (err == 0)
-+                      err = buf.err;
-+      } else if (cmd == EXT3_IOC_GET_TREE_STATS) {
-+              struct ext3_extent_tree_stats buf;
-+              struct ext3_extents_tree tree;
-+
-+              ext3_init_tree_desc(&tree, inode);
-+              down_write(&EXT3_I(inode)->truncate_sem);
-+              buf.depth = EXT_DEPTH(&tree);
-+              buf.extents_num = 0;
-+              buf.leaf_num = 0;
-+              tree.private = &buf;
-+              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
-+              up_write(&EXT3_I(inode)->truncate_sem);
-+              if (!err)
-+                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
-+      } else if (cmd == EXT3_IOC_GET_TREE_DEPTH) {
-+              struct ext3_extents_tree tree;
-+              ext3_init_tree_desc(&tree, inode);
-+              down_write(&EXT3_I(inode)->truncate_sem);
-+              err = EXT_DEPTH(&tree);
-+              up_write(&EXT3_I(inode)->truncate_sem);
-+      }
-+
-+      return err;
-+}
-+
-+EXPORT_SYMBOL(ext3_init_tree_desc);
-+EXPORT_SYMBOL(ext3_mark_inode_dirty);
-+EXPORT_SYMBOL(ext3_ext_invalidate_cache);
-+EXPORT_SYMBOL(ext3_ext_insert_extent);
-+EXPORT_SYMBOL(ext3_ext_walk_space);
-+EXPORT_SYMBOL(ext3_ext_find_goal);
-+EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
-Index: linux-2.4.20-rh-20.9/fs/ext3/ialloc.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/ialloc.c 2004-11-02 21:01:47.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/ialloc.c      2004-11-02 21:03:00.000000000 +0300
-@@ -593,10 +593,22 @@
-               iloc.bh = NULL;
-               goto fail;
-       }
--      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
--      if (err) goto fail;
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
-+              ext3_extents_initialize_blockmap(handle, inode);
-+              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
-+                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
-+                      if (err) goto fail;
-+                      EXT3_SET_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS);
-+                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
-+                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
-+              }
-+      }
-+      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
-+      if (err) goto fail;
-       
-       unlock_super (sb);
-       if(DQUOT_ALLOC_INODE(inode)) {
-Index: linux-2.4.20-rh-20.9/fs/ext3/inode.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/inode.c  2004-11-02 21:01:55.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/inode.c       2004-11-02 21:03:00.000000000 +0300
-@@ -852,6 +852,16 @@
-       goto reread;
- }
-+static inline int
-+ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create, int extend_disksize)
-+{
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_get_block(handle, inode, block, bh, create);
-+      return ext3_get_block_handle(handle, inode, block, bh, create, 
-+                                      extend_disksize);
-+}
-+
- /*
-  * The BKL is not held on entry here.
-  */
-@@ -865,7 +875,7 @@
-               handle = ext3_journal_current_handle();
-               J_ASSERT(handle != 0);
-       }
--      ret = ext3_get_block_handle(handle, inode, iblock,
-+      ret = ext3_get_block_wrap(handle, inode, iblock,
-                               bh_result, create, 1);
-       return ret;
- }
-@@ -892,7 +902,7 @@
-               }
-       }
-       if (ret == 0)
--              ret = ext3_get_block_handle(handle, inode, iblock,
-+              ret = ext3_get_block_wrap(handle, inode, iblock,
-                                       bh_result, create, 0);
-       if (ret == 0)
-               bh_result->b_size = (1 << inode->i_blkbits);
-@@ -914,7 +924,7 @@
-       dummy.b_state = 0;
-       dummy.b_blocknr = -1000;
-       buffer_trace_init(&dummy.b_history);
--      *errp = ext3_get_block_handle(handle, inode, block, &dummy, create, 1);
-+      *errp = ext3_get_block_wrap(handle, inode, block, &dummy, create, 1);
-       if (!*errp && buffer_mapped(&dummy)) {
-               struct buffer_head *bh;
-               bh = sb_getblk(inode->i_sb, dummy.b_blocknr);
-@@ -1502,7 +1512,7 @@
-  * This required during truncate. We need to physically zero the tail end
-  * of that block so it doesn't yield old data if the file is later grown.
-  */
--static int ext3_block_truncate_page(handle_t *handle,
-+int ext3_block_truncate_page(handle_t *handle,
-               struct address_space *mapping, loff_t from)
- {
-       unsigned long index = from >> PAGE_CACHE_SHIFT;
-@@ -1990,6 +2000,9 @@
-       ext3_discard_prealloc(inode);
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_truncate(inode);
-+
-       handle = start_transaction(inode);
-       if (IS_ERR(handle))
-               return;         /* AKPM: return what? */
-@@ -2426,6 +2439,7 @@
-       for (block = 0; block < EXT3_N_BLOCKS; block++)
-               inode->u.ext3_i.i_data[block] = iloc.raw_inode->i_block[block];
-       INIT_LIST_HEAD(&inode->u.ext3_i.i_orphan);
-+      memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
-       if (EXT3_INODE_SIZE(inode->i_sb) > EXT3_GOOD_OLD_INODE_SIZE)
-               inode->u.ext3_i.i_extra_isize =
-@@ -2758,6 +2772,9 @@
-       int indirects = (EXT3_NDIR_BLOCKS % bpp) ? 5 : 3;
-       int ret;
-       
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_writepage_trans_blocks(inode, bpp);
-+
-       if (ext3_should_journal_data(inode))
-               ret = 3 * (bpp + indirects) + 2;
-       else
-@@ -3082,7 +3099,7 @@
-       /* alloc blocks one by one */
-       for (i = 0; i < nblocks; i++) {
--              ret = ext3_get_block_handle(handle, inode, blocks[i],
-+              ret = ext3_get_block_wrap(handle, inode, blocks[i],
-                                               &bh_tmp, 1, 1);
-               if (ret)
-                       break;
-@@ -3158,7 +3175,7 @@
-                 if (blocks[i] != 0)
-                         continue;
--                rc = ext3_get_block_handle(handle, inode, iblock, &bh, 1, 1);
-+                rc = ext3_get_block_wrap(handle, inode, iblock, &bh, 1, 1);
-                 if (rc) {
-                         printk(KERN_INFO "ext3_map_inode_page: error %d "
-                                "allocating block %ld\n", rc, iblock);
-Index: linux-2.4.20-rh-20.9/fs/ext3/Makefile
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/Makefile 2004-11-02 21:01:49.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/Makefile      2004-11-02 21:01:58.000000000 +0300
-@@ -13,7 +13,9 @@
- obj-y    := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o iopen.o \
-               ioctl.o namei.o super.o symlink.o hash.o ext3-exports.o \
--              xattr_trusted.o
-+              xattr_trusted.o extents.o
-+export-objs += extents.o
-+
- obj-m    := $(O_TARGET)
- export-objs += xattr.o
-Index: linux-2.4.20-rh-20.9/fs/ext3/super.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/super.c  2004-11-02 21:01:47.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/super.c       2004-11-02 21:01:58.000000000 +0300
-@@ -623,6 +623,7 @@
-       int i;
-       J_ASSERT(sbi->s_delete_inodes == 0);
-+      ext3_ext_release(sb);
-       ext3_xattr_put_super(sb);
-       journal_destroy(sbi->s_journal);
-       if (!(sb->s_flags & MS_RDONLY)) {
-@@ -798,6 +799,10 @@
-               }
-               else if (!strcmp (this_char, "pdirops"))
-                       set_opt (sbi->s_mount_opt, PDIROPS);
-+              else if (!strcmp (this_char, "extents"))
-+                      set_opt (*mount_options, EXTENTS);
-+              else if (!strcmp (this_char, "extdebug"))
-+                      set_opt (*mount_options, EXTDEBUG);
-               else if (!strcmp (this_char, "grpid") ||
-                        !strcmp (this_char, "bsdgroups"))
-                       set_opt (*mount_options, GRPID);
-@@ -1499,6 +1504,8 @@
-               printk (KERN_INFO "EXT3-fs: mounted filesystem with parallel dirops\n");
-               sb->s_flags |= S_PDIROPS;
-       }
-+
-+      ext3_ext_init(sb);
-               
-       return sb;
-Index: linux-2.4.20-rh-20.9/fs/ext3/ioctl.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/ioctl.c  2004-11-02 21:01:31.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/ioctl.c       2004-11-02 21:01:58.000000000 +0300
-@@ -189,6 +189,10 @@
-                       return ret;
-               }
- #endif
-+      case EXT3_IOC_GET_EXTENTS:
-+      case EXT3_IOC_GET_TREE_STATS:
-+      case EXT3_IOC_GET_TREE_DEPTH:
-+              return ext3_ext_ioctl(inode, filp, cmd, arg);
-       default:
-               return -ENOTTY;
-       }
-Index: linux-2.4.20-rh-20.9/include/linux/ext3_fs.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/linux/ext3_fs.h  2004-11-02 21:01:47.000000000 +0300
-+++ linux-2.4.20-rh-20.9/include/linux/ext3_fs.h       2004-11-02 21:01:58.000000000 +0300
-@@ -184,6 +184,7 @@
- #define EXT3_IMAGIC_FL                        0x00002000 /* AFS directory */
- #define EXT3_JOURNAL_DATA_FL          0x00004000 /* file data should be journaled */
- #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
-+#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
- #define EXT3_FL_USER_VISIBLE          0x00005FFF /* User visible flags */
- #define EXT3_FL_USER_MODIFIABLE               0x000000FF /* User modifiable flags */
-@@ -208,6 +209,9 @@
- #ifdef CONFIG_JBD_DEBUG
- #define EXT3_IOC_WAIT_FOR_READONLY    _IOR('f', 99, long)
- #endif
-+#define       EXT3_IOC_GET_EXTENTS            _IOR('f', 5, long)
-+#define       EXT3_IOC_GET_TREE_DEPTH         _IOR('f', 6, long)
-+#define       EXT3_IOC_GET_TREE_STATS         _IOR('f', 7, long)
- /*
-  * Structure of an inode on the disk
-@@ -328,6 +332,8 @@
- #define EXT3_MOUNT_ASYNCDEL           0x20000 /* Delayed deletion */
- #define EXT3_MOUNT_IOPEN              0x40000 /* Allow access via iopen */
- #define EXT3_MOUNT_IOPEN_NOPRIV               0x80000 /* Make iopen world-readable */
-+#define EXT3_MOUNT_EXTENTS            0x100000/* Extents support */
-+#define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
- /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
- #ifndef _LINUX_EXT2_FS_H
-@@ -504,10 +510,12 @@
- #define EXT3_FEATURE_INCOMPAT_FILETYPE                0x0002
- #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
- #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
-+#define EXT3_FEATURE_INCOMPAT_EXTENTS         0x0040 /* extents support */
- #define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
- #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
--                                       EXT3_FEATURE_INCOMPAT_RECOVER)
-+                                       EXT3_FEATURE_INCOMPAT_RECOVER| \
-+                                       EXT3_FEATURE_INCOMPAT_EXTENTS)
- #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
-                                        EXT3_FEATURE_RO_COMPAT_LARGE_FILE| \
-                                        EXT3_FEATURE_RO_COMPAT_BTREE_DIR)
-@@ -689,6 +697,7 @@
- extern unsigned long ext3_count_free (struct buffer_head *, unsigned);
- /* inode.c */
-+extern int ext3_block_truncate_page(handle_t *, struct address_space *, loff_t);
- extern int ext3_forget(handle_t *, int, struct inode *, struct buffer_head *, int);
- extern struct buffer_head * ext3_getblk (handle_t *, struct inode *, long, int, int *);
- extern struct buffer_head * ext3_bread (handle_t *, struct inode *, int, int, int *);
-@@ -770,6 +779,16 @@
- extern struct inode_operations ext3_symlink_inode_operations;
- extern struct inode_operations ext3_fast_symlink_inode_operations;
-+/* extents.c */
-+extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
-+extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                            struct buffer_head *, int);
-+extern void ext3_ext_truncate(struct inode *);
-+extern void ext3_ext_init(struct super_block *);
-+extern void ext3_ext_release(struct super_block *);
-+extern void ext3_extents_initialize_blockmap(handle_t *, struct inode *);
-+extern int ext3_ext_ioctl(struct inode *inode, struct file *filp,
-+                        unsigned int cmd, unsigned long arg);
- #endif        /* __KERNEL__ */
-Index: linux-2.4.20-rh-20.9/include/linux/ext3_extents.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/linux/ext3_extents.h     2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.20-rh-20.9/include/linux/ext3_extents.h  2004-11-02 21:03:00.000000000 +0300
-@@ -0,0 +1,251 @@
-+/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
-+ * Written by Alex Tomas <alex@clusterfs.com>
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ *
-+ * This program is distributed in the hope that it will be useful,
-+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
-+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-+ * GNU General Public License for more details.
-+ *
-+ * You should have received a copy of the GNU General Public Licens
-+ * along with this program; if not, write to the Free Software
-+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-
-+ */
-+
-+#ifndef _LINUX_EXT3_EXTENTS
-+#define _LINUX_EXT3_EXTENTS
-+
-+/*
-+ * with AGRESSIVE_TEST defined capacity of index/leaf blocks
-+ * become very little, so index split, in-depth growing and
-+ * other hard changes happens much more often
-+ * this is for debug purposes only
-+ */
-+#define AGRESSIVE_TEST_
-+
-+/*
-+ * if CHECK_BINSEARCH defined, then results of binary search
-+ * will be checked by linear search
-+ */
-+#define CHECK_BINSEARCH_
-+
-+/*
-+ * if EXT_DEBUG is defined you can use 'extdebug' mount option
-+ * to get lots of info what's going on
-+ */
-+#define EXT_DEBUG_
-+#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
-+do {                                                  \
-+      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
-+              printk(fmt, ##a);                       \
-+} while (0);
-+#else
-+#define ext_debug(tree,fmt,a...)
-+#endif
-+
-+/*
-+ * if EXT_STATS is defined then stats numbers are collected
-+ * these number will be displayed at umount time
-+ */
-+#define EXT_STATS_
-+
-+
-+#define EXT3_ALLOC_NEEDED     3       /* block bitmap + group desc. + sb */
-+
-+/*
-+ * ext3_inode has i_block array (total 60 bytes)
-+ * first 4 bytes are used to store:
-+ *  - tree depth (0 mean there is no tree yet. all extents in the inode)
-+ *  - number of alive extents in the inode
-+ */
-+
-+/*
-+ * this is extent on-disk structure
-+ * it's used at the bottom of the tree
-+ */
-+struct ext3_extent {
-+      __u32   ee_block;       /* first logical block extent covers */
-+      __u16   ee_len;         /* number of blocks covered by extent */
-+      __u16   ee_start_hi;    /* high 16 bits of physical block */
-+      __u32   ee_start;       /* low 32 bigs of physical block */
-+};
-+
-+/*
-+ * this is index on-disk structure
-+ * it's used at all the levels, but the bottom
-+ */
-+struct ext3_extent_idx {
-+      __u32   ei_block;       /* index covers logical blocks from 'block' */
-+      __u32   ei_leaf;        /* pointer to the physical block of the next *
-+                               * level. leaf or next index could bet here */
-+      __u16   ei_leaf_hi;     /* high 16 bits of physical block */
-+      __u16   ei_unused;
-+};
-+
-+/*
-+ * each block (leaves and indexes), even inode-stored has header
-+ */
-+struct ext3_extent_header {   
-+      __u16   eh_magic;       /* probably will support different formats */   
-+      __u16   eh_entries;     /* number of valid entries */
-+      __u16   eh_max;         /* capacity of store in entries */
-+      __u16   eh_depth;       /* has tree real underlaying blocks? */
-+      __u32   eh_generation;  /* generation of the tree */
-+};
-+
-+#define EXT3_EXT_MAGIC                0xf30a
-+
-+/*
-+ * array of ext3_ext_path contains path to some extent
-+ * creation/lookup routines use it for traversal/splitting/etc
-+ * truncate uses it to simulate recursive walking
-+ */
-+struct ext3_ext_path {
-+      __u32                           p_block;
-+      __u16                           p_depth;
-+      struct ext3_extent              *p_ext;
-+      struct ext3_extent_idx          *p_idx;
-+      struct ext3_extent_header       *p_hdr;
-+      struct buffer_head              *p_bh;
-+};
-+
-+/*
-+ * structure for external API
-+ */
-+
-+/*
-+ * storage for cached extent
-+ */
-+struct ext3_ext_cache {
-+      __u32   ec_start;
-+      __u32   ec_block;
-+      __u32   ec_len;
-+      __u32   ec_type;
-+};
-+
-+#define EXT3_EXT_CACHE_NO     0
-+#define EXT3_EXT_CACHE_GAP    1
-+#define EXT3_EXT_CACHE_EXTENT 2
-+
-+/*
-+ * ext3_extents_tree is used to pass initial information
-+ * to top-level extents API
-+ */
-+struct ext3_extents_helpers;
-+struct ext3_extents_tree {
-+      struct inode *inode;    /* inode which tree belongs to */
-+      void *root;             /* ptr to data top of tree resides at */
-+      void *buffer;           /* will be passed as arg to ^^ routines */
-+      int buffer_len;
-+      void *private;
-+      struct ext3_ext_cache *cex;/* last found extent */
-+      struct ext3_extents_helpers *ops;
-+};
-+
-+struct ext3_extents_helpers {
-+      int (*get_write_access)(handle_t *h, void *buffer);
-+      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
-+      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
-+      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
-+      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
-+      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
-+};
-+
-+/*
-+ * to be called by ext3_ext_walk_space()
-+ * negative retcode - error
-+ * positive retcode - signal for ext3_ext_walk_space(), see below
-+ * callback must return valid extent (passed or newly created)
-+ */
-+typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_extent *, int);
-+
-+#define EXT_CONTINUE  0
-+#define EXT_BREAK     1
-+#define EXT_REPEAT    2
-+
-+
-+#define EXT_MAX_BLOCK 0xffffffff
-+#define EXT_CACHE_MARK        0xffff
-+
-+
-+#define EXT_FIRST_EXTENT(__hdr__) \
-+      ((struct ext3_extent *) (((char *) (__hdr__)) +         \
-+                               sizeof(struct ext3_extent_header)))
-+#define EXT_FIRST_INDEX(__hdr__) \
-+      ((struct ext3_extent_idx *) (((char *) (__hdr__)) +     \
-+                                   sizeof(struct ext3_extent_header)))
-+#define EXT_HAS_FREE_INDEX(__path__) \
-+      ((__path__)->p_hdr->eh_entries < (__path__)->p_hdr->eh_max)
-+#define EXT_LAST_EXTENT(__hdr__) \
-+      (EXT_FIRST_EXTENT((__hdr__)) + (__hdr__)->eh_entries - 1)
-+#define EXT_LAST_INDEX(__hdr__) \
-+      (EXT_FIRST_INDEX((__hdr__)) + (__hdr__)->eh_entries - 1)
-+#define EXT_MAX_EXTENT(__hdr__) \
-+      (EXT_FIRST_EXTENT((__hdr__)) + (__hdr__)->eh_max - 1)
-+#define EXT_MAX_INDEX(__hdr__) \
-+      (EXT_FIRST_INDEX((__hdr__)) + (__hdr__)->eh_max - 1)
-+
-+#define EXT_ROOT_HDR(tree) \
-+      ((struct ext3_extent_header *) (tree)->root)
-+#define EXT_BLOCK_HDR(bh) \
-+      ((struct ext3_extent_header *) (bh)->b_data)
-+#define EXT_DEPTH(_t_)        \
-+      (((struct ext3_extent_header *)((_t_)->root))->eh_depth)
-+#define EXT_GENERATION(_t_)   \
-+      (((struct ext3_extent_header *)((_t_)->root))->eh_generation)
-+
-+
-+#define EXT_ASSERT(__x__) if (!(__x__)) BUG();
-+
-+
-+/*
-+ * this structure is used to gather extents from the tree via ioctl
-+ */
-+struct ext3_extent_buf {
-+      unsigned long start;
-+      int buflen;
-+      void *buffer;
-+      void *cur;
-+      int err;
-+};
-+
-+/*
-+ * this structure is used to collect stats info about the tree
-+ */
-+struct ext3_extent_tree_stats {
-+      int depth;
-+      int extents_num;
-+      int leaf_num;
-+};
-+
-+void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
-+extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
-+extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
-+extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
-+extern int ext3_ext_walk_space(struct ext3_extents_tree *, unsigned long, unsigned long, ext_prepare_callback);
-+extern int ext3_ext_remove_space(struct ext3_extents_tree *, unsigned long, unsigned long);
-+extern struct ext3_ext_path * ext3_ext_find_extent(struct ext3_extents_tree *, int, struct ext3_ext_path *);
-+
-+static inline void
-+ext3_ext_invalidate_cache(struct ext3_extents_tree *tree)
-+{
-+      if (tree->cex)
-+              tree->cex->ec_type = EXT3_EXT_CACHE_NO;
-+}
-+
-+
-+#endif /* _LINUX_EXT3_EXTENTS */
-+
-Index: linux-2.4.20-rh-20.9/include/linux/ext3_fs_i.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/linux/ext3_fs_i.h        2004-11-02 21:01:47.000000000 +0300
-+++ linux-2.4.20-rh-20.9/include/linux/ext3_fs_i.h     2004-11-02 21:06:02.000000000 +0300
-@@ -82,6 +82,8 @@
-       struct dynlock i_htree_lock;
-       struct semaphore i_append_sem;
-       struct semaphore i_rename_sem;
-+
-+      __u32 i_cached_extent[4];
- };
- #endif        /* _LINUX_EXT3_FS_I */
index 4b6ec48..c392ac9 100644 (file)
@@ -1,10 +1,10 @@
-Index: linux-2.4.21-20.EL/fs/ext3/extents.c
+Index: linux-2.4.21-rhel/fs/ext3/extents.c
 ===================================================================
---- linux-2.4.21-20.EL.orig/fs/ext3/extents.c  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.21-20.EL/fs/ext3/extents.c       2004-11-03 00:35:30.644364336 +0300
-@@ -0,0 +1,2278 @@
+--- linux-2.4.21-rhel.orig/fs/ext3/extents.c   2005-03-02 22:42:20.659360368 +0300
++++ linux-2.4.21-rhel/fs/ext3/extents.c        2005-03-04 02:34:52.000000000 +0300
+@@ -0,0 +1,2312 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -39,16 +39,37 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +#include <linux/time.h>
 +#include <linux/ext3_jbd.h>
 +#include <linux/jbd.h>
++#include <linux/locks.h>
 +#include <linux/smp_lock.h>
 +#include <linux/highuid.h>
 +#include <linux/pagemap.h>
 +#include <linux/quotaops.h>
 +#include <linux/string.h>
 +#include <linux/slab.h>
-+#include <linux/locks.h>
 +#include <linux/ext3_extents.h>
 +#include <asm/uaccess.h>
 +
++
++static inline int ext3_ext_check_header(struct ext3_extent_header *eh)
++{
++      if (eh->eh_magic != EXT3_EXT_MAGIC) {
++              printk(KERN_ERR "EXT3-fs: invalid magic = 0x%x\n",
++                     (unsigned)eh->eh_magic);
++              return -EIO;
++      }
++      if (eh->eh_max == 0) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_max = %u\n",
++                     (unsigned)eh->eh_max);
++              return -EIO;
++      }
++      if (eh->eh_entries > eh->eh_max) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_entries = %u\n",
++                     (unsigned)eh->eh_entries);
++              return -EIO;
++      }
++      return 0;
++}
++
 +static handle_t *ext3_ext_journal_restart(handle_t *handle, int needed)
 +{
 +      int err;
@@ -86,8 +107,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + *  - ENOMEM
 + */
 +static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_extents_tree *tree,
++                             struct ext3_ext_path *path)
 +{
 +      int err;
 +
@@ -108,7 +129,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + *  - EIO
 + */
 +static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                        struct ext3_ext_path *path)
 +{
 +      int err;
 +      if (path->p_bh) {
@@ -123,8 +144,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static int inline
 +ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
++                 struct ext3_ext_path *path, struct ext3_extent *ex,
++                 int *err)
 +{
 +      int goal, depth, newblock;
 +      struct inode *inode;
@@ -143,7 +164,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              unsigned long colour;
 +
 +              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
++                          EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
 +                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
 +              colour = (current->pid % 16) *
 +                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
@@ -166,8 +187,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 6;
 +#endif
@@ -179,8 +200,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent_idx);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 5;
 +#endif
@@ -191,8 +212,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      sizeof(struct ext3_extent);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 3;
 +#endif
@@ -203,9 +224,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 4;
 +#endif
@@ -213,7 +233,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int k, l = path->p_depth;
@@ -222,12 +242,12 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      for (k = 0; k <= l; k++, path++) {
 +              if (path->p_idx) {
 +                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
++                                path->p_idx->ei_leaf);
 +              } else if (path->p_ext) {
 +                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
++                                path->p_ext->ee_block,
++                                path->p_ext->ee_len,
++                                path->p_ext->ee_start);
 +              } else
 +                      ext_debug(tree, "  []");
 +      }
@@ -236,7 +256,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int depth = EXT_DEPTH(tree);
@@ -252,7 +272,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +      for (i = 0; i < eh->eh_entries; i++, ex++) {
 +              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +      }
 +      ext_debug(tree, "\n");
 +#endif
@@ -263,11 +283,12 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      int depth = path->p_depth;
 +      int i;
 +
-+      for (i = 0; i <= depth; i++, path++)
++      for (i = 0; i <= depth; i++, path++) {
 +              if (path->p_bh) {
 +                      brelse(path->p_bh);
 +                      path->p_bh = NULL;
 +              }
++      }
 +}
 +
 +/*
@@ -275,7 +296,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                     struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent_idx *ix;
@@ -301,7 +322,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +      ix += l;
 +      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
++      ext_debug(tree," -> %d->%d ",path->p_idx->ei_block,path->p_idx->ei_leaf);
 +
 +      while (l++ < r) {
 +              if (block < ix->ei_block) 
@@ -309,7 +330,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              path->p_idx = ix++;
 +      }
 +      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -319,9 +340,9 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              for (k = 0; k < eh->eh_entries; k++, ix++) {
 +                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
 +                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
++                                     ix, EXT_FIRST_INDEX(eh));
 +                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
++                                     ix->ei_block,ix[-1].ei_block);
 +                      }
 +                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
 +                      if (block < ix->ei_block) 
@@ -331,7 +352,6 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              EXT_ASSERT(chix == path->p_idx);
 +      }
 +#endif
-+
 +}
 +
 +/*
@@ -339,7 +359,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                 struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent *ex;
@@ -373,7 +393,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      ex += l;
 +      path->p_ext = ex;
 +      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +      while (l++ < r) {
 +              if (block < ex->ee_block) 
@@ -381,7 +401,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              path->p_ext = ex++;
 +      }
 +      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -397,7 +417,6 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              EXT_ASSERT(chex == path->p_ext);
 +      }
 +#endif
-+
 +}
 +
 +int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
@@ -418,7 +437,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +struct ext3_ext_path *
 +ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
++                   struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      struct buffer_head *bh;
@@ -430,15 +449,17 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +      eh = EXT_ROOT_HDR(tree);
 +      EXT_ASSERT(eh);
++      if (ext3_ext_check_header(eh))
++              goto err;
++
 +      i = depth = EXT_DEPTH(tree);
 +      EXT_ASSERT(eh->eh_max);
 +      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(i == 0 || eh->eh_entries > 0);
 +      
 +      /* account possible depth increase */
 +      if (!path) {
 +              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
++                             GFP_NOFS);
 +              if (!path)
 +                      return ERR_PTR(-ENOMEM);
 +      }
@@ -448,29 +469,34 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      /* walk through the tree */
 +      while (i) {
 +              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
++                        ppos, eh->eh_entries, eh->eh_max);
 +              ext3_ext_binsearch_idx(tree, path + ppos, block);
 +              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
 +              path[ppos].p_depth = i;
 +              path[ppos].p_ext = NULL;
 +
 +              bh = sb_bread(tree->inode->i_sb, path[ppos].p_block);
-+              if (!bh) {
-+                      ext3_ext_drop_refs(path);
-+                      kfree(path);
-+                      return ERR_PTR(-EIO);
-+              }
++              if (!bh)
++                      goto err;
++
 +              eh = EXT_BLOCK_HDR(bh);
 +              ppos++;
 +              EXT_ASSERT(ppos <= depth);
 +              path[ppos].p_bh = bh;
 +              path[ppos].p_hdr = eh;
 +              i--;
++
++              if (ext3_ext_check_header(eh))
++                      goto err;
 +      }
 +
 +      path[ppos].p_depth = i;
 +      path[ppos].p_hdr = eh;
 +      path[ppos].p_ext = NULL;
++      path[ppos].p_idx = NULL;
++
++      if (ext3_ext_check_header(eh))
++              goto err;
 +
 +      /* find extent */
 +      ext3_ext_binsearch(tree, path + ppos, block);
@@ -478,6 +504,12 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      ext3_ext_show_path(tree, path);
 +
 +      return path;
++
++err:
++      printk(KERN_ERR "EXT3-fs: header is corrupted!\n");
++      ext3_ext_drop_refs(path);
++      kfree(path);
++      return ERR_PTR(-EIO);
 +}
 +
 +/*
@@ -485,9 +517,9 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + * it check where to insert: before curp or after curp
 + */
 +static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *curp,
++                               int logical, int ptr)
 +{
 +      struct ext3_extent_idx *ix;
 +      int len, err;
@@ -503,9 +535,9 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent_idx);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
++                                "move %d from 0x%p to 0x%p\n",
++                                logical, ptr, len,
++                                (curp->p_idx + 1), (curp->p_idx + 2));
 +                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
 +              }
 +              ix = curp->p_idx + 1;
@@ -514,9 +546,9 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              len = len * sizeof(struct ext3_extent_idx);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
++                        "move %d from 0x%p to 0x%p\n",
++                        logical, ptr, len,
++                        curp->p_idx, (curp->p_idx + 1));
 +              memmove(curp->p_idx + 1, curp->p_idx, len);
 +              ix = curp->p_idx;
 +      }
@@ -544,8 +576,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + *  - initialize subtree
 + */
 +static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
++                        struct ext3_ext_path *path,
++                        struct ext3_extent *newext, int at)
 +{
 +      struct buffer_head *bh = NULL;
 +      int depth = EXT_DEPTH(tree);
@@ -566,13 +598,13 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              border = path[depth].p_ext[1].ee_block;
 +              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      } else {
 +              border = newext->ee_block;
 +              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      }
 +
 +      /* 
@@ -630,12 +662,11 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      while (path[depth].p_ext <=
 +                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
++                        path[depth].p_ext->ee_block,
++                        path[depth].p_ext->ee_start,
++                        path[depth].p_ext->ee_len,
++                        newblock);
++              memmove(ex++, path[depth].p_ext++, sizeof(struct ext3_extent));
 +              neh->eh_entries++;
 +              m++;
 +      }
@@ -688,21 +719,21 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              fidx->ei_leaf = oldblock;
 +
 +              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
++                        i, newblock, border, oldblock);
 +              /* copy indexes */
 +              m = 0;
 +              path[i].p_idx++;
 +
 +              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
++                        EXT_MAX_INDEX(path[i].p_hdr));
 +              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
++                         EXT_LAST_INDEX(path[i].p_hdr));
 +              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
 +                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
++                                i, path[i].p_idx->ei_block,
++                                path[i].p_idx->ei_leaf, newblock);
 +                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
++                              sizeof(struct ext3_extent_idx));
 +                      neh->eh_entries++;
 +                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
 +                      m++;
@@ -732,7 +763,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      /* insert new index */
 +      if (!err)
 +              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
++                                          border, newblock);
 +
 +cleanup:
 +      if (bh) {
@@ -762,9 +793,9 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + *    just created block
 + */
 +static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *path,
++                               struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp = path;
 +      struct ext3_extent_header *neh;
@@ -823,7 +854,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      neh = EXT_ROOT_HDR(tree);
 +      fidx = EXT_FIRST_INDEX(neh);
 +      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
++                neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
 +
 +      neh->eh_depth = path->p_depth + 1;
 +      err = ext3_ext_dirty(handle, tree, curp);
@@ -838,9 +869,9 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + * then it requests in-depth growing
 + */
 +static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                                  struct ext3_extents_tree *tree,
++                                  struct ext3_ext_path *path,
++                                  struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp;
 +      int depth, i, err = 0;
@@ -916,12 +947,12 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              if (depth == path->p_depth) {
 +                      /* leaf */
 +                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
++                          EXT_LAST_EXTENT(path[depth].p_hdr))
 +                              return path[depth].p_ext[1].ee_block;
 +              } else {
 +                      /* index */
 +                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
++                          EXT_LAST_INDEX(path[depth].p_hdr))
 +                              return path[depth].p_idx[1].ei_block;
 +              }
 +              depth--;        
@@ -934,7 +965,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + * returns first allocated block from next leaf or EXT_MAX_BLOCK
 + */
 +static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
++                                       struct ext3_ext_path *path)
 +{
 +      int depth;
 +
@@ -950,7 +981,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      
 +      while (depth >= 0) {
 +              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
++                  EXT_LAST_INDEX(path[depth].p_hdr))
 +                      return path[depth].p_idx[1].ei_block;
 +              depth--;        
 +      }
@@ -964,7 +995,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + * TODO: do we need to correct tree in all cases?
 + */
 +int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                           struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      int depth = EXT_DEPTH(tree);    
@@ -1014,8 +1045,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static int inline
 +ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                         struct ext3_extent *ex1,
++                         struct ext3_extent *ex2)
 +{
 +      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
 +              return 0;
@@ -1037,8 +1068,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + * creating new leaf in no-space case
 + */
 +int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
++                         struct ext3_ext_path *path,
++                         struct ext3_extent *newext)
 +{
 +      struct ext3_extent_header * eh;
 +      struct ext3_extent *ex, *fex;
@@ -1047,7 +1078,6 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      int depth, len, err, next;
 +
 +      EXT_ASSERT(newext->ee_len > 0);
-+      EXT_ASSERT(newext->ee_len < EXT_CACHE_MARK);
 +      depth = EXT_DEPTH(tree);
 +      ex = path[depth].p_ext;
 +      EXT_ASSERT(path[depth].p_hdr);
@@ -1055,8 +1085,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      /* try to insert block into found extent and return */
 +      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
 +              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
++                        newext->ee_len, ex->ee_block, ex->ee_len,
++                        ex->ee_start);
 +              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
 +                      return err;
 +              ex->ee_len += newext->ee_len;
@@ -1084,12 +1114,12 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              eh = npath[depth].p_hdr;
 +              if (eh->eh_entries < eh->eh_max) {
 +                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
++                                eh->eh_entries);
 +                      path = npath;
 +                      goto repeat;
 +              }
 +              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
++                        eh->eh_entries, eh->eh_max);
 +      }
 +
 +      /*
@@ -1111,8 +1141,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      if (!nearex) {
 +              /* there is no extent in this leaf, create first one */
 +              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
++                        newext->ee_block, newext->ee_start,
++                        newext->ee_len);
 +              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
 +      } else if (newext->ee_block > nearex->ee_block) {
 +              EXT_ASSERT(newext->ee_block != nearex->ee_block);
@@ -1121,10 +1151,10 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
++                                "move %d from 0x%p to 0x%p\n",
++                                newext->ee_block, newext->ee_start,
++                                newext->ee_len,
++                                nearex, len, nearex + 1, nearex + 2);
 +                      memmove(nearex + 2, nearex + 1, len);
 +              }
 +              path[depth].p_ext = nearex + 1;
@@ -1133,9 +1163,9 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
++                        "move %d from 0x%p to 0x%p\n",
++                        newext->ee_block, newext->ee_start, newext->ee_len,
++                        nearex, len, nearex + 1, nearex + 2);
 +              memmove(nearex + 1, nearex, len);
 +              path[depth].p_ext = nearex;
 +      }
@@ -1156,8 +1186,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              /* merge with next extent! */
 +              nearex->ee_len += nearex[1].ee_len;
 +              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
++                      len = (EXT_LAST_EXTENT(eh) - nearex - 1) *
++                              sizeof(struct ext3_extent);
 +                      memmove(nearex + 1, nearex + 2, len);
 +              }
 +              eh->eh_entries--;
@@ -1187,7 +1217,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +                      unsigned long num, ext_prepare_callback func)
 +{
 +      struct ext3_ext_path *path = NULL;
-+      struct ext3_extent *ex, cbex;
++      struct ext3_ext_cache cbex;
++      struct ext3_extent *ex;
 +      unsigned long next, start = 0, end = 0;
 +      unsigned long last = block + num;
 +      int depth, exists, err = 0;
@@ -1246,14 +1277,20 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              EXT_ASSERT(end > start);
 +
 +              if (!exists) {
-+                      cbex.ee_block = start;
-+                      cbex.ee_len = end - start;
-+                      cbex.ee_start = 0;
-+              } else
-+                      cbex = *ex;
++                      cbex.ec_block = start;
++                      cbex.ec_len = end - start;
++                      cbex.ec_start = 0;
++                      cbex.ec_type = EXT3_EXT_CACHE_GAP;
++              } else {
++                      cbex.ec_block = ex->ee_block;
++                      cbex.ec_len = ex->ee_len;
++                      cbex.ec_start = ex->ee_start;
++                      cbex.ec_type = EXT3_EXT_CACHE_EXTENT;
++              }
 +
++              EXT_ASSERT(cbex.ec_len > 0);
 +              EXT_ASSERT(path[depth].p_hdr);
-+              err = func(tree, path, &cbex, exists);
++              err = func(tree, path, &cbex);
 +              ext3_ext_drop_refs(path);
 +
 +              if (err < 0)
@@ -1271,7 +1308,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +                      path = NULL;
 +              }
 +
-+              block = cbex.ee_block + cbex.ee_len;
++              block = cbex.ec_block + cbex.ec_len;
 +      }
 +
 +      if (path) {
@@ -1284,7 +1321,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static inline void
 +ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
++                    __u32 len, __u32 start, int type)
 +{
 +      EXT_ASSERT(len > 0);
 +      if (tree->cex) {
@@ -1301,8 +1338,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
++                        struct ext3_ext_path *path,
++                        unsigned long block)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      unsigned long lblock, len;
@@ -1321,16 +1358,16 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              lblock = block;
 +              len = ex->ee_block - block;
 +              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len);
 +      } else if (block >= ex->ee_block + ex->ee_len) {
 +              lblock = ex->ee_block + ex->ee_len;
 +              len = ext3_ext_next_allocated_block(path);
 +              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) block);
 +              EXT_ASSERT(len > lblock);
 +              len = len - lblock;
 +      } else {
@@ -1344,7 +1381,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static inline int
 +ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
++                struct ext3_extent *ex)
 +{
 +      struct ext3_ext_cache *cex = tree->cex;
 +
@@ -1357,16 +1394,16 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              return EXT3_EXT_CACHE_NO;
 +
 +      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
++                 cex->ec_type == EXT3_EXT_CACHE_EXTENT);
 +      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
 +              ex->ee_block = cex->ec_block;
 +              ex->ee_start = cex->ec_start;
 +              ex->ee_len = cex->ec_len;
 +              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) ex->ee_start);
 +              return cex->ec_type;
 +      }
 +
@@ -1380,7 +1417,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 + * last index in the block only
 + */
 +int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
++                  struct ext3_ext_path *path)
 +{
 +      struct buffer_head *bh;
 +      int err;
@@ -1394,7 +1431,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      if ((err = ext3_ext_dirty(handle, tree, path)))
 +              return err;
 +      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +      bh = sb_get_hash_table(tree->inode->i_sb, path->p_idx->ei_leaf);
 +      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
 +      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
@@ -1402,7 +1439,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
++                                   struct ext3_ext_path *path)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      int needed;
@@ -1439,8 +1476,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++                    struct ext3_ext_path *path, unsigned long start,
++                    unsigned long end)
 +{
 +      struct ext3_extent *ex, tex;
 +      struct ext3_ext_path *npath;
@@ -1474,7 +1511,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      /* FIXME: some callback to free underlying resource
 +       * and correct ee_start? */
 +      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
++                ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
 +
 +      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
 +      if (IS_ERR(npath))
@@ -1488,13 +1525,12 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      kfree(npath);
 +
 +      return err;
-+                      
 +}
 +
 +static int
 +ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++               struct ext3_ext_path *path, unsigned long start,
++               unsigned long end)
 +{
 +      struct ext3_extent *ex, *fu = NULL, *lu, *le;
 +      int err = 0, correct_index = 0;
@@ -1527,8 +1563,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      }
 +      
 +      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
++      while (ex >= EXT_FIRST_EXTENT(eh) && ex->ee_block + ex->ee_len > start) {
 +              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
 +              path[depth].p_ext = ex;
 +      
@@ -1555,7 +1590,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +                      block = ex->ee_block; 
 +                      num = 0;
 +                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
++                                 b == ex->ee_block + ex->ee_len - 1);
 +              }
 +
 +              if (ex == EXT_FIRST_EXTENT(eh))
@@ -1597,7 +1632,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +                      goto out;
 +
 +              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +              ex--;
 +      }
 +
@@ -1661,7 +1696,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
++                        unsigned long start, unsigned long end)
 +{
 +      struct inode *inode = tree->inode;
 +      struct super_block *sb = inode->i_sb;
@@ -1685,8 +1720,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +       */
 +      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
 +      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
++              ext3_error(sb, __FUNCTION__, "Can't allocate path array");
 +              ext3_journal_stop(handle, inode);
 +              return -ENOMEM;
 +      }
@@ -1718,19 +1752,19 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +                              ext3_ext_last_covered(path[i].p_hdr, end);
 +                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
 +                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
++                                path[i].p_hdr, path[i].p_hdr->eh_entries);
 +              } else {
 +                      /* we've already was here, see at next index */
 +                      path[i].p_idx--;
 +              }
 +
 +              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
++                        i, EXT_FIRST_INDEX(path[i].p_hdr),
++                        path[i].p_idx);
 +              if (ext3_ext_more_to_rm(path + i)) {
 +                      /* go to the next level */
 +                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
++                                i + 1, path[i].p_idx->ei_leaf);
 +                      memset(path + i + 1, 0, sizeof(*path));
 +                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
 +                      if (!path[i+1].p_bh) {
@@ -1823,7 +1857,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +}
 +
 +static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                           struct ext3_extent *ex2)
 +{
 +      /* FIXME: support for large fs */
 +      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
@@ -1833,8 +1867,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                         struct ext3_extent *ex,
++                         unsigned long from, unsigned long to)
 +{
 +      int needed;
 +      
@@ -1849,8 +1883,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                 struct ext3_extent *ex,
++                 unsigned long from, unsigned long to)
 +{
 +      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
 +      handle_t *handle = ext3_journal_start(tree->inode, needed);
@@ -1865,7 +1899,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              num = ex->ee_block + ex->ee_len - from;
 +              start = ex->ee_start + ex->ee_len - num;
 +              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
++                        num, start);
 +              for (i = 0; i < num; i++) {
 +                      bh = sb_get_hash_table(tree->inode->i_sb, start + i);
 +                      ext3_forget(handle, 0, tree->inode, bh, start + i);
@@ -1873,17 +1907,17 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              ext3_free_blocks(handle, tree->inode, start, num);
 +      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
 +              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      } else {
 +              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      }
 +      ext3_journal_stop(handle, tree->inode);
 +      return 0;
 +}
 +
 +int ext3_ext_find_goal(struct inode *inode, struct ext3_ext_path *path,
-+                      unsigned long block)
++                     unsigned long block)
 +{
 +      struct ext3_inode_info *ei = EXT3_I(inode);
 +      unsigned long bg_start;
@@ -1913,8 +1947,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +}
 +
 +static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
++                           struct ext3_ext_path *path,
++                           struct ext3_extent *ex, int *err)
 +{
 +      struct inode *inode = tree->inode;
 +      int newblock, goal;
@@ -1951,7 +1985,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +};
 +
 +void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
++                       struct inode *inode)
 +{
 +      tree->inode = inode;
 +      tree->root = (void *) EXT3_I(inode)->i_data;
@@ -1962,7 +1996,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result, int create)
++                     long iblock, struct buffer_head *bh_result, int create)
 +{
 +      struct ext3_ext_path *path = NULL;
 +      struct ext3_extent newex;
@@ -1973,7 +2007,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      clear_bit(BH_New, &bh_result->b_state);
 +      ext3_init_tree_desc(&tree, inode);
 +      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
++                (int) iblock, (unsigned) inode->i_ino);
 +      down_write(&EXT3_I(inode)->truncate_sem);
 +
 +      /* check in cache */
@@ -2016,11 +2050,11 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
 +                      newblock = iblock - ex->ee_block + ex->ee_start;
 +                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
++                                (int) iblock, ex->ee_block, ex->ee_len,
++                                newblock);
 +                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
++                                            ex->ee_len, ex->ee_start,
++                                            EXT3_EXT_CACHE_EXTENT);
 +                      goto out;
 +              }
 +      }
@@ -2041,7 +2075,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      if (!newblock)
 +              goto out2;
 +      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
++                goal, newblock);
 +
 +      /* try to insert new extent into found leaf and return */
 +      newex.ee_block = iblock;
@@ -2059,7 +2093,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      set_bit(BH_New, &bh_result->b_state);
 +
 +      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
++                            newex.ee_start, EXT3_EXT_CACHE_EXTENT);
 +out:
 +      ext3_ext_show_leaf(&tree, path);
 +      set_bit(BH_Mapped, &bh_result->b_state);
@@ -2096,7 +2130,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +      if (page)
 +              ext3_block_truncate_page(handle, mapping, inode->i_size, page, 
-+                                      inode->i_sb->s_blocksize);
++                                       inode->i_sb->s_blocksize);
 +
 +      down_write(&EXT3_I(inode)->truncate_sem);
 +      ext3_ext_invalidate_cache(&tree);
@@ -2113,8 +2147,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +      EXT3_I(inode)->i_disksize = inode->i_size;
 +      ext3_mark_inode_dirty(handle, inode);
 +
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
++      last_block = (inode->i_size + sb->s_blocksize - 1) >>
++                      EXT3_BLOCK_SIZE_BITS(sb);
 +      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
 +      
 +      /* In a multi-transaction truncate, we only make the final
@@ -2181,13 +2215,14 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *newex, int exist)
++                       struct ext3_ext_path *path,
++                       struct ext3_ext_cache *newex)
 +{
 +      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
 +
-+      if (!exist)
++      if (newex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
++
 +      if (buf->err < 0)
 +              return EXT_BREAK;
 +      if (buf->cur - buf->buffer + sizeof(*newex) > buf->buflen)
@@ -2205,14 +2240,14 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *ex, int exist)
++                        struct ext3_ext_path *path,
++                        struct ext3_ext_cache *ex)
 +{
 +      struct ext3_extent_tree_stats *buf =
 +              (struct ext3_extent_tree_stats *) tree->private;
 +      int depth;
 +
-+      if (!exist)
++      if (ex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
 +
 +      depth = EXT_DEPTH(tree);
@@ -2243,7 +2278,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              tree.private = &buf;
 +              down_write(&EXT3_I(inode)->truncate_sem);
 +              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
++                                        ext3_ext_store_extent_cb);
 +              up_write(&EXT3_I(inode)->truncate_sem);
 +              if (err == 0)
 +                      err = buf.err;
@@ -2258,7 +2293,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +              buf.leaf_num = 0;
 +              tree.private = &buf;
 +              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
++                                        ext3_ext_collect_stats_cb);
 +              up_write(&EXT3_I(inode)->truncate_sem);
 +              if (!err)
 +                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
@@ -2280,22 +2315,18 @@ Index: linux-2.4.21-20.EL/fs/ext3/extents.c
 +EXPORT_SYMBOL(ext3_ext_walk_space);
 +EXPORT_SYMBOL(ext3_ext_find_goal);
 +EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
-Index: linux-2.4.21-20.EL/fs/ext3/ialloc.c
+Index: linux-2.4.21-rhel/fs/ext3/ialloc.c
 ===================================================================
---- linux-2.4.21-20.EL.orig/fs/ext3/ialloc.c   2004-11-02 20:43:27.000000000 +0300
-+++ linux-2.4.21-20.EL/fs/ext3/ialloc.c        2004-11-02 20:53:34.000000000 +0300
-@@ -596,9 +596,22 @@
+--- linux-2.4.21-rhel.orig/fs/ext3/ialloc.c    2005-03-04 00:44:34.000000000 +0300
++++ linux-2.4.21-rhel/fs/ext3/ialloc.c 2005-03-04 00:44:35.000000000 +0300
+@@ -596,6 +596,19 @@
                iloc.bh = NULL;
                goto fail;
        }
--      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
--      if (err) goto fail;
-  
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
-+              ext3_extents_initialize_blockmap(handle, inode);
++      if (test_opt(sb, EXTENTS) && S_ISREG(inode->i_mode)) {
++              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
++              memset(&EXT3_I(inode)->i_cached_extent, 0, sizeof(__u32) * 4);
++              ext3_extents_initialize_blockmap(handle, inode);
 +              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
 +                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
 +                      if (err) goto fail;
@@ -2303,29 +2334,27 @@ Index: linux-2.4.21-20.EL/fs/ext3/ialloc.c
 +                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
 +                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
 +              }
-+      }
-+  
-+      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
-+      if (err) goto fail;
- #ifdef CONFIG_EXT3_FS_XATTR
-Index: linux-2.4.21-20.EL/fs/ext3/inode.c
++      }
++
+       err = ext3_mark_iloc_dirty(handle, inode, &iloc);
+       if (err) goto fail;
+  
+Index: linux-2.4.21-rhel/fs/ext3/inode.c
 ===================================================================
---- linux-2.4.21-20.EL.orig/fs/ext3/inode.c    2004-11-02 20:43:31.000000000 +0300
-+++ linux-2.4.21-20.EL/fs/ext3/inode.c 2004-11-02 20:53:34.000000000 +0300
+--- linux-2.4.21-rhel.orig/fs/ext3/inode.c     2005-03-04 00:44:34.000000000 +0300
++++ linux-2.4.21-rhel/fs/ext3/inode.c  2005-03-04 00:44:35.000000000 +0300
 @@ -859,6 +859,16 @@
        goto reread;
  }
  
 +static inline int
 +ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create, int extend_disksize)
++                  struct buffer_head *bh, int create, int extend_disksize)
 +{
 +      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
 +              return ext3_ext_get_block(handle, inode, block, bh, create);
 +      return ext3_get_block_handle(handle, inode, block, bh, create,
-+                                      extend_disksize);
++                                   extend_disksize);
 +}
 +
  /*
@@ -2363,8 +2392,8 @@ Index: linux-2.4.21-20.EL/fs/ext3/inode.c
        if (IS_ERR(page))
                return;
 +
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_truncate(inode, page);
++      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
++              return ext3_ext_truncate(inode, page);
        
        handle = start_transaction(inode);
        if (IS_ERR(handle))
@@ -2372,7 +2401,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/inode.c
        for (block = 0; block < EXT3_N_BLOCKS; block++)
                ei->i_data[block] = iloc.raw_inode->i_block[block];
        INIT_LIST_HEAD(&ei->i_orphan);
-+      memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
++      memset(&EXT3_I(inode)->i_cached_extent, 0, sizeof(__u32) * 4);
  
        if (EXT3_INODE_SIZE(inode->i_sb) > EXT3_GOOD_OLD_INODE_SIZE)
                EXT3_I(inode)->i_extra_isize =
@@ -2404,10 +2433,10 @@ Index: linux-2.4.21-20.EL/fs/ext3/inode.c
                  if (rc) {
                          printk(KERN_INFO "ext3_map_inode_page: error %d "
                                 "allocating block %ld\n", rc, iblock);
-Index: linux-2.4.21-20.EL/fs/ext3/Makefile
+Index: linux-2.4.21-rhel/fs/ext3/Makefile
 ===================================================================
---- linux-2.4.21-20.EL.orig/fs/ext3/Makefile   2004-11-02 20:43:19.000000000 +0300
-+++ linux-2.4.21-20.EL/fs/ext3/Makefile        2004-11-02 20:53:34.000000000 +0300
+--- linux-2.4.21-rhel.orig/fs/ext3/Makefile    2005-03-04 00:44:33.000000000 +0300
++++ linux-2.4.21-rhel/fs/ext3/Makefile 2005-03-04 00:44:35.000000000 +0300
 @@ -9,10 +9,11 @@
  
  O_TARGET := ext3.o
@@ -2422,11 +2451,11 @@ Index: linux-2.4.21-20.EL/fs/ext3/Makefile
  obj-m    := $(O_TARGET)
  
  export-objs += xattr.o
-Index: linux-2.4.21-20.EL/fs/ext3/super.c
+Index: linux-2.4.21-rhel/fs/ext3/super.c
 ===================================================================
---- linux-2.4.21-20.EL.orig/fs/ext3/super.c    2004-11-02 20:43:27.000000000 +0300
-+++ linux-2.4.21-20.EL/fs/ext3/super.c 2004-11-02 20:53:34.000000000 +0300
-@@ -648,6 +648,7 @@
+--- linux-2.4.21-rhel.orig/fs/ext3/super.c     2005-03-04 00:44:34.000000000 +0300
++++ linux-2.4.21-rhel/fs/ext3/super.c  2005-03-04 00:44:35.000000000 +0300
+@@ -556,6 +556,7 @@
  #ifdef EXT3_DELETE_THREAD
        J_ASSERT(sbi->s_delete_inodes == 0);
  #endif
@@ -2434,7 +2463,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/super.c
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
        if (!(sb->s_flags & MS_RDONLY)) {
-@@ -851,6 +852,10 @@
+@@ -755,6 +756,10 @@
                                return 0;
                        }
                }
@@ -2445,7 +2474,7 @@ Index: linux-2.4.21-20.EL/fs/ext3/super.c
                else if (!strcmp (this_char, "grpid") ||
                         !strcmp (this_char, "bsdgroups"))
                        set_opt (*mount_options, GRPID);
-@@ -1546,6 +1551,8 @@
+@@ -1450,6 +1455,8 @@
                test_opt(sb,DATA_FLAGS) == EXT3_MOUNT_ORDERED_DATA ? "ordered":
                "writeback");
  
@@ -2454,10 +2483,10 @@ Index: linux-2.4.21-20.EL/fs/ext3/super.c
        return sb;
  
  failed_mount3:
-Index: linux-2.4.21-20.EL/fs/ext3/ioctl.c
+Index: linux-2.4.21-rhel/fs/ext3/ioctl.c
 ===================================================================
---- linux-2.4.21-20.EL.orig/fs/ext3/ioctl.c    2004-11-02 20:43:14.000000000 +0300
-+++ linux-2.4.21-20.EL/fs/ext3/ioctl.c 2004-11-02 20:53:34.000000000 +0300
+--- linux-2.4.21-rhel.orig/fs/ext3/ioctl.c     2005-03-04 00:44:32.000000000 +0300
++++ linux-2.4.21-rhel/fs/ext3/ioctl.c  2005-03-04 00:44:35.000000000 +0300
 @@ -173,6 +173,10 @@
                        return ret;
                }
@@ -2469,25 +2498,28 @@ Index: linux-2.4.21-20.EL/fs/ext3/ioctl.c
        default:
                return -ENOTTY;
        }
-Index: linux-2.4.21-20.EL/include/linux/ext3_fs.h
+Index: linux-2.4.21-rhel/include/linux/ext3_fs.h
 ===================================================================
---- linux-2.4.21-20.EL.orig/include/linux/ext3_fs.h    2004-11-02 20:43:27.000000000 +0300
-+++ linux-2.4.21-20.EL/include/linux/ext3_fs.h 2004-11-02 20:53:34.000000000 +0300
-@@ -188,6 +188,7 @@
+--- linux-2.4.21-rhel.orig/include/linux/ext3_fs.h     2005-03-04 00:44:34.000000000 +0300
++++ linux-2.4.21-rhel/include/linux/ext3_fs.h  2005-03-04 00:44:35.000000000 +0300
+@@ -188,8 +188,9 @@
  #define EXT3_IMAGIC_FL                        0x00002000 /* AFS directory */
  #define EXT3_JOURNAL_DATA_FL          0x00004000 /* file data should be journaled */
  #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
 +#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
  
- #define EXT3_FL_USER_VISIBLE          0x00005FFF /* User visible flags */
+-#define EXT3_FL_USER_VISIBLE          0x00005FFF /* User visible flags */
++#define EXT3_FL_USER_VISIBLE          0x00085FFF /* User visible flags */
  #define EXT3_FL_USER_MODIFIABLE               0x000000FF /* User modifiable flags */
+ /*
 @@ -212,6 +213,9 @@
  #ifdef CONFIG_JBD_DEBUG
  #define EXT3_IOC_WAIT_FOR_READONLY    _IOR('f', 99, long)
  #endif
-+#define       EXT3_IOC_GET_EXTENTS            _IOR('f', 5, long)
-+#define       EXT3_IOC_GET_TREE_DEPTH         _IOR('f', 6, long)
-+#define       EXT3_IOC_GET_TREE_STATS         _IOR('f', 7, long)
++#define EXT3_IOC_GET_EXTENTS          _IOR('f', 5, long)
++#define EXT3_IOC_GET_TREE_DEPTH               _IOR('f', 6, long)
++#define EXT3_IOC_GET_TREE_STATS               _IOR('f', 7, long)
  
  /*
   * Structure of an inode on the disk
@@ -2518,7 +2550,7 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_fs.h
  extern unsigned long ext3_count_free (struct buffer_head *, unsigned);
  
  /* inode.c */
-+int ext3_block_truncate_page(handle_t *, struct address_space *, loff_t,
++extern int ext3_block_truncate_page(handle_t *, struct address_space *, loff_t,
 +                                  struct page *, unsigned);
  extern int ext3_forget(handle_t *, int, struct inode *, struct buffer_head *, int);
  extern struct buffer_head * ext3_getblk (handle_t *, struct inode *, long, int, int *);
@@ -2530,7 +2562,7 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_fs.h
 +/* extents.c */
 +extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
 +extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                              struct buffer_head *, int);
++                            struct buffer_head *, int);
 +extern void ext3_ext_truncate(struct inode *, struct page *);
 +extern void ext3_ext_init(struct super_block *);
 +extern void ext3_ext_release(struct super_block *);
@@ -2540,11 +2572,11 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_fs.h
  
  #endif        /* __KERNEL__ */
  
-Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
+Index: linux-2.4.21-rhel/include/linux/ext3_extents.h
 ===================================================================
---- linux-2.4.21-20.EL.orig/include/linux/ext3_extents.h       2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.21-20.EL/include/linux/ext3_extents.h    2004-11-02 20:53:34.000000000 +0300
-@@ -0,0 +1,251 @@
+--- linux-2.4.21-rhel.orig/include/linux/ext3_extents.h        2005-03-02 22:42:20.659360368 +0300
++++ linux-2.4.21-rhel/include/linux/ext3_extents.h     2005-03-04 02:34:52.000000000 +0300
+@@ -0,0 +1,263 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -2586,7 +2618,7 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
 + */
 +#define EXT_DEBUG_
 +#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
++#define ext_debug(tree,fmt,a...)                      \
 +do {                                                  \
 +      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
 +              printk(fmt, ##a);                       \
@@ -2699,14 +2731,14 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
 +      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
 +      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
 +      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
++                                   struct ext3_extent *, unsigned long,
++                                   unsigned long);
 +      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
++                           struct ext3_extent *, unsigned long,
++                           unsigned long);
 +      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
++                       struct ext3_ext_path *, struct ext3_extent *,
++                       int *);
 +};
 +
 +/*
@@ -2716,8 +2748,8 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
 + * callback must return valid extent (passed or newly created)
 + */
 +typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_extent *, int);
++                                  struct ext3_ext_path *,
++                                  struct ext3_ext_cache *);
 +
 +#define EXT_CONTINUE  0
 +#define EXT_BREAK     1
@@ -2725,7 +2757,6 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
 +
 +
 +#define EXT_MAX_BLOCK 0xffffffff
-+#define EXT_CACHE_MARK        0xffff
 +
 +
 +#define EXT_FIRST_EXTENT(__hdr__) \
@@ -2757,6 +2788,20 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
 +
 +#define EXT_ASSERT(__x__) if (!(__x__)) BUG();
 +
++#define EXT_CHECK_PATH(tree,path)                                     \
++{                                                                     \
++      int depth = EXT_DEPTH(tree);                                    \
++      BUG_ON((unsigned long) (path) < __PAGE_OFFSET);                 \
++      BUG_ON((unsigned long) (path)[depth].p_idx <                    \
++                      __PAGE_OFFSET && (path)[depth].p_idx != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_ext <                    \
++                      __PAGE_OFFSET && (path)[depth].p_ext != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_hdr < __PAGE_OFFSET);    \
++      BUG_ON((unsigned long) (path)[depth].p_bh < __PAGE_OFFSET       \
++                      && depth != 0);                                 \
++      BUG_ON((path)[0].p_depth != depth);                             \
++}
++
 +
 +/*
 + * this structure is used to gather extents from the tree via ioctl
@@ -2778,7 +2823,7 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
 +      int leaf_num;
 +};
 +
-+void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
++extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
 +extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
 +extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
@@ -2795,17 +2840,16 @@ Index: linux-2.4.21-20.EL/include/linux/ext3_extents.h
 +
 +
 +#endif /* _LINUX_EXT3_EXTENTS */
-+
-Index: linux-2.4.21-20.EL/include/linux/ext3_fs_i.h
+Index: linux-2.4.21-rhel/include/linux/ext3_fs_i.h
 ===================================================================
---- linux-2.4.21-20.EL.orig/include/linux/ext3_fs_i.h  2004-11-02 20:43:27.000000000 +0300
-+++ linux-2.4.21-20.EL/include/linux/ext3_fs_i.h       2004-11-02 20:58:19.000000000 +0300
+--- linux-2.4.21-rhel.orig/include/linux/ext3_fs_i.h   2005-03-04 00:44:34.000000000 +0300
++++ linux-2.4.21-rhel/include/linux/ext3_fs_i.h        2005-03-04 01:56:36.000000000 +0300
 @@ -90,6 +90,8 @@
         * by other means, so we have truncate_sem.
         */
        struct rw_semaphore truncate_sem;
 +
-+      __u32 i_cached_extent[4];
++      __u32 i_cached_extent[4];
  };
  
  #endif        /* _LINUX_EXT3_FS_I */
index 2e467d6..7cfd7ee 100644 (file)
@@ -2,9 +2,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 ===================================================================
 --- linux-2.4.21-suse2.orig/fs/ext3/extents.c  2003-01-30 13:24:37.000000000 +0300
 +++ linux-2.4.21-suse2/fs/ext3/extents.c       2004-11-03 00:34:45.404241880 +0300
-@@ -0,0 +1,2269 @@
+@@ -0,0 +1,2303 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -49,6 +49,27 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +#include <linux/ext3_extents.h>
 +#include <asm/uaccess.h>
 +
++
++static inline int ext3_ext_check_header(struct ext3_extent_header *eh)
++{
++      if (eh->eh_magic != EXT3_EXT_MAGIC) {
++              printk(KERN_ERR "EXT3-fs: invalid magic = 0x%x\n",
++                     (unsigned)eh->eh_magic);
++              return -EIO;
++      }
++      if (eh->eh_max == 0) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_max = %u\n",
++                     (unsigned)eh->eh_max);
++              return -EIO;
++      }
++      if (eh->eh_entries > eh->eh_max) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_entries = %u\n",
++                     (unsigned)eh->eh_entries);
++              return -EIO;
++      }
++      return 0;
++}
++
 +static handle_t *ext3_ext_journal_restart(handle_t *handle, int needed)
 +{
 +      int err;
@@ -86,8 +107,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + *  - ENOMEM
 + */
 +static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_extents_tree *tree,
++                             struct ext3_ext_path *path)
 +{
 +      int err;
 +
@@ -108,7 +129,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + *  - EIO
 + */
 +static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                        struct ext3_ext_path *path)
 +{
 +      int err;
 +      if (path->p_bh) {
@@ -123,8 +144,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static int inline
 +ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
++                 struct ext3_ext_path *path, struct ext3_extent *ex,
++                 int *err)
 +{
 +      int goal, depth, newblock;
 +      struct inode *inode;
@@ -143,7 +164,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              unsigned long colour;
 +
 +              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
++                          EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
 +                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
 +              colour = (current->pid % 16) *
 +                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
@@ -166,8 +187,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 6;
 +#endif
@@ -179,8 +200,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent_idx);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 5;
 +#endif
@@ -191,8 +212,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      sizeof(struct ext3_extent);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 3;
 +#endif
@@ -203,9 +224,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 4;
 +#endif
@@ -213,7 +233,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int k, l = path->p_depth;
@@ -222,12 +242,12 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      for (k = 0; k <= l; k++, path++) {
 +              if (path->p_idx) {
 +                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
++                                path->p_idx->ei_leaf);
 +              } else if (path->p_ext) {
 +                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
++                                path->p_ext->ee_block,
++                                path->p_ext->ee_len,
++                                path->p_ext->ee_start);
 +              } else
 +                      ext_debug(tree, "  []");
 +      }
@@ -236,7 +256,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int depth = EXT_DEPTH(tree);
@@ -252,7 +272,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +      for (i = 0; i < eh->eh_entries; i++, ex++) {
 +              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +      }
 +      ext_debug(tree, "\n");
 +#endif
@@ -263,11 +283,12 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      int depth = path->p_depth;
 +      int i;
 +
-+      for (i = 0; i <= depth; i++, path++)
++      for (i = 0; i <= depth; i++, path++) {
 +              if (path->p_bh) {
 +                      brelse(path->p_bh);
 +                      path->p_bh = NULL;
 +              }
++      }
 +}
 +
 +/*
@@ -275,7 +296,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                     struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent_idx *ix;
@@ -301,7 +322,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +      ix += l;
 +      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
++      ext_debug(tree," -> %d->%d ",path->p_idx->ei_block,path->p_idx->ei_leaf);
 +
 +      while (l++ < r) {
 +              if (block < ix->ei_block) 
@@ -309,7 +330,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              path->p_idx = ix++;
 +      }
 +      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -319,9 +340,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              for (k = 0; k < eh->eh_entries; k++, ix++) {
 +                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
 +                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
++                                     ix, EXT_FIRST_INDEX(eh));
 +                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
++                                     ix->ei_block,ix[-1].ei_block);
 +                      }
 +                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
 +                      if (block < ix->ei_block) 
@@ -331,7 +352,6 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              EXT_ASSERT(chix == path->p_idx);
 +      }
 +#endif
-+
 +}
 +
 +/*
@@ -339,7 +359,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                 struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent *ex;
@@ -373,7 +393,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      ex += l;
 +      path->p_ext = ex;
 +      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +      while (l++ < r) {
 +              if (block < ex->ee_block) 
@@ -381,7 +401,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              path->p_ext = ex++;
 +      }
 +      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -397,7 +417,6 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              EXT_ASSERT(chex == path->p_ext);
 +      }
 +#endif
-+
 +}
 +
 +int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
@@ -418,7 +437,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +struct ext3_ext_path *
 +ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
++                   struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      struct buffer_head *bh;
@@ -430,15 +449,17 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +      eh = EXT_ROOT_HDR(tree);
 +      EXT_ASSERT(eh);
++      if (ext3_ext_check_header(eh))
++              goto err;
++
 +      i = depth = EXT_DEPTH(tree);
 +      EXT_ASSERT(eh->eh_max);
 +      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(i == 0 || eh->eh_entries > 0);
 +      
 +      /* account possible depth increase */
 +      if (!path) {
 +              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
++                             GFP_NOFS);
 +              if (!path)
 +                      return ERR_PTR(-ENOMEM);
 +      }
@@ -448,29 +469,34 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      /* walk through the tree */
 +      while (i) {
 +              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
++                        ppos, eh->eh_entries, eh->eh_max);
 +              ext3_ext_binsearch_idx(tree, path + ppos, block);
 +              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
 +              path[ppos].p_depth = i;
 +              path[ppos].p_ext = NULL;
 +
 +              bh = sb_bread(tree->inode->i_sb, path[ppos].p_block);
-+              if (!bh) {
-+                      ext3_ext_drop_refs(path);
-+                      kfree(path);
-+                      return ERR_PTR(-EIO);
-+              }
++              if (!bh)
++                      goto err;
++
 +              eh = EXT_BLOCK_HDR(bh);
 +              ppos++;
 +              EXT_ASSERT(ppos <= depth);
 +              path[ppos].p_bh = bh;
 +              path[ppos].p_hdr = eh;
 +              i--;
++
++              if (ext3_ext_check_header(eh))
++                      goto err;
 +      }
 +
 +      path[ppos].p_depth = i;
 +      path[ppos].p_hdr = eh;
 +      path[ppos].p_ext = NULL;
++      path[ppos].p_idx = NULL;
++
++      if (ext3_ext_check_header(eh))
++              goto err;
 +
 +      /* find extent */
 +      ext3_ext_binsearch(tree, path + ppos, block);
@@ -478,6 +504,12 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      ext3_ext_show_path(tree, path);
 +
 +      return path;
++
++err:
++      printk(KERN_ERR "EXT3-fs: header is corrupted!\n");
++      ext3_ext_drop_refs(path);
++      kfree(path);
++      return ERR_PTR(-EIO);
 +}
 +
 +/*
@@ -485,9 +517,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + * it check where to insert: before curp or after curp
 + */
 +static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *curp,
++                               int logical, int ptr)
 +{
 +      struct ext3_extent_idx *ix;
 +      int len, err;
@@ -503,9 +535,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent_idx);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
++                                "move %d from 0x%p to 0x%p\n",
++                                logical, ptr, len,
++                                (curp->p_idx + 1), (curp->p_idx + 2));
 +                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
 +              }
 +              ix = curp->p_idx + 1;
@@ -514,9 +546,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              len = len * sizeof(struct ext3_extent_idx);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
++                        "move %d from 0x%p to 0x%p\n",
++                        logical, ptr, len,
++                        curp->p_idx, (curp->p_idx + 1));
 +              memmove(curp->p_idx + 1, curp->p_idx, len);
 +              ix = curp->p_idx;
 +      }
@@ -544,8 +576,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + *  - initialize subtree
 + */
 +static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
++                        struct ext3_ext_path *path,
++                        struct ext3_extent *newext, int at)
 +{
 +      struct buffer_head *bh = NULL;
 +      int depth = EXT_DEPTH(tree);
@@ -566,13 +598,13 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              border = path[depth].p_ext[1].ee_block;
 +              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      } else {
 +              border = newext->ee_block;
 +              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      }
 +
 +      /* 
@@ -630,12 +662,11 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      while (path[depth].p_ext <=
 +                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
++                        path[depth].p_ext->ee_block,
++                        path[depth].p_ext->ee_start,
++                        path[depth].p_ext->ee_len,
++                        newblock);
++              memmove(ex++, path[depth].p_ext++, sizeof(struct ext3_extent));
 +              neh->eh_entries++;
 +              m++;
 +      }
@@ -688,21 +719,21 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              fidx->ei_leaf = oldblock;
 +
 +              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
++                        i, newblock, border, oldblock);
 +              /* copy indexes */
 +              m = 0;
 +              path[i].p_idx++;
 +
 +              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
++                        EXT_MAX_INDEX(path[i].p_hdr));
 +              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
++                         EXT_LAST_INDEX(path[i].p_hdr));
 +              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
 +                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
++                                i, path[i].p_idx->ei_block,
++                                path[i].p_idx->ei_leaf, newblock);
 +                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
++                              sizeof(struct ext3_extent_idx));
 +                      neh->eh_entries++;
 +                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
 +                      m++;
@@ -732,7 +763,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      /* insert new index */
 +      if (!err)
 +              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
++                                          border, newblock);
 +
 +cleanup:
 +      if (bh) {
@@ -762,9 +793,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + *    just created block
 + */
 +static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *path,
++                               struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp = path;
 +      struct ext3_extent_header *neh;
@@ -823,7 +854,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      neh = EXT_ROOT_HDR(tree);
 +      fidx = EXT_FIRST_INDEX(neh);
 +      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
++                neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
 +
 +      neh->eh_depth = path->p_depth + 1;
 +      err = ext3_ext_dirty(handle, tree, curp);
@@ -838,9 +869,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + * then it requests in-depth growing
 + */
 +static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                                  struct ext3_extents_tree *tree,
++                                  struct ext3_ext_path *path,
++                                  struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp;
 +      int depth, i, err = 0;
@@ -916,12 +947,12 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              if (depth == path->p_depth) {
 +                      /* leaf */
 +                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
++                          EXT_LAST_EXTENT(path[depth].p_hdr))
 +                              return path[depth].p_ext[1].ee_block;
 +              } else {
 +                      /* index */
 +                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
++                          EXT_LAST_INDEX(path[depth].p_hdr))
 +                              return path[depth].p_idx[1].ei_block;
 +              }
 +              depth--;        
@@ -934,7 +965,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + * returns first allocated block from next leaf or EXT_MAX_BLOCK
 + */
 +static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
++                                       struct ext3_ext_path *path)
 +{
 +      int depth;
 +
@@ -950,7 +981,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      
 +      while (depth >= 0) {
 +              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
++                  EXT_LAST_INDEX(path[depth].p_hdr))
 +                      return path[depth].p_idx[1].ei_block;
 +              depth--;        
 +      }
@@ -964,7 +995,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + * TODO: do we need to correct tree in all cases?
 + */
 +int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                           struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      int depth = EXT_DEPTH(tree);    
@@ -1014,8 +1045,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static int inline
 +ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                         struct ext3_extent *ex1,
++                         struct ext3_extent *ex2)
 +{
 +      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
 +              return 0;
@@ -1037,8 +1068,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + * creating new leaf in no-space case
 + */
 +int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
++                         struct ext3_ext_path *path,
++                         struct ext3_extent *newext)
 +{
 +      struct ext3_extent_header * eh;
 +      struct ext3_extent *ex, *fex;
@@ -1047,7 +1078,6 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      int depth, len, err, next;
 +
 +      EXT_ASSERT(newext->ee_len > 0);
-+      EXT_ASSERT(newext->ee_len < EXT_CACHE_MARK);
 +      depth = EXT_DEPTH(tree);
 +      ex = path[depth].p_ext;
 +      EXT_ASSERT(path[depth].p_hdr);
@@ -1055,8 +1085,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      /* try to insert block into found extent and return */
 +      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
 +              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
++                        newext->ee_len, ex->ee_block, ex->ee_len,
++                        ex->ee_start);
 +              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
 +                      return err;
 +              ex->ee_len += newext->ee_len;
@@ -1084,12 +1114,12 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              eh = npath[depth].p_hdr;
 +              if (eh->eh_entries < eh->eh_max) {
 +                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
++                                eh->eh_entries);
 +                      path = npath;
 +                      goto repeat;
 +              }
 +              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
++                        eh->eh_entries, eh->eh_max);
 +      }
 +
 +      /*
@@ -1111,8 +1141,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      if (!nearex) {
 +              /* there is no extent in this leaf, create first one */
 +              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
++                        newext->ee_block, newext->ee_start,
++                        newext->ee_len);
 +              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
 +      } else if (newext->ee_block > nearex->ee_block) {
 +              EXT_ASSERT(newext->ee_block != nearex->ee_block);
@@ -1121,10 +1151,10 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
++                                "move %d from 0x%p to 0x%p\n",
++                                newext->ee_block, newext->ee_start,
++                                newext->ee_len,
++                                nearex, len, nearex + 1, nearex + 2);
 +                      memmove(nearex + 2, nearex + 1, len);
 +              }
 +              path[depth].p_ext = nearex + 1;
@@ -1133,9 +1163,9 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
++                        "move %d from 0x%p to 0x%p\n",
++                        newext->ee_block, newext->ee_start, newext->ee_len,
++                        nearex, len, nearex + 1, nearex + 2);
 +              memmove(nearex + 1, nearex, len);
 +              path[depth].p_ext = nearex;
 +      }
@@ -1156,8 +1186,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              /* merge with next extent! */
 +              nearex->ee_len += nearex[1].ee_len;
 +              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
++                      len = (EXT_LAST_EXTENT(eh) - nearex - 1) *
++                              sizeof(struct ext3_extent);
 +                      memmove(nearex + 1, nearex + 2, len);
 +              }
 +              eh->eh_entries--;
@@ -1187,7 +1217,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +                      unsigned long num, ext_prepare_callback func)
 +{
 +      struct ext3_ext_path *path = NULL;
-+      struct ext3_extent *ex, cbex;
++      struct ext3_ext_cache cbex;
++      struct ext3_extent *ex;
 +      unsigned long next, start = 0, end = 0;
 +      unsigned long last = block + num;
 +      int depth, exists, err = 0;
@@ -1246,14 +1277,20 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              EXT_ASSERT(end > start);
 +
 +              if (!exists) {
-+                      cbex.ee_block = start;
-+                      cbex.ee_len = end - start;
-+                      cbex.ee_start = 0;
-+              } else
-+                      cbex = *ex;
++                      cbex.ec_block = start;
++                      cbex.ec_len = end - start;
++                      cbex.ec_start = 0;
++                      cbex.ec_type = EXT3_EXT_CACHE_GAP;
++              } else {
++                      cbex.ec_block = ex->ee_block;
++                      cbex.ec_len = ex->ee_len;
++                      cbex.ec_start = ex->ee_start;
++                      cbex.ec_type = EXT3_EXT_CACHE_EXTENT;
++              }
 +
++              EXT_ASSERT(cbex.ec_len > 0);
 +              EXT_ASSERT(path[depth].p_hdr);
-+              err = func(tree, path, &cbex, exists);
++              err = func(tree, path, &cbex);
 +              ext3_ext_drop_refs(path);
 +
 +              if (err < 0)
@@ -1271,7 +1308,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +                      path = NULL;
 +              }
 +
-+              block = cbex.ee_block + cbex.ee_len;
++              block = cbex.ec_block + cbex.ec_len;
 +      }
 +
 +      if (path) {
@@ -1284,7 +1321,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static inline void
 +ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
++                    __u32 len, __u32 start, int type)
 +{
 +      EXT_ASSERT(len > 0);
 +      if (tree->cex) {
@@ -1301,8 +1338,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
++                        struct ext3_ext_path *path,
++                        unsigned long block)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      unsigned long lblock, len;
@@ -1321,16 +1358,16 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              lblock = block;
 +              len = ex->ee_block - block;
 +              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len);
 +      } else if (block >= ex->ee_block + ex->ee_len) {
 +              lblock = ex->ee_block + ex->ee_len;
 +              len = ext3_ext_next_allocated_block(path);
 +              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) block);
 +              EXT_ASSERT(len > lblock);
 +              len = len - lblock;
 +      } else {
@@ -1344,7 +1381,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static inline int
 +ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
++                struct ext3_extent *ex)
 +{
 +      struct ext3_ext_cache *cex = tree->cex;
 +
@@ -1357,16 +1394,16 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              return EXT3_EXT_CACHE_NO;
 +
 +      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
++                 cex->ec_type == EXT3_EXT_CACHE_EXTENT);
 +      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
 +              ex->ee_block = cex->ec_block;
 +              ex->ee_start = cex->ec_start;
 +              ex->ee_len = cex->ec_len;
 +              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) ex->ee_start);
 +              return cex->ec_type;
 +      }
 +
@@ -1380,7 +1417,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 + * last index in the block only
 + */
 +int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
++                  struct ext3_ext_path *path)
 +{
 +      struct buffer_head *bh;
 +      int err;
@@ -1394,7 +1431,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      if ((err = ext3_ext_dirty(handle, tree, path)))
 +              return err;
 +      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +      bh = sb_get_hash_table(tree->inode->i_sb, path->p_idx->ei_leaf);
 +      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
 +      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
@@ -1402,7 +1439,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
++                                   struct ext3_ext_path *path)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      int needed;
@@ -1439,8 +1476,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++                    struct ext3_ext_path *path, unsigned long start,
++                    unsigned long end)
 +{
 +      struct ext3_extent *ex, tex;
 +      struct ext3_ext_path *npath;
@@ -1474,7 +1511,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      /* FIXME: some callback to free underlying resource
 +       * and correct ee_start? */
 +      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
++                ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
 +
 +      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
 +      if (IS_ERR(npath))
@@ -1488,13 +1525,12 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      kfree(npath);
 +
 +      return err;
-+                      
 +}
 +
 +static int
 +ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++               struct ext3_ext_path *path, unsigned long start,
++               unsigned long end)
 +{
 +      struct ext3_extent *ex, *fu = NULL, *lu, *le;
 +      int err = 0, correct_index = 0;
@@ -1527,8 +1563,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      }
 +      
 +      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
++      while (ex >= EXT_FIRST_EXTENT(eh) && ex->ee_block + ex->ee_len > start) {
 +              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
 +              path[depth].p_ext = ex;
 +      
@@ -1555,7 +1590,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +                      block = ex->ee_block; 
 +                      num = 0;
 +                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
++                                 b == ex->ee_block + ex->ee_len - 1);
 +              }
 +
 +              if (ex == EXT_FIRST_EXTENT(eh))
@@ -1597,7 +1632,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +                      goto out;
 +
 +              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +              ex--;
 +      }
 +
@@ -1661,7 +1696,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
++                        unsigned long start, unsigned long end)
 +{
 +      struct inode *inode = tree->inode;
 +      struct super_block *sb = inode->i_sb;
@@ -1685,8 +1720,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +       */
 +      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
 +      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
++              ext3_error(sb, __FUNCTION__, "Can't allocate path array");
 +              ext3_journal_stop(handle, inode);
 +              return -ENOMEM;
 +      }
@@ -1718,19 +1752,19 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +                              ext3_ext_last_covered(path[i].p_hdr, end);
 +                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
 +                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
++                                path[i].p_hdr, path[i].p_hdr->eh_entries);
 +              } else {
 +                      /* we've already was here, see at next index */
 +                      path[i].p_idx--;
 +              }
 +
 +              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
++                        i, EXT_FIRST_INDEX(path[i].p_hdr),
++                        path[i].p_idx);
 +              if (ext3_ext_more_to_rm(path + i)) {
 +                      /* go to the next level */
 +                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
++                                i + 1, path[i].p_idx->ei_leaf);
 +                      memset(path + i + 1, 0, sizeof(*path));
 +                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
 +                      if (!path[i+1].p_bh) {
@@ -1823,7 +1857,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +}
 +
 +static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                           struct ext3_extent *ex2)
 +{
 +      /* FIXME: support for large fs */
 +      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
@@ -1833,8 +1867,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                         struct ext3_extent *ex,
++                         unsigned long from, unsigned long to)
 +{
 +      int needed;
 +      
@@ -1849,8 +1883,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                 struct ext3_extent *ex,
++                 unsigned long from, unsigned long to)
 +{
 +      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
 +      handle_t *handle = ext3_journal_start(tree->inode, needed);
@@ -1865,7 +1899,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              num = ex->ee_block + ex->ee_len - from;
 +              start = ex->ee_start + ex->ee_len - num;
 +              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
++                        num, start);
 +              for (i = 0; i < num; i++) {
 +                      bh = sb_get_hash_table(tree->inode->i_sb, start + i);
 +                      ext3_forget(handle, 0, tree->inode, bh, start + i);
@@ -1873,17 +1907,17 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              ext3_free_blocks(handle, tree->inode, start, num);
 +      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
 +              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      } else {
 +              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      }
 +      ext3_journal_stop(handle, tree->inode);
 +      return 0;
 +}
 +
 +int ext3_ext_find_goal(struct inode *inode, struct ext3_ext_path *path,
-+                      unsigned long block)
++                     unsigned long block)
 +{
 +      struct ext3_inode_info *ei = EXT3_I(inode);
 +      unsigned long bg_start;
@@ -1913,8 +1947,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +}
 +
 +static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
++                           struct ext3_ext_path *path,
++                           struct ext3_extent *ex, int *err)
 +{
 +      struct inode *inode = tree->inode;
 +      int newblock, goal;
@@ -1951,7 +1985,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +};
 +
 +void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
++                       struct inode *inode)
 +{
 +      tree->inode = inode;
 +      tree->root = (void *) EXT3_I(inode)->i_data;
@@ -1962,7 +1996,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result, int create)
++                     long iblock, struct buffer_head *bh_result, int create)
 +{
 +      struct ext3_ext_path *path = NULL;
 +      struct ext3_extent newex;
@@ -1973,7 +2007,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      clear_bit(BH_New, &bh_result->b_state);
 +      ext3_init_tree_desc(&tree, inode);
 +      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
++                (int) iblock, (unsigned) inode->i_ino);
 +      down_write(&EXT3_I(inode)->truncate_sem);
 +
 +      /* check in cache */
@@ -2016,11 +2050,11 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
 +                      newblock = iblock - ex->ee_block + ex->ee_start;
 +                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
++                                (int) iblock, ex->ee_block, ex->ee_len,
++                                newblock);
 +                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
++                                            ex->ee_len, ex->ee_start,
++                                            EXT3_EXT_CACHE_EXTENT);
 +                      goto out;
 +              }
 +      }
@@ -2041,7 +2075,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      if (!newblock)
 +              goto out2;
 +      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
++                goal, newblock);
 +
 +      /* try to insert new extent into found leaf and return */
 +      newex.ee_block = iblock;
@@ -2059,7 +2093,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      set_bit(BH_New, &bh_result->b_state);
 +
 +      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
++                            newex.ee_start, EXT3_EXT_CACHE_EXTENT);
 +out:
 +      ext3_ext_show_leaf(&tree, path);
 +      set_bit(BH_Mapped, &bh_result->b_state);
@@ -2111,8 +2145,8 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +      EXT3_I(inode)->i_disksize = inode->i_size;
 +      ext3_mark_inode_dirty(handle, inode);
 +
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
++      last_block = (inode->i_size + sb->s_blocksize - 1) >>
++                      EXT3_BLOCK_SIZE_BITS(sb);
 +      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
 +      
 +      /* In a multi-transaction truncate, we only make the final
@@ -2172,13 +2206,14 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *newex, int exist)
++                       struct ext3_ext_path *path,
++                       struct ext3_ext_cache *newex)
 +{
 +      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
 +
-+      if (!exist)
++      if (newex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
++
 +      if (buf->err < 0)
 +              return EXT_BREAK;
 +      if (buf->cur - buf->buffer + sizeof(*newex) > buf->buflen)
@@ -2196,14 +2231,14 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *ex, int exist)
++                        struct ext3_ext_path *path,
++                        struct ext3_ext_cache *ex)
 +{
 +      struct ext3_extent_tree_stats *buf =
 +              (struct ext3_extent_tree_stats *) tree->private;
 +      int depth;
 +
-+      if (!exist)
++      if (ex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
 +
 +      depth = EXT_DEPTH(tree);
@@ -2234,7 +2269,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              tree.private = &buf;
 +              down_write(&EXT3_I(inode)->truncate_sem);
 +              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
++                                        ext3_ext_store_extent_cb);
 +              up_write(&EXT3_I(inode)->truncate_sem);
 +              if (err == 0)
 +                      err = buf.err;
@@ -2249,7 +2284,7 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +              buf.leaf_num = 0;
 +              tree.private = &buf;
 +              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
++                                        ext3_ext_collect_stats_cb);
 +              up_write(&EXT3_I(inode)->truncate_sem);
 +              if (!err)
 +                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
@@ -2271,23 +2306,18 @@ Index: linux-2.4.21-suse2/fs/ext3/extents.c
 +EXPORT_SYMBOL(ext3_ext_walk_space);
 +EXPORT_SYMBOL(ext3_ext_find_goal);
 +EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
 Index: linux-2.4.21-suse2/fs/ext3/ialloc.c
 ===================================================================
 --- linux-2.4.21-suse2.orig/fs/ext3/ialloc.c   2004-11-02 20:31:37.000000000 +0300
 +++ linux-2.4.21-suse2/fs/ext3/ialloc.c        2004-11-02 20:34:00.000000000 +0300
-@@ -592,10 +592,22 @@
+@@ -592,6 +592,19 @@
                iloc.bh = NULL;
                goto fail;
        }
--      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
--      if (err) goto fail;
-- 
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
-+              ext3_extents_initialize_blockmap(handle, inode);
++      if (test_opt(sb, EXTENTS) && S_ISREG(inode->i_mode)) {
++              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
++              memset(&EXT3_I(inode)->i_cached_extent, 0, sizeof(__u32) * 4);
++              ext3_extents_initialize_blockmap(handle, inode);
 +              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
 +                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
 +                      if (err) goto fail;
@@ -2295,13 +2325,11 @@ Index: linux-2.4.21-suse2/fs/ext3/ialloc.c
 +                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
 +                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
 +              }
-+      }
-+ 
-+      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
-+      if (err) goto fail;
- #ifdef CONFIG_EXT3_FS_XATTR
-       init_rwsem(&inode->u.ext3_i.xattr_sem);
++      }
++
+       err = ext3_mark_iloc_dirty(handle, inode, &iloc);
+       if (err) goto fail;
+  
 Index: linux-2.4.21-suse2/fs/ext3/inode.c
 ===================================================================
 --- linux-2.4.21-suse2.orig/fs/ext3/inode.c    2004-11-02 20:31:38.000000000 +0300
@@ -2312,12 +2340,12 @@ Index: linux-2.4.21-suse2/fs/ext3/inode.c
  
 +static inline int
 +ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create, int extend_disksize)
++                  struct buffer_head *bh, int create, int extend_disksize)
 +{
 +      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
 +              return ext3_ext_get_block(handle, inode, block, bh, create);
 +      return ext3_get_block_handle(handle, inode, block, bh, create,
-+                                      extend_disksize);
++                                   extend_disksize);
 +}
 +
  /*
@@ -2373,7 +2401,7 @@ Index: linux-2.4.21-suse2/fs/ext3/inode.c
        for (block = 0; block < EXT3_N_BLOCKS; block++)
                inode->u.ext3_i.i_data[block] = iloc.raw_inode->i_block[block];
        INIT_LIST_HEAD(&inode->u.ext3_i.i_orphan);
-+      memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
++      memset(&EXT3_I(inode)->i_cached_extent, 0, sizeof(__u32) * 4);
  
        brelse (iloc.bh);
  
@@ -2472,21 +2500,24 @@ Index: linux-2.4.21-suse2/include/linux/ext3_fs.h
 ===================================================================
 --- linux-2.4.21-suse2.orig/include/linux/ext3_fs.h    2004-11-02 20:31:37.000000000 +0300
 +++ linux-2.4.21-suse2/include/linux/ext3_fs.h 2004-11-02 20:31:39.000000000 +0300
-@@ -184,6 +184,7 @@
+@@ -184,8 +184,9 @@
  #define EXT3_IMAGIC_FL                        0x00002000 /* AFS directory */
  #define EXT3_JOURNAL_DATA_FL          0x00004000 /* file data should be journaled */
  #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
 +#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
  
- #define EXT3_FL_USER_VISIBLE          0x00005FFF /* User visible flags */
+-#define EXT3_FL_USER_VISIBLE          0x00005FFF /* User visible flags */
++#define EXT3_FL_USER_VISIBLE          0x00085FFF /* User visible flags */
  #define EXT3_FL_USER_MODIFIABLE               0x000000FF /* User modifiable flags */
+ /*
 @@ -208,6 +209,9 @@
  #ifdef CONFIG_JBD_DEBUG
  #define EXT3_IOC_WAIT_FOR_READONLY    _IOR('f', 99, long)
  #endif
-+#define       EXT3_IOC_GET_EXTENTS            _IOR('f', 5, long)
-+#define       EXT3_IOC_GET_TREE_DEPTH         _IOR('f', 6, long)
-+#define       EXT3_IOC_GET_TREE_STATS         _IOR('f', 7, long)
++#define EXT3_IOC_GET_EXTENTS          _IOR('f', 5, long)
++#define EXT3_IOC_GET_TREE_DEPTH               _IOR('f', 6, long)
++#define EXT3_IOC_GET_TREE_STATS               _IOR('f', 7, long)
  
  /*
   * Structure of an inode on the disk
@@ -2528,7 +2559,7 @@ Index: linux-2.4.21-suse2/include/linux/ext3_fs.h
 +/* extents.c */
 +extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
 +extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                              struct buffer_head *, int);
++                            struct buffer_head *, int);
 +extern void ext3_ext_truncate(struct inode *);
 +extern void ext3_ext_init(struct super_block *);
 +extern void ext3_ext_release(struct super_block *);
@@ -2542,7 +2573,7 @@ Index: linux-2.4.21-suse2/include/linux/ext3_extents.h
 ===================================================================
 --- linux-2.4.21-suse2.orig/include/linux/ext3_extents.h       2003-01-30 13:24:37.000000000 +0300
 +++ linux-2.4.21-suse2/include/linux/ext3_extents.h    2004-11-02 20:34:00.000000000 +0300
-@@ -0,0 +1,251 @@
+@@ -0,0 +1,264 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -2584,7 +2615,7 @@ Index: linux-2.4.21-suse2/include/linux/ext3_extents.h
 + */
 +#define EXT_DEBUG_
 +#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
++#define ext_debug(tree,fmt,a...)                      \
 +do {                                                  \
 +      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
 +              printk(fmt, ##a);                       \
@@ -2697,14 +2728,14 @@ Index: linux-2.4.21-suse2/include/linux/ext3_extents.h
 +      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
 +      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
 +      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
++                                   struct ext3_extent *, unsigned long,
++                                   unsigned long);
 +      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
++                           struct ext3_extent *, unsigned long,
++                           unsigned long);
 +      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
++                       struct ext3_ext_path *, struct ext3_extent *,
++                       int *);
 +};
 +
 +/*
@@ -2714,8 +2745,8 @@ Index: linux-2.4.21-suse2/include/linux/ext3_extents.h
 + * callback must return valid extent (passed or newly created)
 + */
 +typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_extent *, int);
++                                  struct ext3_ext_path *,
++                                  struct ext3_ext_cache *);
 +
 +#define EXT_CONTINUE  0
 +#define EXT_BREAK     1
@@ -2723,7 +2754,6 @@ Index: linux-2.4.21-suse2/include/linux/ext3_extents.h
 +
 +
 +#define EXT_MAX_BLOCK 0xffffffff
-+#define EXT_CACHE_MARK        0xffff
 +
 +
 +#define EXT_FIRST_EXTENT(__hdr__) \
@@ -2755,6 +2785,20 @@ Index: linux-2.4.21-suse2/include/linux/ext3_extents.h
 +
 +#define EXT_ASSERT(__x__) if (!(__x__)) BUG();
 +
++#define EXT_CHECK_PATH(tree,path)                                     \
++{                                                                     \
++      int depth = EXT_DEPTH(tree);                                    \
++      BUG_ON((unsigned long) (path) < __PAGE_OFFSET);                 \
++      BUG_ON((unsigned long) (path)[depth].p_idx <                    \
++                      __PAGE_OFFSET && (path)[depth].p_idx != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_ext <                    \
++                      __PAGE_OFFSET && (path)[depth].p_ext != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_hdr < __PAGE_OFFSET);    \
++      BUG_ON((unsigned long) (path)[depth].p_bh < __PAGE_OFFSET       \
++                      && depth != 0);                                 \
++      BUG_ON((path)[0].p_depth != depth);                             \
++}
++
 +
 +/*
 + * this structure is used to gather extents from the tree via ioctl
@@ -2776,7 +2820,7 @@ Index: linux-2.4.21-suse2/include/linux/ext3_extents.h
 +      int leaf_num;
 +};
 +
-+void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
++extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
 +extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
 +extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
@@ -2803,7 +2847,7 @@ Index: linux-2.4.21-suse2/include/linux/ext3_fs_i.h
         */
        struct rw_semaphore truncate_sem;
 +
-+      __u32 i_cached_extent[4];
++      __u32 i_cached_extent[4];
  };
  
  #endif        /* _LINUX_EXT3_FS_I */
index 7480bde..1ad7c36 100644 (file)
@@ -2,9 +2,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 ===================================================================
 --- linux-2.4.24.orig/fs/ext3/extents.c        2003-01-30 13:24:37.000000000 +0300
 +++ linux-2.4.24/fs/ext3/extents.c     2004-11-03 00:36:44.894076664 +0300
-@@ -0,0 +1,2269 @@
+@@ -0,0 +1,2302 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -49,6 +49,27 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +#include <linux/ext3_extents.h>
 +#include <asm/uaccess.h>
 +
++
++static inline int ext3_ext_check_header(struct ext3_extent_header *eh)
++{
++      if (eh->eh_magic != EXT3_EXT_MAGIC) {
++              printk(KERN_ERR "EXT3-fs: invalid magic = 0x%x\n",
++                     (unsigned)eh->eh_magic);
++              return -EIO;
++      }
++      if (eh->eh_max == 0) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_max = %u\n",
++                     (unsigned)eh->eh_max);
++              return -EIO;
++      }
++      if (eh->eh_entries > eh->eh_max) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_entries = %u\n",
++                     (unsigned)eh->eh_entries);
++              return -EIO;
++      }
++      return 0;
++}
++
 +static handle_t *ext3_ext_journal_restart(handle_t *handle, int needed)
 +{
 +      int err;
@@ -86,8 +107,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + *  - ENOMEM
 + */
 +static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_extents_tree *tree,
++                             struct ext3_ext_path *path)
 +{
 +      int err;
 +
@@ -108,7 +129,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + *  - EIO
 + */
 +static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                        struct ext3_ext_path *path)
 +{
 +      int err;
 +      if (path->p_bh) {
@@ -123,8 +144,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static int inline
 +ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
++                 struct ext3_ext_path *path, struct ext3_extent *ex,
++                 int *err)
 +{
 +      int goal, depth, newblock;
 +      struct inode *inode;
@@ -143,7 +164,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              unsigned long colour;
 +
 +              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
++                          EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
 +                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
 +              colour = (current->pid % 16) *
 +                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
@@ -166,8 +187,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 6;
 +#endif
@@ -179,8 +200,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent_idx);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 5;
 +#endif
@@ -191,8 +212,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      sizeof(struct ext3_extent);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 3;
 +#endif
@@ -203,9 +224,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 4;
 +#endif
@@ -213,7 +233,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int k, l = path->p_depth;
@@ -222,12 +242,12 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      for (k = 0; k <= l; k++, path++) {
 +              if (path->p_idx) {
 +                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
++                                path->p_idx->ei_leaf);
 +              } else if (path->p_ext) {
 +                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
++                                path->p_ext->ee_block,
++                                path->p_ext->ee_len,
++                                path->p_ext->ee_start);
 +              } else
 +                      ext_debug(tree, "  []");
 +      }
@@ -236,7 +256,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int depth = EXT_DEPTH(tree);
@@ -252,7 +272,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +      for (i = 0; i < eh->eh_entries; i++, ex++) {
 +              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +      }
 +      ext_debug(tree, "\n");
 +#endif
@@ -263,11 +283,12 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      int depth = path->p_depth;
 +      int i;
 +
-+      for (i = 0; i <= depth; i++, path++)
++      for (i = 0; i <= depth; i++, path++) {
 +              if (path->p_bh) {
 +                      brelse(path->p_bh);
 +                      path->p_bh = NULL;
 +              }
++      }
 +}
 +
 +/*
@@ -275,7 +296,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                     struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent_idx *ix;
@@ -301,7 +322,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +      ix += l;
 +      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
++      ext_debug(tree," -> %d->%d ",path->p_idx->ei_block,path->p_idx->ei_leaf);
 +
 +      while (l++ < r) {
 +              if (block < ix->ei_block) 
@@ -309,7 +330,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              path->p_idx = ix++;
 +      }
 +      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -319,9 +340,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              for (k = 0; k < eh->eh_entries; k++, ix++) {
 +                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
 +                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
++                                     ix, EXT_FIRST_INDEX(eh));
 +                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
++                                     ix->ei_block,ix[-1].ei_block);
 +                      }
 +                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
 +                      if (block < ix->ei_block) 
@@ -331,7 +352,6 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              EXT_ASSERT(chix == path->p_idx);
 +      }
 +#endif
-+
 +}
 +
 +/*
@@ -339,7 +359,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                 struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent *ex;
@@ -373,7 +393,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      ex += l;
 +      path->p_ext = ex;
 +      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +      while (l++ < r) {
 +              if (block < ex->ee_block) 
@@ -381,7 +401,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              path->p_ext = ex++;
 +      }
 +      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -397,7 +417,6 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              EXT_ASSERT(chex == path->p_ext);
 +      }
 +#endif
-+
 +}
 +
 +int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
@@ -418,7 +437,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +struct ext3_ext_path *
 +ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
++                   struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      struct buffer_head *bh;
@@ -430,15 +449,17 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +      eh = EXT_ROOT_HDR(tree);
 +      EXT_ASSERT(eh);
++      if (ext3_ext_check_header(eh))
++              goto err;
++
 +      i = depth = EXT_DEPTH(tree);
 +      EXT_ASSERT(eh->eh_max);
 +      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(i == 0 || eh->eh_entries > 0);
 +      
 +      /* account possible depth increase */
 +      if (!path) {
 +              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
++                             GFP_NOFS);
 +              if (!path)
 +                      return ERR_PTR(-ENOMEM);
 +      }
@@ -448,29 +469,33 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      /* walk through the tree */
 +      while (i) {
 +              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
++                        ppos, eh->eh_entries, eh->eh_max);
 +              ext3_ext_binsearch_idx(tree, path + ppos, block);
 +              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
 +              path[ppos].p_depth = i;
 +              path[ppos].p_ext = NULL;
 +
 +              bh = sb_bread(tree->inode->i_sb, path[ppos].p_block);
-+              if (!bh) {
-+                      ext3_ext_drop_refs(path);
-+                      kfree(path);
-+                      return ERR_PTR(-EIO);
-+              }
++              if (!bh)
++                      goto err;
 +              eh = EXT_BLOCK_HDR(bh);
 +              ppos++;
 +              EXT_ASSERT(ppos <= depth);
 +              path[ppos].p_bh = bh;
 +              path[ppos].p_hdr = eh;
 +              i--;
++
++              if (ext3_ext_check_header(eh))
++                      goto err;
 +      }
 +
 +      path[ppos].p_depth = i;
 +      path[ppos].p_hdr = eh;
 +      path[ppos].p_ext = NULL;
++      path[ppos].p_idx = NULL;
++
++      if (ext3_ext_check_header(eh))
++              goto err;
 +
 +      /* find extent */
 +      ext3_ext_binsearch(tree, path + ppos, block);
@@ -478,6 +503,12 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      ext3_ext_show_path(tree, path);
 +
 +      return path;
++
++err:
++      printk(KERN_ERR "EXT3-fs: header is corrupted!\n");
++      ext3_ext_drop_refs(path);
++      kfree(path);
++      return ERR_PTR(-EIO);
 +}
 +
 +/*
@@ -485,9 +516,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + * it check where to insert: before curp or after curp
 + */
 +static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *curp,
++                               int logical, int ptr)
 +{
 +      struct ext3_extent_idx *ix;
 +      int len, err;
@@ -503,9 +534,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent_idx);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
++                                "move %d from 0x%p to 0x%p\n",
++                                logical, ptr, len,
++                                (curp->p_idx + 1), (curp->p_idx + 2));
 +                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
 +              }
 +              ix = curp->p_idx + 1;
@@ -514,9 +545,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              len = len * sizeof(struct ext3_extent_idx);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
++                        "move %d from 0x%p to 0x%p\n",
++                        logical, ptr, len,
++                        curp->p_idx, (curp->p_idx + 1));
 +              memmove(curp->p_idx + 1, curp->p_idx, len);
 +              ix = curp->p_idx;
 +      }
@@ -544,8 +575,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + *  - initialize subtree
 + */
 +static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
++                        struct ext3_ext_path *path,
++                        struct ext3_extent *newext, int at)
 +{
 +      struct buffer_head *bh = NULL;
 +      int depth = EXT_DEPTH(tree);
@@ -566,13 +597,13 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              border = path[depth].p_ext[1].ee_block;
 +              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      } else {
 +              border = newext->ee_block;
 +              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      }
 +
 +      /* 
@@ -630,12 +661,11 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      while (path[depth].p_ext <=
 +                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
++                        path[depth].p_ext->ee_block,
++                        path[depth].p_ext->ee_start,
++                        path[depth].p_ext->ee_len,
++                        newblock);
++              memmove(ex++, path[depth].p_ext++, sizeof(struct ext3_extent));
 +              neh->eh_entries++;
 +              m++;
 +      }
@@ -688,21 +718,21 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              fidx->ei_leaf = oldblock;
 +
 +              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
++                        i, newblock, border, oldblock);
 +              /* copy indexes */
 +              m = 0;
 +              path[i].p_idx++;
 +
 +              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
++                        EXT_MAX_INDEX(path[i].p_hdr));
 +              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
++                         EXT_LAST_INDEX(path[i].p_hdr));
 +              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
 +                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
++                                i, path[i].p_idx->ei_block,
++                                path[i].p_idx->ei_leaf, newblock);
 +                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
++                              sizeof(struct ext3_extent_idx));
 +                      neh->eh_entries++;
 +                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
 +                      m++;
@@ -732,7 +762,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      /* insert new index */
 +      if (!err)
 +              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
++                                          border, newblock);
 +
 +cleanup:
 +      if (bh) {
@@ -762,9 +792,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + *    just created block
 + */
 +static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *path,
++                               struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp = path;
 +      struct ext3_extent_header *neh;
@@ -823,7 +853,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      neh = EXT_ROOT_HDR(tree);
 +      fidx = EXT_FIRST_INDEX(neh);
 +      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
++                neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
 +
 +      neh->eh_depth = path->p_depth + 1;
 +      err = ext3_ext_dirty(handle, tree, curp);
@@ -838,9 +868,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + * then it requests in-depth growing
 + */
 +static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                                  struct ext3_extents_tree *tree,
++                                  struct ext3_ext_path *path,
++                                  struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp;
 +      int depth, i, err = 0;
@@ -916,12 +946,12 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              if (depth == path->p_depth) {
 +                      /* leaf */
 +                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
++                          EXT_LAST_EXTENT(path[depth].p_hdr))
 +                              return path[depth].p_ext[1].ee_block;
 +              } else {
 +                      /* index */
 +                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
++                          EXT_LAST_INDEX(path[depth].p_hdr))
 +                              return path[depth].p_idx[1].ei_block;
 +              }
 +              depth--;        
@@ -934,7 +964,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + * returns first allocated block from next leaf or EXT_MAX_BLOCK
 + */
 +static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
++                                       struct ext3_ext_path *path)
 +{
 +      int depth;
 +
@@ -950,7 +980,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      
 +      while (depth >= 0) {
 +              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
++                  EXT_LAST_INDEX(path[depth].p_hdr))
 +                      return path[depth].p_idx[1].ei_block;
 +              depth--;        
 +      }
@@ -964,7 +994,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + * TODO: do we need to correct tree in all cases?
 + */
 +int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                           struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      int depth = EXT_DEPTH(tree);    
@@ -1014,8 +1044,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static int inline
 +ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                         struct ext3_extent *ex1,
++                         struct ext3_extent *ex2)
 +{
 +      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
 +              return 0;
@@ -1037,8 +1067,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + * creating new leaf in no-space case
 + */
 +int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
++                         struct ext3_ext_path *path,
++                         struct ext3_extent *newext)
 +{
 +      struct ext3_extent_header * eh;
 +      struct ext3_extent *ex, *fex;
@@ -1047,7 +1077,6 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      int depth, len, err, next;
 +
 +      EXT_ASSERT(newext->ee_len > 0);
-+      EXT_ASSERT(newext->ee_len < EXT_CACHE_MARK);
 +      depth = EXT_DEPTH(tree);
 +      ex = path[depth].p_ext;
 +      EXT_ASSERT(path[depth].p_hdr);
@@ -1055,8 +1084,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      /* try to insert block into found extent and return */
 +      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
 +              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
++                        newext->ee_len, ex->ee_block, ex->ee_len,
++                        ex->ee_start);
 +              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
 +                      return err;
 +              ex->ee_len += newext->ee_len;
@@ -1084,12 +1113,12 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              eh = npath[depth].p_hdr;
 +              if (eh->eh_entries < eh->eh_max) {
 +                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
++                                eh->eh_entries);
 +                      path = npath;
 +                      goto repeat;
 +              }
 +              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
++                        eh->eh_entries, eh->eh_max);
 +      }
 +
 +      /*
@@ -1111,8 +1140,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      if (!nearex) {
 +              /* there is no extent in this leaf, create first one */
 +              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
++                        newext->ee_block, newext->ee_start,
++                        newext->ee_len);
 +              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
 +      } else if (newext->ee_block > nearex->ee_block) {
 +              EXT_ASSERT(newext->ee_block != nearex->ee_block);
@@ -1121,10 +1150,10 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
++                                "move %d from 0x%p to 0x%p\n",
++                                newext->ee_block, newext->ee_start,
++                                newext->ee_len,
++                                nearex, len, nearex + 1, nearex + 2);
 +                      memmove(nearex + 2, nearex + 1, len);
 +              }
 +              path[depth].p_ext = nearex + 1;
@@ -1133,9 +1162,9 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
++                        "move %d from 0x%p to 0x%p\n",
++                        newext->ee_block, newext->ee_start, newext->ee_len,
++                        nearex, len, nearex + 1, nearex + 2);
 +              memmove(nearex + 1, nearex, len);
 +              path[depth].p_ext = nearex;
 +      }
@@ -1156,8 +1185,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              /* merge with next extent! */
 +              nearex->ee_len += nearex[1].ee_len;
 +              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
++                      len = (EXT_LAST_EXTENT(eh) - nearex - 1) *
++                              sizeof(struct ext3_extent);
 +                      memmove(nearex + 1, nearex + 2, len);
 +              }
 +              eh->eh_entries--;
@@ -1187,7 +1216,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +                      unsigned long num, ext_prepare_callback func)
 +{
 +      struct ext3_ext_path *path = NULL;
-+      struct ext3_extent *ex, cbex;
++      struct ext3_ext_cache cbex;
++      struct ext3_extent *ex;
 +      unsigned long next, start = 0, end = 0;
 +      unsigned long last = block + num;
 +      int depth, exists, err = 0;
@@ -1246,14 +1276,20 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              EXT_ASSERT(end > start);
 +
 +              if (!exists) {
-+                      cbex.ee_block = start;
-+                      cbex.ee_len = end - start;
-+                      cbex.ee_start = 0;
-+              } else
-+                      cbex = *ex;
++                      cbex.ec_block = start;
++                      cbex.ec_len = end - start;
++                      cbex.ec_start = 0;
++                      cbex.ec_type = EXT3_EXT_CACHE_GAP;
++              } else {
++                      cbex.ec_block = ex->ee_block;
++                      cbex.ec_len = ex->ee_len;
++                      cbex.ec_start = ex->ee_start;
++                      cbex.ec_type = EXT3_EXT_CACHE_EXTENT;
++              }
 +
++              EXT_ASSERT(cbex.ec_len > 0);
 +              EXT_ASSERT(path[depth].p_hdr);
-+              err = func(tree, path, &cbex, exists);
++              err = func(tree, path, &cbex);
 +              ext3_ext_drop_refs(path);
 +
 +              if (err < 0)
@@ -1271,7 +1307,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +                      path = NULL;
 +              }
 +
-+              block = cbex.ee_block + cbex.ee_len;
++              block = cbex.ec_block + cbex.ec_len;
 +      }
 +
 +      if (path) {
@@ -1284,7 +1320,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static inline void
 +ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
++                    __u32 len, __u32 start, int type)
 +{
 +      EXT_ASSERT(len > 0);
 +      if (tree->cex) {
@@ -1301,8 +1337,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
++                        struct ext3_ext_path *path,
++                        unsigned long block)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      unsigned long lblock, len;
@@ -1321,16 +1357,16 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              lblock = block;
 +              len = ex->ee_block - block;
 +              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len);
 +      } else if (block >= ex->ee_block + ex->ee_len) {
 +              lblock = ex->ee_block + ex->ee_len;
 +              len = ext3_ext_next_allocated_block(path);
 +              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) block);
 +              EXT_ASSERT(len > lblock);
 +              len = len - lblock;
 +      } else {
@@ -1344,7 +1380,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static inline int
 +ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
++                struct ext3_extent *ex)
 +{
 +      struct ext3_ext_cache *cex = tree->cex;
 +
@@ -1357,16 +1393,16 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              return EXT3_EXT_CACHE_NO;
 +
 +      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
++                 cex->ec_type == EXT3_EXT_CACHE_EXTENT);
 +      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
 +              ex->ee_block = cex->ec_block;
 +              ex->ee_start = cex->ec_start;
 +              ex->ee_len = cex->ec_len;
 +              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) ex->ee_start);
 +              return cex->ec_type;
 +      }
 +
@@ -1380,7 +1416,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 + * last index in the block only
 + */
 +int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
++                  struct ext3_ext_path *path)
 +{
 +      struct buffer_head *bh;
 +      int err;
@@ -1394,7 +1430,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      if ((err = ext3_ext_dirty(handle, tree, path)))
 +              return err;
 +      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +      bh = sb_get_hash_table(tree->inode->i_sb, path->p_idx->ei_leaf);
 +      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
 +      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
@@ -1402,7 +1438,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
++                                   struct ext3_ext_path *path)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      int needed;
@@ -1439,8 +1475,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++                    struct ext3_ext_path *path, unsigned long start,
++                    unsigned long end)
 +{
 +      struct ext3_extent *ex, tex;
 +      struct ext3_ext_path *npath;
@@ -1474,7 +1510,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      /* FIXME: some callback to free underlying resource
 +       * and correct ee_start? */
 +      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
++                ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
 +
 +      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
 +      if (IS_ERR(npath))
@@ -1488,13 +1524,12 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      kfree(npath);
 +
 +      return err;
-+                      
 +}
 +
 +static int
 +ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++               struct ext3_ext_path *path, unsigned long start,
++               unsigned long end)
 +{
 +      struct ext3_extent *ex, *fu = NULL, *lu, *le;
 +      int err = 0, correct_index = 0;
@@ -1527,8 +1562,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      }
 +      
 +      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
++      while (ex >= EXT_FIRST_EXTENT(eh) && ex->ee_block + ex->ee_len > start) {
 +              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
 +              path[depth].p_ext = ex;
 +      
@@ -1555,7 +1589,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +                      block = ex->ee_block; 
 +                      num = 0;
 +                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
++                                 b == ex->ee_block + ex->ee_len - 1);
 +              }
 +
 +              if (ex == EXT_FIRST_EXTENT(eh))
@@ -1597,7 +1631,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +                      goto out;
 +
 +              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +              ex--;
 +      }
 +
@@ -1661,7 +1695,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
++                        unsigned long start, unsigned long end)
 +{
 +      struct inode *inode = tree->inode;
 +      struct super_block *sb = inode->i_sb;
@@ -1685,8 +1719,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +       */
 +      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
 +      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
++              ext3_error(sb, __FUNCTION__, "Can't allocate path array");
 +              ext3_journal_stop(handle, inode);
 +              return -ENOMEM;
 +      }
@@ -1718,19 +1751,19 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +                              ext3_ext_last_covered(path[i].p_hdr, end);
 +                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
 +                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
++                                path[i].p_hdr, path[i].p_hdr->eh_entries);
 +              } else {
 +                      /* we've already was here, see at next index */
 +                      path[i].p_idx--;
 +              }
 +
 +              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
++                        i, EXT_FIRST_INDEX(path[i].p_hdr),
++                        path[i].p_idx);
 +              if (ext3_ext_more_to_rm(path + i)) {
 +                      /* go to the next level */
 +                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
++                                i + 1, path[i].p_idx->ei_leaf);
 +                      memset(path + i + 1, 0, sizeof(*path));
 +                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
 +                      if (!path[i+1].p_bh) {
@@ -1823,7 +1856,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +}
 +
 +static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                           struct ext3_extent *ex2)
 +{
 +      /* FIXME: support for large fs */
 +      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
@@ -1833,8 +1866,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                         struct ext3_extent *ex,
++                         unsigned long from, unsigned long to)
 +{
 +      int needed;
 +      
@@ -1849,8 +1882,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                 struct ext3_extent *ex,
++                 unsigned long from, unsigned long to)
 +{
 +      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
 +      handle_t *handle = ext3_journal_start(tree->inode, needed);
@@ -1865,7 +1898,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              num = ex->ee_block + ex->ee_len - from;
 +              start = ex->ee_start + ex->ee_len - num;
 +              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
++                        num, start);
 +              for (i = 0; i < num; i++) {
 +                      bh = sb_get_hash_table(tree->inode->i_sb, start + i);
 +                      ext3_forget(handle, 0, tree->inode, bh, start + i);
@@ -1873,17 +1906,17 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              ext3_free_blocks(handle, tree->inode, start, num);
 +      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
 +              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      } else {
 +              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      }
 +      ext3_journal_stop(handle, tree->inode);
 +      return 0;
 +}
 +
 +int ext3_ext_find_goal(struct inode *inode, struct ext3_ext_path *path,
-+                      unsigned long block)
++                     unsigned long block)
 +{
 +      struct ext3_inode_info *ei = EXT3_I(inode);
 +      unsigned long bg_start;
@@ -1913,8 +1946,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +}
 +
 +static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
++                           struct ext3_ext_path *path,
++                           struct ext3_extent *ex, int *err)
 +{
 +      struct inode *inode = tree->inode;
 +      int newblock, goal;
@@ -1951,7 +1984,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +};
 +
 +void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
++                       struct inode *inode)
 +{
 +      tree->inode = inode;
 +      tree->root = (void *) EXT3_I(inode)->i_data;
@@ -1962,7 +1995,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result, int create)
++                     long iblock, struct buffer_head *bh_result, int create)
 +{
 +      struct ext3_ext_path *path = NULL;
 +      struct ext3_extent newex;
@@ -1973,7 +2006,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      clear_bit(BH_New, &bh_result->b_state);
 +      ext3_init_tree_desc(&tree, inode);
 +      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
++                (int) iblock, (unsigned) inode->i_ino);
 +      down_write(&EXT3_I(inode)->truncate_sem);
 +
 +      /* check in cache */
@@ -2016,11 +2049,11 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
 +                      newblock = iblock - ex->ee_block + ex->ee_start;
 +                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
++                                (int) iblock, ex->ee_block, ex->ee_len,
++                                newblock);
 +                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
++                                            ex->ee_len, ex->ee_start,
++                                            EXT3_EXT_CACHE_EXTENT);
 +                      goto out;
 +              }
 +      }
@@ -2041,7 +2074,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      if (!newblock)
 +              goto out2;
 +      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
++                goal, newblock);
 +
 +      /* try to insert new extent into found leaf and return */
 +      newex.ee_block = iblock;
@@ -2059,7 +2092,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      set_bit(BH_New, &bh_result->b_state);
 +
 +      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
++                            newex.ee_start, EXT3_EXT_CACHE_EXTENT);
 +out:
 +      ext3_ext_show_leaf(&tree, path);
 +      set_bit(BH_Mapped, &bh_result->b_state);
@@ -2111,8 +2144,8 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +      EXT3_I(inode)->i_disksize = inode->i_size;
 +      ext3_mark_inode_dirty(handle, inode);
 +
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
++      last_block = (inode->i_size + sb->s_blocksize - 1) >>
++                      EXT3_BLOCK_SIZE_BITS(sb);
 +      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
 +      
 +      /* In a multi-transaction truncate, we only make the final
@@ -2172,13 +2205,14 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *newex, int exist)
++                       struct ext3_ext_path *path,
++                       struct ext3_ext_cache *newex)
 +{
 +      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
 +
-+      if (!exist)
++      if (newex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
++
 +      if (buf->err < 0)
 +              return EXT_BREAK;
 +      if (buf->cur - buf->buffer + sizeof(*newex) > buf->buflen)
@@ -2196,14 +2230,14 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *ex, int exist)
++                        struct ext3_ext_path *path,
++                        struct ext3_ext_cache *ex)
 +{
 +      struct ext3_extent_tree_stats *buf =
 +              (struct ext3_extent_tree_stats *) tree->private;
 +      int depth;
 +
-+      if (!exist)
++      if (ex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
 +
 +      depth = EXT_DEPTH(tree);
@@ -2234,7 +2268,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              tree.private = &buf;
 +              down_write(&EXT3_I(inode)->truncate_sem);
 +              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
++                                        ext3_ext_store_extent_cb);
 +              up_write(&EXT3_I(inode)->truncate_sem);
 +              if (err == 0)
 +                      err = buf.err;
@@ -2249,7 +2283,7 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +              buf.leaf_num = 0;
 +              tree.private = &buf;
 +              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
++                                        ext3_ext_collect_stats_cb);
 +              up_write(&EXT3_I(inode)->truncate_sem);
 +              if (!err)
 +                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
@@ -2271,22 +2305,18 @@ Index: linux-2.4.24/fs/ext3/extents.c
 +EXPORT_SYMBOL(ext3_ext_walk_space);
 +EXPORT_SYMBOL(ext3_ext_find_goal);
 +EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
 Index: linux-2.4.24/fs/ext3/ialloc.c
 ===================================================================
 --- linux-2.4.24.orig/fs/ext3/ialloc.c 2004-11-02 20:28:32.000000000 +0300
 +++ linux-2.4.24/fs/ext3/ialloc.c      2004-11-02 20:32:17.000000000 +0300
-@@ -592,10 +592,22 @@
+@@ -592,6 +592,19 @@
                iloc.bh = NULL;
                goto fail;
        }
--      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
--      if (err) goto fail;
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
-+              ext3_extents_initialize_blockmap(handle, inode);
++      if (test_opt(sb, EXTENTS) && S_ISREG(inode->i_mode)) {
++              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
++              memset(&EXT3_I(inode)->i_cached_extent, 0, sizeof(__u32) * 4);
++              ext3_extents_initialize_blockmap(handle, inode);
 +              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
 +                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
 +                      if (err) goto fail;
@@ -2294,13 +2324,11 @@ Index: linux-2.4.24/fs/ext3/ialloc.c
 +                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
 +                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
 +              }
-+      }
++      }
++
+       err = ext3_mark_iloc_dirty(handle, inode, &iloc);
+       if (err) goto fail;
  
-+      err = ext3_mark_iloc_dirty(handle, inode, &iloc);
-+      if (err) goto fail;
-       
-       unlock_super (sb);
-       if(DQUOT_ALLOC_INODE(inode)) {
 Index: linux-2.4.24/fs/ext3/inode.c
 ===================================================================
 --- linux-2.4.24.orig/fs/ext3/inode.c  2004-11-02 20:28:33.000000000 +0300
@@ -2311,7 +2339,7 @@ Index: linux-2.4.24/fs/ext3/inode.c
  
 +static inline int
 +ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create)
++                  struct buffer_head *bh, int create)
 +{
 +      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
 +              return ext3_ext_get_block(handle, inode, block, bh, create);
@@ -2362,7 +2390,7 @@ Index: linux-2.4.24/fs/ext3/inode.c
        for (block = 0; block < EXT3_N_BLOCKS; block++)
                inode->u.ext3_i.i_data[block] = iloc.raw_inode->i_block[block];
        INIT_LIST_HEAD(&inode->u.ext3_i.i_orphan);
-+      memset(&inode->u.ext3_i.i_cached_extent, 0, sizeof(__u32) * 4);
++      memset(&EXT3_I(inode)->i_cached_extent, 0, sizeof(__u32) * 4);
  
        if (EXT3_INODE_SIZE(inode->i_sb) > EXT3_GOOD_OLD_INODE_SIZE)
                inode->u.ext3_i.i_extra_isize =
@@ -2460,21 +2488,24 @@ Index: linux-2.4.24/include/linux/ext3_fs.h
 ===================================================================
 --- linux-2.4.24.orig/include/linux/ext3_fs.h  2004-11-02 20:28:32.000000000 +0300
 +++ linux-2.4.24/include/linux/ext3_fs.h       2004-11-02 20:32:17.000000000 +0300
-@@ -184,6 +184,7 @@
+@@ -184,8 +184,9 @@
  #define EXT3_IMAGIC_FL                        0x00002000 /* AFS directory */
  #define EXT3_JOURNAL_DATA_FL          0x00004000 /* file data should be journaled */
  #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
 +#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
  
- #define EXT3_FL_USER_VISIBLE          0x00005FFF /* User visible flags */
+-#define EXT3_FL_USER_VISIBLE          0x00005FFF /* User visible flags */
++#define EXT3_FL_USER_VISIBLE          0x00085FFF /* User visible flags */
  #define EXT3_FL_USER_MODIFIABLE               0x000000FF /* User modifiable flags */
+ /*
 @@ -208,6 +209,9 @@
  #ifdef CONFIG_JBD_DEBUG
  #define EXT3_IOC_WAIT_FOR_READONLY    _IOR('f', 99, long)
  #endif
-+#define       EXT3_IOC_GET_EXTENTS            _IOR('f', 5, long)
-+#define       EXT3_IOC_GET_TREE_DEPTH         _IOR('f', 6, long)
-+#define       EXT3_IOC_GET_TREE_STATS         _IOR('f', 7, long)
++#define EXT3_IOC_GET_EXTENTS          _IOR('f', 5, long)
++#define EXT3_IOC_GET_TREE_DEPTH               _IOR('f', 6, long)
++#define EXT3_IOC_GET_TREE_STATS               _IOR('f', 7, long)
  
  /*
   * Structure of an inode on the disk
@@ -2516,7 +2547,7 @@ Index: linux-2.4.24/include/linux/ext3_fs.h
 +/* extents.c */
 +extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
 +extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                              struct buffer_head *, int);
++                            struct buffer_head *, int);
 +extern void ext3_ext_truncate(struct inode *);
 +extern void ext3_ext_init(struct super_block *);
 +extern void ext3_ext_release(struct super_block *);
@@ -2530,7 +2561,7 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 ===================================================================
 --- linux-2.4.24.orig/include/linux/ext3_extents.h     2003-01-30 13:24:37.000000000 +0300
 +++ linux-2.4.24/include/linux/ext3_extents.h  2004-11-02 20:32:17.000000000 +0300
-@@ -0,0 +1,251 @@
+@@ -0,0 +1,263 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -2572,7 +2603,7 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 + */
 +#define EXT_DEBUG_
 +#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
++#define ext_debug(tree,fmt,a...)                      \
 +do {                                                  \
 +      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
 +              printk(fmt, ##a);                       \
@@ -2685,14 +2716,14 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 +      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
 +      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
 +      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
++                                   struct ext3_extent *, unsigned long,
++                                   unsigned long);
 +      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
++                           struct ext3_extent *, unsigned long,
++                           unsigned long);
 +      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
++                       struct ext3_ext_path *, struct ext3_extent *,
++                       int *);
 +};
 +
 +/*
@@ -2702,8 +2733,8 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 + * callback must return valid extent (passed or newly created)
 + */
 +typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_extent *, int);
++                                  struct ext3_ext_path *,
++                                  struct ext3_ext_cache *);
 +
 +#define EXT_CONTINUE  0
 +#define EXT_BREAK     1
@@ -2711,7 +2742,6 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 +
 +
 +#define EXT_MAX_BLOCK 0xffffffff
-+#define EXT_CACHE_MARK        0xffff
 +
 +
 +#define EXT_FIRST_EXTENT(__hdr__) \
@@ -2743,6 +2773,20 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 +
 +#define EXT_ASSERT(__x__) if (!(__x__)) BUG();
 +
++#define EXT_CHECK_PATH(tree,path)                                     \
++{                                                                     \
++      int depth = EXT_DEPTH(tree);                                    \
++      BUG_ON((unsigned long) (path) < __PAGE_OFFSET);                 \
++      BUG_ON((unsigned long) (path)[depth].p_idx <                    \
++                      __PAGE_OFFSET && (path)[depth].p_idx != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_ext <                    \
++                      __PAGE_OFFSET && (path)[depth].p_ext != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_hdr < __PAGE_OFFSET);    \
++      BUG_ON((unsigned long) (path)[depth].p_bh < __PAGE_OFFSET       \
++                      && depth != 0);                                 \
++      BUG_ON((path)[0].p_depth != depth);                             \
++}
++
 +
 +/*
 + * this structure is used to gather extents from the tree via ioctl
@@ -2764,7 +2808,7 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 +      int leaf_num;
 +};
 +
-+void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
++extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
 +extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
 +extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
@@ -2781,7 +2825,6 @@ Index: linux-2.4.24/include/linux/ext3_extents.h
 +
 +
 +#endif /* _LINUX_EXT3_EXTENTS */
-+
 Index: linux-2.4.24/include/linux/ext3_fs_i.h
 ===================================================================
 --- linux-2.4.24.orig/include/linux/ext3_fs_i.h        2004-11-02 20:28:32.000000000 +0300
@@ -2791,7 +2834,7 @@ Index: linux-2.4.24/include/linux/ext3_fs_i.h
         */
        struct rw_semaphore truncate_sem;
 +
-+      __u32 i_cached_extent[4];
++      __u32 i_cached_extent[4];
  };
  
  #endif        /* _LINUX_EXT3_FS_I */
index 671fbc0..053c0fb 100644 (file)
@@ -3,9 +3,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 ===================================================================
 --- linux-2.6.5-sles9.orig/fs/ext3/extents.c   2005-02-17 22:07:57.023609040 +0300
 +++ linux-2.6.5-sles9/fs/ext3/extents.c        2005-02-23 01:02:37.396435640 +0300
-@@ -0,0 +1,2356 @@
+@@ -0,0 +1,2349 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -54,17 +54,17 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +{
 +      if (eh->eh_magic != EXT3_EXT_MAGIC) {
 +              printk(KERN_ERR "EXT3-fs: invalid magic = 0x%x\n",
-+                              (unsigned) eh->eh_magic);
++                     (unsigned)eh->eh_magic);
 +              return -EIO;
 +      }
 +      if (eh->eh_max == 0) {
 +              printk(KERN_ERR "EXT3-fs: invalid eh_max = %u\n",
-+                              (unsigned) eh->eh_max);
++                     (unsigned)eh->eh_max);
 +              return -EIO;
 +      }
 +      if (eh->eh_entries > eh->eh_max) {
 +              printk(KERN_ERR "EXT3-fs: invalid eh_entries = %u\n",
-+                              (unsigned) eh->eh_entries);
++                     (unsigned)eh->eh_entries);
 +              return -EIO;
 +      }
 +      return 0;
@@ -107,8 +107,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *  - ENOMEM
 + */
 +static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_extents_tree *tree,
++                             struct ext3_ext_path *path)
 +{
 +      int err;
 +
@@ -129,7 +129,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *  - EIO
 + */
 +static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                        struct ext3_ext_path *path)
 +{
 +      int err;
 +      if (path->p_bh) {
@@ -144,8 +144,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int inline
 +ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
++                 struct ext3_ext_path *path, struct ext3_extent *ex,
++                 int *err)
 +{
 +      int goal, depth, newblock;
 +      struct inode *inode;
@@ -164,7 +164,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              unsigned long colour;
 +
 +              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
++                          EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
 +                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
 +              colour = (current->pid % 16) *
 +                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
@@ -187,8 +187,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 6;
 +#endif
@@ -200,8 +200,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent_idx);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 5;
 +#endif
@@ -212,8 +212,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      sizeof(struct ext3_extent);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 3;
 +#endif
@@ -224,9 +224,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 4;
 +#endif
@@ -234,7 +233,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int k, l = path->p_depth;
@@ -243,12 +242,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      for (k = 0; k <= l; k++, path++) {
 +              if (path->p_idx) {
 +                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
++                                path->p_idx->ei_leaf);
 +              } else if (path->p_ext) {
 +                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
++                                path->p_ext->ee_block,
++                                path->p_ext->ee_len,
++                                path->p_ext->ee_start);
 +              } else
 +                      ext_debug(tree, "  []");
 +      }
@@ -257,7 +256,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int depth = EXT_DEPTH(tree);
@@ -273,7 +272,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +      for (i = 0; i < eh->eh_entries; i++, ex++) {
 +              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +      }
 +      ext_debug(tree, "\n");
 +#endif
@@ -284,11 +283,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      int depth = path->p_depth;
 +      int i;
 +
-+      for (i = 0; i <= depth; i++, path++)
++      for (i = 0; i <= depth; i++, path++) {
 +              if (path->p_bh) {
 +                      brelse(path->p_bh);
 +                      path->p_bh = NULL;
 +              }
++      }
 +}
 +
 +/*
@@ -296,7 +296,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                     struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent_idx *ix;
@@ -322,7 +322,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +      ix += l;
 +      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
++      ext_debug(tree," -> %d->%d ",path->p_idx->ei_block,path->p_idx->ei_leaf);
 +
 +      while (l++ < r) {
 +              if (block < ix->ei_block) 
@@ -330,7 +330,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              path->p_idx = ix++;
 +      }
 +      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -340,9 +340,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              for (k = 0; k < eh->eh_entries; k++, ix++) {
 +                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
 +                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
++                                     ix, EXT_FIRST_INDEX(eh));
 +                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
++                                     ix->ei_block,ix[-1].ei_block);
 +                      }
 +                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
 +                      if (block < ix->ei_block) 
@@ -352,7 +352,6 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              EXT_ASSERT(chix == path->p_idx);
 +      }
 +#endif
-+
 +}
 +
 +/*
@@ -360,7 +359,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                 struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent *ex;
@@ -394,7 +393,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      ex += l;
 +      path->p_ext = ex;
 +      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +      while (l++ < r) {
 +              if (block < ex->ee_block) 
@@ -402,7 +401,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              path->p_ext = ex++;
 +      }
 +      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -418,7 +417,6 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              EXT_ASSERT(chex == path->p_ext);
 +      }
 +#endif
-+
 +}
 +
 +int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
@@ -439,7 +437,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +struct ext3_ext_path *
 +ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
++                   struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      struct buffer_head *bh;
@@ -461,7 +459,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* account possible depth increase */
 +      if (!path) {
 +              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
++                             GFP_NOFS);
 +              if (!path)
 +                      return ERR_PTR(-ENOMEM);
 +      }
@@ -471,7 +469,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* walk through the tree */
 +      while (i) {
 +              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
++                        ppos, eh->eh_entries, eh->eh_max);
 +              ext3_ext_binsearch_idx(tree, path + ppos, block);
 +              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
 +              path[ppos].p_depth = i;
@@ -519,9 +517,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * it check where to insert: before curp or after curp
 + */
 +static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *curp,
++                               int logical, int ptr)
 +{
 +      struct ext3_extent_idx *ix;
 +      int len, err;
@@ -537,9 +535,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent_idx);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
++                                "move %d from 0x%p to 0x%p\n",
++                                logical, ptr, len,
++                                (curp->p_idx + 1), (curp->p_idx + 2));
 +                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
 +              }
 +              ix = curp->p_idx + 1;
@@ -548,9 +546,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              len = len * sizeof(struct ext3_extent_idx);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
++                        "move %d from 0x%p to 0x%p\n",
++                        logical, ptr, len,
++                        curp->p_idx, (curp->p_idx + 1));
 +              memmove(curp->p_idx + 1, curp->p_idx, len);
 +              ix = curp->p_idx;
 +      }
@@ -578,8 +576,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *  - initialize subtree
 + */
 +static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
++                        struct ext3_ext_path *path,
++                        struct ext3_extent *newext, int at)
 +{
 +      struct buffer_head *bh = NULL;
 +      int depth = EXT_DEPTH(tree);
@@ -600,13 +598,13 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              border = path[depth].p_ext[1].ee_block;
 +              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      } else {
 +              border = newext->ee_block;
 +              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      }
 +
 +      /* 
@@ -664,12 +662,11 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      while (path[depth].p_ext <=
 +                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
++                        path[depth].p_ext->ee_block,
++                        path[depth].p_ext->ee_start,
++                        path[depth].p_ext->ee_len,
++                        newblock);
++              memmove(ex++, path[depth].p_ext++, sizeof(struct ext3_extent));
 +              neh->eh_entries++;
 +              m++;
 +      }
@@ -722,21 +719,21 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              fidx->ei_leaf = oldblock;
 +
 +              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
++                        i, newblock, border, oldblock);
 +              /* copy indexes */
 +              m = 0;
 +              path[i].p_idx++;
 +
 +              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
++                        EXT_MAX_INDEX(path[i].p_hdr));
 +              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
++                         EXT_LAST_INDEX(path[i].p_hdr));
 +              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
 +                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
++                                i, path[i].p_idx->ei_block,
++                                path[i].p_idx->ei_leaf, newblock);
 +                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
++                              sizeof(struct ext3_extent_idx));
 +                      neh->eh_entries++;
 +                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
 +                      m++;
@@ -766,7 +763,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* insert new index */
 +      if (!err)
 +              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
++                                          border, newblock);
 +
 +cleanup:
 +      if (bh) {
@@ -796,9 +793,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + *    just created block
 + */
 +static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *path,
++                               struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp = path;
 +      struct ext3_extent_header *neh;
@@ -830,7 +827,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* set size of new block */
 +      neh = EXT_BLOCK_HDR(bh);
 +      /* old root could have indexes or leaves
-+       * so calculate e_max right way */
++       * so calculate eh_max right way */
 +      if (EXT_DEPTH(tree))
 +              neh->eh_max = ext3_ext_space_block_idx(tree);
 +      else
@@ -857,7 +854,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      neh = EXT_ROOT_HDR(tree);
 +      fidx = EXT_FIRST_INDEX(neh);
 +      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
++                neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
 +
 +      neh->eh_depth = path->p_depth + 1;
 +      err = ext3_ext_dirty(handle, tree, curp);
@@ -872,9 +869,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * then it requests in-depth growing
 + */
 +static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                                  struct ext3_extents_tree *tree,
++                                  struct ext3_ext_path *path,
++                                  struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp;
 +      int depth, i, err = 0;
@@ -950,12 +947,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              if (depth == path->p_depth) {
 +                      /* leaf */
 +                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
++                          EXT_LAST_EXTENT(path[depth].p_hdr))
 +                              return path[depth].p_ext[1].ee_block;
 +              } else {
 +                      /* index */
 +                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
++                          EXT_LAST_INDEX(path[depth].p_hdr))
 +                              return path[depth].p_idx[1].ei_block;
 +              }
 +              depth--;        
@@ -968,7 +965,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * returns first allocated block from next leaf or EXT_MAX_BLOCK
 + */
 +static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
++                                       struct ext3_ext_path *path)
 +{
 +      int depth;
 +
@@ -984,7 +981,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      
 +      while (depth >= 0) {
 +              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
++                  EXT_LAST_INDEX(path[depth].p_hdr))
 +                      return path[depth].p_idx[1].ei_block;
 +              depth--;        
 +      }
@@ -998,7 +995,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * TODO: do we need to correct tree in all cases?
 + */
 +int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                           struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      int depth = EXT_DEPTH(tree);    
@@ -1048,8 +1045,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int inline
 +ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                         struct ext3_extent *ex1,
++                         struct ext3_extent *ex2)
 +{
 +      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
 +              return 0;
@@ -1071,8 +1068,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * creating new leaf in no-space case
 + */
 +int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
++                         struct ext3_ext_path *path,
++                         struct ext3_extent *newext)
 +{
 +      struct ext3_extent_header * eh;
 +      struct ext3_extent *ex, *fex;
@@ -1088,8 +1085,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* try to insert block into found extent and return */
 +      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
 +              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
++                        newext->ee_len, ex->ee_block, ex->ee_len,
++                        ex->ee_start);
 +              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
 +                      return err;
 +              ex->ee_len += newext->ee_len;
@@ -1117,12 +1114,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              eh = npath[depth].p_hdr;
 +              if (eh->eh_entries < eh->eh_max) {
 +                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
++                                eh->eh_entries);
 +                      path = npath;
 +                      goto repeat;
 +              }
 +              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
++                        eh->eh_entries, eh->eh_max);
 +      }
 +
 +      /*
@@ -1144,8 +1141,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if (!nearex) {
 +              /* there is no extent in this leaf, create first one */
 +              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
++                        newext->ee_block, newext->ee_start,
++                        newext->ee_len);
 +              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
 +      } else if (newext->ee_block > nearex->ee_block) {
 +              EXT_ASSERT(newext->ee_block != nearex->ee_block);
@@ -1154,10 +1151,10 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
++                                "move %d from 0x%p to 0x%p\n",
++                                newext->ee_block, newext->ee_start,
++                                newext->ee_len,
++                                nearex, len, nearex + 1, nearex + 2);
 +                      memmove(nearex + 2, nearex + 1, len);
 +              }
 +              path[depth].p_ext = nearex + 1;
@@ -1166,9 +1163,9 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
++                        "move %d from 0x%p to 0x%p\n",
++                        newext->ee_block, newext->ee_start, newext->ee_len,
++                        nearex, len, nearex + 1, nearex + 2);
 +              memmove(nearex + 1, nearex, len);
 +              path[depth].p_ext = nearex;
 +      }
@@ -1189,8 +1186,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              /* merge with next extent! */
 +              nearex->ee_len += nearex[1].ee_len;
 +              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
++                      len = (EXT_LAST_EXTENT(eh) - nearex - 1) *
++                              sizeof(struct ext3_extent);
 +                      memmove(nearex + 1, nearex + 2, len);
 +              }
 +              eh->eh_entries--;
@@ -1324,7 +1321,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static inline void
 +ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
++                    __u32 len, __u32 start, int type)
 +{
 +      EXT_ASSERT(len > 0);
 +      if (tree->cex) {
@@ -1341,8 +1338,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
++                        struct ext3_ext_path *path,
++                        unsigned long block)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      unsigned long lblock, len;
@@ -1361,16 +1358,16 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              lblock = block;
 +              len = ex->ee_block - block;
 +              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len);
 +      } else if (block >= ex->ee_block + ex->ee_len) {
 +              lblock = ex->ee_block + ex->ee_len;
 +              len = ext3_ext_next_allocated_block(path);
 +              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) block);
 +              EXT_ASSERT(len > lblock);
 +              len = len - lblock;
 +      } else {
@@ -1384,7 +1381,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static inline int
 +ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
++                struct ext3_extent *ex)
 +{
 +      struct ext3_ext_cache *cex = tree->cex;
 +
@@ -1397,16 +1394,16 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              return EXT3_EXT_CACHE_NO;
 +
 +      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
++                 cex->ec_type == EXT3_EXT_CACHE_EXTENT);
 +      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
 +              ex->ee_block = cex->ec_block;
 +              ex->ee_start = cex->ec_start;
 +              ex->ee_len = cex->ec_len;
 +              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) ex->ee_start);
 +              return cex->ec_type;
 +      }
 +
@@ -1420,7 +1417,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 + * last index in the block only
 + */
 +int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
++                  struct ext3_ext_path *path)
 +{
 +      struct buffer_head *bh;
 +      int err;
@@ -1434,7 +1431,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if ((err = ext3_ext_dirty(handle, tree, path)))
 +              return err;
 +      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +      bh = sb_find_get_block(tree->inode->i_sb, path->p_idx->ei_leaf);
 +      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
 +      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
@@ -1442,7 +1439,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
++                                   struct ext3_ext_path *path)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      int needed;
@@ -1479,8 +1476,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++                    struct ext3_ext_path *path, unsigned long start,
++                    unsigned long end)
 +{
 +      struct ext3_extent *ex, tex;
 +      struct ext3_ext_path *npath;
@@ -1514,7 +1511,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      /* FIXME: some callback to free underlying resource
 +       * and correct ee_start? */
 +      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
++                ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
 +
 +      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
 +      if (IS_ERR(npath))
@@ -1528,13 +1525,12 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      kfree(npath);
 +
 +      return err;
-+                      
 +}
 +
 +static int
 +ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++               struct ext3_ext_path *path, unsigned long start,
++               unsigned long end)
 +{
 +      struct ext3_extent *ex, *fu = NULL, *lu, *le;
 +      int err = 0, correct_index = 0;
@@ -1567,8 +1563,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      }
 +      
 +      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
++      while (ex >= EXT_FIRST_EXTENT(eh) && ex->ee_block + ex->ee_len > start) {
 +              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
 +              path[depth].p_ext = ex;
 +      
@@ -1595,7 +1590,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      block = ex->ee_block; 
 +                      num = 0;
 +                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
++                                 b == ex->ee_block + ex->ee_len - 1);
 +              }
 +
 +              if (ex == EXT_FIRST_EXTENT(eh))
@@ -1637,7 +1632,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                      goto out;
 +
 +              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +              ex--;
 +      }
 +
@@ -1701,7 +1696,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
++                        unsigned long start, unsigned long end)
 +{
 +      struct inode *inode = tree->inode;
 +      struct super_block *sb = inode->i_sb;
@@ -1725,8 +1720,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +       */
 +      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
 +      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
++              ext3_error(sb, __FUNCTION__, "Can't allocate path array");
 +              ext3_journal_stop(handle);
 +              return -ENOMEM;
 +      }
@@ -1758,19 +1752,19 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +                              ext3_ext_last_covered(path[i].p_hdr, end);
 +                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
 +                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
++                                path[i].p_hdr, path[i].p_hdr->eh_entries);
 +              } else {
 +                      /* we've already was here, see at next index */
 +                      path[i].p_idx--;
 +              }
 +
 +              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
++                        i, EXT_FIRST_INDEX(path[i].p_hdr),
++                        path[i].p_idx);
 +              if (ext3_ext_more_to_rm(path + i)) {
 +                      /* go to the next level */
 +                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
++                                i + 1, path[i].p_idx->ei_leaf);
 +                      memset(path + i + 1, 0, sizeof(*path));
 +                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
 +                      if (!path[i+1].p_bh) {
@@ -1893,7 +1887,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                           struct ext3_extent *ex2)
 +{
 +      /* FIXME: support for large fs */
 +      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
@@ -1903,8 +1897,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                         struct ext3_extent *ex,
++                         unsigned long from, unsigned long to)
 +{
 +      int needed;
 +      
@@ -1919,8 +1913,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                 struct ext3_extent *ex,
++                 unsigned long from, unsigned long to)
 +{
 +      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
 +      handle_t *handle = ext3_journal_start(tree->inode, needed);
@@ -1935,7 +1929,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              num = ex->ee_block + ex->ee_len - from;
 +              start = ex->ee_start + ex->ee_len - num;
 +              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
++                        num, start);
 +              for (i = 0; i < num; i++) {
 +                      bh = sb_find_get_block(tree->inode->i_sb, start + i);
 +                      ext3_forget(handle, 0, tree->inode, bh, start + i);
@@ -1943,17 +1937,17 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              ext3_free_blocks(handle, tree->inode, start, num);
 +      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
 +              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      } else {
 +              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      }
 +      ext3_journal_stop(handle);
 +      return 0;
 +}
 +
 +static int ext3_ext_find_goal(struct inode *inode,
-+                              struct ext3_ext_path *path, unsigned long block)
++                            struct ext3_ext_path *path, unsigned long block)
 +{
 +      struct ext3_inode_info *ei = EXT3_I(inode);
 +      unsigned long bg_start;
@@ -1983,8 +1977,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
++                           struct ext3_ext_path *path,
++                           struct ext3_extent *ex, int *err)
 +{
 +      struct inode *inode = tree->inode;
 +      int newblock, goal;
@@ -2021,7 +2015,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +};
 +
 +void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
++                       struct inode *inode)
 +{
 +      tree->inode = inode;
 +      tree->root = (void *) EXT3_I(inode)->i_data;
@@ -2032,8 +2026,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result,
-+                      int create, int extend_disksize)
++                     long iblock, struct buffer_head *bh_result,
++                     int create, int extend_disksize)
 +{
 +      struct ext3_ext_path *path = NULL;
 +      struct ext3_extent newex;
@@ -2044,7 +2038,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      __clear_bit(BH_New, &bh_result->b_state);
 +      ext3_init_tree_desc(&tree, inode);
 +      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
++                (int) iblock, (unsigned) inode->i_ino);
 +      down(&EXT3_I(inode)->truncate_sem);
 +
 +      /* check in cache */
@@ -2087,11 +2081,11 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
 +                      newblock = iblock - ex->ee_block + ex->ee_start;
 +                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
++                                (int) iblock, ex->ee_block, ex->ee_len,
++                                newblock);
 +                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
++                                            ex->ee_len, ex->ee_start,
++                                            EXT3_EXT_CACHE_EXTENT);
 +                      goto out;
 +              }
 +      }
@@ -2112,7 +2106,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      if (!newblock)
 +              goto out2;
 +      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
++                goal, newblock);
 +
 +      /* try to insert new extent into found leaf and return */
 +      newex.ee_block = iblock;
@@ -2130,7 +2124,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      __set_bit(BH_New, &bh_result->b_state);
 +
 +      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
++                            newex.ee_start, EXT3_EXT_CACHE_EXTENT);
 +out:
 +      ext3_ext_show_leaf(&tree, path);
 +      __set_bit(BH_Mapped, &bh_result->b_state);
@@ -2190,8 +2184,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      EXT3_I(inode)->i_disksize = inode->i_size;
 +      ext3_mark_inode_dirty(handle, inode);
 +
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
++      last_block = (inode->i_size + sb->s_blocksize - 1) >>
++                      EXT3_BLOCK_SIZE_BITS(sb);
 +      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
 +      
 +      /* In a multi-transaction truncate, we only make the final
@@ -2259,8 +2253,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +      
 +static int
 +ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_ext_cache *newex)
++                       struct ext3_ext_path *path,
++                       struct ext3_ext_cache *newex)
 +{
 +      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
 +
@@ -2284,8 +2278,8 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_ext_cache *ex)
++                        struct ext3_ext_path *path,
++                        struct ext3_ext_cache *ex)
 +{
 +      struct ext3_extent_tree_stats *buf =
 +              (struct ext3_extent_tree_stats *) tree->private;
@@ -2302,7 +2296,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_ioctl(struct inode *inode, struct file *filp, unsigned int cmd,
-+              unsigned long arg)
++                 unsigned long arg)
 +{
 +      int err = 0;
 +
@@ -2322,7 +2316,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              tree.private = &buf;
 +              down(&EXT3_I(inode)->truncate_sem);
 +              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
++                                        ext3_ext_store_extent_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (err == 0)
 +                      err = buf.err;
@@ -2337,7 +2331,7 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +              buf.leaf_num = 0;
 +              tree.private = &buf;
 +              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
++                                        ext3_ext_collect_stats_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (!err)
 +                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
@@ -2359,19 +2353,26 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
 +EXPORT_SYMBOL(ext3_ext_walk_space);
 +EXPORT_SYMBOL(ext3_ext_find_goal);
 +EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
 Index: linux-2.6.5-sles9/fs/ext3/ialloc.c
 ===================================================================
 --- linux-2.6.5-sles9.orig/fs/ext3/ialloc.c    2005-02-23 01:01:52.366281264 +0300
 +++ linux-2.6.5-sles9/fs/ext3/ialloc.c 2005-02-23 01:02:37.398435336 +0300
-@@ -647,6 +647,10 @@
+@@ -647,6 +647,18 @@
                DQUOT_FREE_INODE(inode);
                goto fail2;
        }
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              ext3_extents_initialize_blockmap(handle, inode);
-+      }
++      if (test_opt(sb, EXTENTS) && S_ISREG(inode->i_mode)) {
++              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
++              ext3_extents_initialize_blockmap(handle, inode);
++              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
++                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
++                      if (err) goto fail;
++                      EXT3_SET_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS);
++                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
++                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
++              }
++      }
++
        err = ext3_mark_inode_dirty(handle, inode);
        if (err) {
                ext3_std_error(sb, err);
@@ -2385,13 +2386,13 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
  
 +static inline int
 +ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create, int extend_disksize)
++                  struct buffer_head *bh, int create, int extend_disksize)
 +{
 +      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
 +              return ext3_ext_get_block(handle, inode, block, bh, create,
-+                                              extend_disksize);
++                                        extend_disksize);
 +      return ext3_get_block_handle(handle, inode, block, bh, create,
-+                                      extend_disksize);
++                                   extend_disksize);
 +}
 +
  static int ext3_get_block(struct inode *inode, sector_t iblock,
@@ -2404,7 +2405,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
 -      ret = ext3_get_block_handle(handle, inode, iblock,
 -                              bh_result, create, 1);
 +      ret = ext3_get_block_wrap(handle, inode, iblock,
-+                                      bh_result, create, 1);
++                                bh_result, create, 1);
        return ret;
  }
  
@@ -2415,7 +2416,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
 -              ret = ext3_get_block_handle(handle, inode, iblock,
 -                                      bh_result, create, 0);
 +              ret = ext3_get_block_wrap(handle, inode, iblock,
-+                                              bh_result, create, 0);
++                                        bh_result, create, 0);
        if (ret == 0)
                bh_result->b_size = (1 << inode->i_blkbits);
        return ret;
@@ -2451,9 +2452,9 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
        int indirects = (EXT3_NDIR_BLOCKS % bpp) ? 5 : 3;
        int ret;
  
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_writepage_trans_blocks(inode, bpp);
-+ 
++      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
++              return ext3_ext_writepage_trans_blocks(inode, bpp);
++
        if (ext3_should_journal_data(inode))
                ret = 3 * (bpp + indirects) + 2;
        else
@@ -2478,7 +2479,7 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        struct ext3_super_block *es = sbi->s_es;
        int i;
  
-+      ext3_ext_release(sb);
++      ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
        if (!(sb->s_flags & MS_RDONLY)) {
@@ -2526,8 +2527,8 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        percpu_counter_mod(&sbi->s_dirs_counter,
                ext3_count_dirs(sb));
  
-+      ext3_ext_init(sb);
-+ 
++      ext3_ext_init(sb);
++
        return 0;
  
  failed_mount3:
@@ -2550,14 +2551,17 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
 ===================================================================
 --- linux-2.6.5-sles9.orig/include/linux/ext3_fs.h     2005-02-23 01:02:35.823674736 +0300
 +++ linux-2.6.5-sles9/include/linux/ext3_fs.h  2005-02-23 01:02:37.414432904 +0300
-@@ -186,6 +186,7 @@
+@@ -186,8 +186,9 @@
+ #define EXT3_NOTAIL_FL                        0x00008000 /* don't merge file tail */
  #define EXT3_DIRSYNC_FL                       0x00010000 /* dirsync behaviour (directories only) */
  #define EXT3_TOPDIR_FL                        0x00020000 /* Top of directory hierarchies*/
- #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
 +#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
+ #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
  
- #define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
+-#define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
++#define EXT3_FL_USER_VISIBLE          0x000BDFFF /* User visible flags */
  #define EXT3_FL_USER_MODIFIABLE               0x000380FF /* User modifiable flags */
 @@ -211,6 +212,9 @@
  #endif
  #define EXT3_IOC_GETRSVSZ             _IOR('f', 5, long)
@@ -2577,6 +2581,21 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
  #ifndef clear_opt
+@@ -503,11 +509,13 @@
+ #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
+ #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
+ #define EXT3_FEATURE_INCOMPAT_META_BG         0x0010
++#define EXT3_FEATURE_INCOMPAT_EXTENTS         0x0040 /* extents support */
+ #define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
+ #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
+                                        EXT3_FEATURE_INCOMPAT_RECOVER| \
+-                                       EXT3_FEATURE_INCOMPAT_META_BG)
++                                       EXT3_FEATURE_INCOMPAT_META_BG| \
++                                       EXT3_FEATURE_INCOMPAT_EXTENTS)
+ #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
+                                        EXT3_FEATURE_RO_COMPAT_LARGE_FILE| \
+                                        EXT3_FEATURE_RO_COMPAT_BTREE_DIR)
 @@ -729,6 +735,7 @@
  
  
@@ -2592,7 +2611,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
 +/* extents.c */
 +extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
 +extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                              struct buffer_head *, int, int);
++                            struct buffer_head *, int, int);
 +extern void ext3_ext_truncate(struct inode *, struct page *);
 +extern void ext3_ext_init(struct super_block *);
 +extern void ext3_ext_release(struct super_block *);
@@ -2606,7 +2625,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 ===================================================================
 --- linux-2.6.5-sles9.orig/include/linux/ext3_extents.h        2005-02-17 22:07:57.023609040 +0300
 +++ linux-2.6.5-sles9/include/linux/ext3_extents.h     2005-02-23 01:02:37.416432600 +0300
-@@ -0,0 +1,265 @@
+@@ -0,0 +1,264 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -2648,7 +2667,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 + */
 +#define EXT_DEBUG_
 +#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
++#define ext_debug(tree,fmt,a...)                      \
 +do {                                                  \
 +      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
 +              printk(fmt, ##a);                       \
@@ -2761,14 +2780,14 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
 +      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
 +      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
++                                   struct ext3_extent *, unsigned long,
++                                   unsigned long);
 +      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
++                           struct ext3_extent *, unsigned long,
++                           unsigned long);
 +      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
++                       struct ext3_ext_path *, struct ext3_extent *,
++                       int *);
 +};
 +
 +/*
@@ -2778,8 +2797,8 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 + * callback must return valid extent (passed or newly created)
 + */
 +typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_ext_cache *);
++                                  struct ext3_ext_path *,
++                                  struct ext3_ext_cache *);
 +
 +#define EXT_CONTINUE  0
 +#define EXT_BREAK     1
@@ -2831,7 +2850,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +                      && depth != 0);                                 \
 +      BUG_ON((path)[0].p_depth != depth);                             \
 +}
-+      
++
 +
 +/*
 + * this structure is used to gather extents from the tree via ioctl
@@ -2853,13 +2872,13 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +      int leaf_num;
 +};
 +
++extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
 +extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
 +extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
 +extern int ext3_ext_walk_space(struct ext3_extents_tree *, unsigned long, unsigned long, ext_prepare_callback);
 +extern int ext3_ext_remove_space(struct ext3_extents_tree *, unsigned long, unsigned long);
 +extern struct ext3_ext_path * ext3_ext_find_extent(struct ext3_extents_tree *, int, struct ext3_ext_path *);
-+extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_ext_calc_blockmap_metadata(struct inode *, int);
 +
 +static inline void
@@ -2871,7 +2890,6 @@ Index: linux-2.6.5-sles9/include/linux/ext3_extents.h
 +
 +
 +#endif /* _LINUX_EXT3_EXTENTS */
-+
 Index: linux-2.6.5-sles9/include/linux/ext3_fs_i.h
 ===================================================================
 --- linux-2.6.5-sles9.orig/include/linux/ext3_fs_i.h   2005-02-23 01:01:52.425272296 +0300
index 78c5d81..02745cc 100644 (file)
@@ -2,9 +2,9 @@ Index: linux-stage/fs/ext3/extents.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/extents.c 2005-02-25 15:33:48.890198160 +0200
 +++ linux-stage/fs/ext3/extents.c      2005-02-25 15:33:48.917194056 +0200
-@@ -0,0 +1,2313 @@
+@@ -0,0 +1,2347 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -48,6 +48,27 @@ Index: linux-stage/fs/ext3/extents.c
 +#include <linux/ext3_extents.h>
 +#include <asm/uaccess.h>
 +
++
++static inline int ext3_ext_check_header(struct ext3_extent_header *eh)
++{
++      if (eh->eh_magic != EXT3_EXT_MAGIC) {
++              printk(KERN_ERR "EXT3-fs: invalid magic = 0x%x\n",
++                     (unsigned)eh->eh_magic);
++              return -EIO;
++      }
++      if (eh->eh_max == 0) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_max = %u\n",
++                     (unsigned)eh->eh_max);
++              return -EIO;
++      }
++      if (eh->eh_entries > eh->eh_max) {
++              printk(KERN_ERR "EXT3-fs: invalid eh_entries = %u\n",
++                     (unsigned)eh->eh_entries);
++              return -EIO;
++      }
++      return 0;
++}
++
 +static handle_t *ext3_ext_journal_restart(handle_t *handle, int needed)
 +{
 +      int err;
@@ -85,8 +106,8 @@ Index: linux-stage/fs/ext3/extents.c
 + *  - ENOMEM
 + */
 +static int ext3_ext_get_access(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_extents_tree *tree,
++                             struct ext3_ext_path *path)
 +{
 +      int err;
 +
@@ -107,7 +128,7 @@ Index: linux-stage/fs/ext3/extents.c
 + *  - EIO
 + */
 +static int ext3_ext_dirty(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                        struct ext3_ext_path *path)
 +{
 +      int err;
 +      if (path->p_bh) {
@@ -122,8 +143,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int inline
 +ext3_ext_new_block(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, struct ext3_extent *ex,
-+                      int *err)
++                 struct ext3_ext_path *path, struct ext3_extent *ex,
++                 int *err)
 +{
 +      int goal, depth, newblock;
 +      struct inode *inode;
@@ -142,7 +163,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              unsigned long colour;
 +
 +              bg_start = (ei->i_block_group *
-+                              EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
++                          EXT3_BLOCKS_PER_GROUP(inode->i_sb)) +
 +                      le32_to_cpu(EXT3_SB(inode->i_sb)->s_es->s_first_data_block);
 +              colour = (current->pid % 16) *
 +                      (EXT3_BLOCKS_PER_GROUP(inode->i_sb) / 16);
@@ -165,8 +186,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 6;
 +#endif
@@ -178,8 +199,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      int size;
 +
 +      size = (tree->inode->i_sb->s_blocksize -
-+                      sizeof(struct ext3_extent_header))
-+                              sizeof(struct ext3_extent_idx);
++              sizeof(struct ext3_extent_header)) /
++                              sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 5;
 +#endif
@@ -190,8 +211,8 @@ Index: linux-stage/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len - sizeof(struct ext3_extent_header))
-+                      sizeof(struct ext3_extent);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent);
 +#ifdef AGRESSIVE_TEST
 +      size = 3;
 +#endif
@@ -202,9 +223,8 @@ Index: linux-stage/fs/ext3/extents.c
 +{
 +      int size;
 +
-+      size = (tree->buffer_len -
-+                      sizeof(struct ext3_extent_header))
-+                      / sizeof(struct ext3_extent_idx);
++      size = (tree->buffer_len - sizeof(struct ext3_extent_header)) /
++                      sizeof(struct ext3_extent_idx);
 +#ifdef AGRESSIVE_TEST
 +      size = 4;
 +#endif
@@ -212,7 +232,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_path(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int k, l = path->p_depth;
@@ -221,12 +241,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      for (k = 0; k <= l; k++, path++) {
 +              if (path->p_idx) {
 +                      ext_debug(tree, "  %d->%d", path->p_idx->ei_block,
-+                                      path->p_idx->ei_leaf);
++                                path->p_idx->ei_leaf);
 +              } else if (path->p_ext) {
 +                      ext_debug(tree, "  %d:%d:%d",
-+                                      path->p_ext->ee_block,
-+                                      path->p_ext->ee_len,
-+                                      path->p_ext->ee_start);
++                                path->p_ext->ee_block,
++                                path->p_ext->ee_len,
++                                path->p_ext->ee_start);
 +              } else
 +                      ext_debug(tree, "  []");
 +      }
@@ -235,7 +255,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static void ext3_ext_show_leaf(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                             struct ext3_ext_path *path)
 +{
 +#ifdef EXT_DEBUG
 +      int depth = EXT_DEPTH(tree);
@@ -251,7 +271,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +      for (i = 0; i < eh->eh_entries; i++, ex++) {
 +              ext_debug(tree, "%d:%d:%d ",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +      }
 +      ext_debug(tree, "\n");
 +#endif
@@ -262,11 +282,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      int depth = path->p_depth;
 +      int i;
 +
-+      for (i = 0; i <= depth; i++, path++)
++      for (i = 0; i <= depth; i++, path++) {
 +              if (path->p_bh) {
 +                      brelse(path->p_bh);
 +                      path->p_bh = NULL;
 +              }
++      }
 +}
 +
 +/*
@@ -274,7 +295,7 @@ Index: linux-stage/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch_idx(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                     struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent_idx *ix;
@@ -300,7 +321,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +      ix += l;
 +      path->p_idx = ix;
-+      ext_debug(tree, "  -> %d->%d ", path->p_idx->ei_block, path->p_idx->ei_leaf);
++      ext_debug(tree," -> %d->%d ",path->p_idx->ei_block,path->p_idx->ei_leaf);
 +
 +      while (l++ < r) {
 +              if (block < ix->ei_block) 
@@ -308,7 +329,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              path->p_idx = ix++;
 +      }
 +      ext_debug(tree, "  -> %d->%d\n", path->p_idx->ei_block,
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -318,9 +339,9 @@ Index: linux-stage/fs/ext3/extents.c
 +              for (k = 0; k < eh->eh_entries; k++, ix++) {
 +                      if (k != 0 && ix->ei_block <= ix[-1].ei_block) {
 +                              printk("k=%d, ix=0x%p, first=0x%p\n", k,
-+                                      ix, EXT_FIRST_INDEX(eh));
++                                     ix, EXT_FIRST_INDEX(eh));
 +                              printk("%u <= %u\n",
-+                                      ix->ei_block,ix[-1].ei_block);
++                                     ix->ei_block,ix[-1].ei_block);
 +                      }
 +                      EXT_ASSERT(k == 0 || ix->ei_block > ix[-1].ei_block);
 +                      if (block < ix->ei_block) 
@@ -330,7 +351,6 @@ Index: linux-stage/fs/ext3/extents.c
 +              EXT_ASSERT(chix == path->p_idx);
 +      }
 +#endif
-+
 +}
 +
 +/*
@@ -338,7 +358,7 @@ Index: linux-stage/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_binsearch(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, int block)
++                 struct ext3_ext_path *path, int block)
 +{
 +      struct ext3_extent_header *eh = path->p_hdr;
 +      struct ext3_extent *ex;
@@ -372,7 +392,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      ex += l;
 +      path->p_ext = ex;
 +      ext_debug(tree, "  -> %d:%d:%d ", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +      while (l++ < r) {
 +              if (block < ex->ee_block) 
@@ -380,7 +400,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              path->p_ext = ex++;
 +      }
 +      ext_debug(tree, "  -> %d:%d:%d\n", path->p_ext->ee_block,
-+                      path->p_ext->ee_start, path->p_ext->ee_len);
++                path->p_ext->ee_start, path->p_ext->ee_len);
 +
 +#ifdef CHECK_BINSEARCH 
 +      {
@@ -396,7 +416,6 @@ Index: linux-stage/fs/ext3/extents.c
 +              EXT_ASSERT(chex == path->p_ext);
 +      }
 +#endif
-+
 +}
 +
 +int ext3_extent_tree_init(handle_t *handle, struct ext3_extents_tree *tree)
@@ -417,7 +436,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +struct ext3_ext_path *
 +ext3_ext_find_extent(struct ext3_extents_tree *tree, int block,
-+                      struct ext3_ext_path *path)
++                   struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      struct buffer_head *bh;
@@ -429,15 +448,17 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +      eh = EXT_ROOT_HDR(tree);
 +      EXT_ASSERT(eh);
++      if (ext3_ext_check_header(eh))
++              goto err;
++
 +      i = depth = EXT_DEPTH(tree);
 +      EXT_ASSERT(eh->eh_max);
 +      EXT_ASSERT(eh->eh_magic == EXT3_EXT_MAGIC);
-+      EXT_ASSERT(i == 0 || eh->eh_entries > 0);
 +      
 +      /* account possible depth increase */
 +      if (!path) {
 +              path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 2),
-+                              GFP_NOFS);
++                             GFP_NOFS);
 +              if (!path)
 +                      return ERR_PTR(-ENOMEM);
 +      }
@@ -447,29 +468,34 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* walk through the tree */
 +      while (i) {
 +              ext_debug(tree, "depth %d: num %d, max %d\n",
-+                              ppos, eh->eh_entries, eh->eh_max);
++                        ppos, eh->eh_entries, eh->eh_max);
 +              ext3_ext_binsearch_idx(tree, path + ppos, block);
 +              path[ppos].p_block = path[ppos].p_idx->ei_leaf;
 +              path[ppos].p_depth = i;
 +              path[ppos].p_ext = NULL;
 +
 +              bh = sb_bread(tree->inode->i_sb, path[ppos].p_block);
-+              if (!bh) {
-+                      ext3_ext_drop_refs(path);
-+                      kfree(path);
-+                      return ERR_PTR(-EIO);
-+              }
++              if (!bh)
++                      goto err;
++
 +              eh = EXT_BLOCK_HDR(bh);
 +              ppos++;
 +              EXT_ASSERT(ppos <= depth);
 +              path[ppos].p_bh = bh;
 +              path[ppos].p_hdr = eh;
 +              i--;
++
++              if (ext3_ext_check_header(eh))
++                      goto err;
 +      }
 +
 +      path[ppos].p_depth = i;
 +      path[ppos].p_hdr = eh;
 +      path[ppos].p_ext = NULL;
++      path[ppos].p_idx = NULL;
++
++      if (ext3_ext_check_header(eh))
++              goto err;
 +
 +      /* find extent */
 +      ext3_ext_binsearch(tree, path + ppos, block);
@@ -477,6 +503,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      ext3_ext_show_path(tree, path);
 +
 +      return path;
++
++err:
++      printk(KERN_ERR "EXT3-fs: header is corrupted!\n");
++      ext3_ext_drop_refs(path);
++      kfree(path);
++      return ERR_PTR(-EIO);
 +}
 +
 +/*
@@ -484,9 +516,9 @@ Index: linux-stage/fs/ext3/extents.c
 + * it check where to insert: before curp or after curp
 + */
 +static int ext3_ext_insert_index(handle_t *handle,
-+                              struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *curp,
-+                              int logical, int ptr)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *curp,
++                               int logical, int ptr)
 +{
 +      struct ext3_extent_idx *ix;
 +      int len, err;
@@ -502,9 +534,9 @@ Index: linux-stage/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent_idx);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert new index %d after: %d. "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      logical, ptr, len,
-+                                      (curp->p_idx + 1), (curp->p_idx + 2));
++                                "move %d from 0x%p to 0x%p\n",
++                                logical, ptr, len,
++                                (curp->p_idx + 1), (curp->p_idx + 2));
 +                      memmove(curp->p_idx + 2, curp->p_idx + 1, len);
 +              }
 +              ix = curp->p_idx + 1;
@@ -513,9 +545,9 @@ Index: linux-stage/fs/ext3/extents.c
 +              len = len * sizeof(struct ext3_extent_idx);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert new index %d before: %d. "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              logical, ptr, len,
-+                              curp->p_idx, (curp->p_idx + 1));
++                        "move %d from 0x%p to 0x%p\n",
++                        logical, ptr, len,
++                        curp->p_idx, (curp->p_idx + 1));
 +              memmove(curp->p_idx + 1, curp->p_idx, len);
 +              ix = curp->p_idx;
 +      }
@@ -543,8 +575,8 @@ Index: linux-stage/fs/ext3/extents.c
 + *  - initialize subtree
 + */
 +static int ext3_ext_split(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext, int at)
++                        struct ext3_ext_path *path,
++                        struct ext3_extent *newext, int at)
 +{
 +      struct buffer_head *bh = NULL;
 +      int depth = EXT_DEPTH(tree);
@@ -565,13 +597,13 @@ Index: linux-stage/fs/ext3/extents.c
 +      if (path[depth].p_ext != EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              border = path[depth].p_ext[1].ee_block;
 +              ext_debug(tree, "leaf will be splitted."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      } else {
 +              border = newext->ee_block;
 +              ext_debug(tree, "leaf will be added."
-+                              " next leaf starts at %d\n",
-+                              (int)border);
++                        " next leaf starts at %d\n",
++                        (int)border);
 +      }
 +
 +      /* 
@@ -629,12 +661,11 @@ Index: linux-stage/fs/ext3/extents.c
 +      while (path[depth].p_ext <=
 +                      EXT_MAX_EXTENT(path[depth].p_hdr)) {
 +              ext_debug(tree, "move %d:%d:%d in new leaf %lu\n",
-+                              path[depth].p_ext->ee_block,
-+                              path[depth].p_ext->ee_start,
-+                              path[depth].p_ext->ee_len,
-+                              newblock);
-+              memmove(ex++, path[depth].p_ext++,
-+                              sizeof(struct ext3_extent));
++                        path[depth].p_ext->ee_block,
++                        path[depth].p_ext->ee_start,
++                        path[depth].p_ext->ee_len,
++                        newblock);
++              memmove(ex++, path[depth].p_ext++, sizeof(struct ext3_extent));
 +              neh->eh_entries++;
 +              m++;
 +      }
@@ -687,21 +718,21 @@ Index: linux-stage/fs/ext3/extents.c
 +              fidx->ei_leaf = oldblock;
 +
 +              ext_debug(tree, "int.index at %d (block %lu): %lu -> %lu\n",
-+                              i, newblock, border, oldblock);
++                        i, newblock, border, oldblock);
 +              /* copy indexes */
 +              m = 0;
 +              path[i].p_idx++;
 +
 +              ext_debug(tree, "cur 0x%p, last 0x%p\n", path[i].p_idx,
-+                              EXT_MAX_INDEX(path[i].p_hdr));
++                        EXT_MAX_INDEX(path[i].p_hdr));
 +              EXT_ASSERT(EXT_MAX_INDEX(path[i].p_hdr) ==
-+                              EXT_LAST_INDEX(path[i].p_hdr));
++                         EXT_LAST_INDEX(path[i].p_hdr));
 +              while (path[i].p_idx <= EXT_MAX_INDEX(path[i].p_hdr)) {
 +                      ext_debug(tree, "%d: move %d:%d in new index %lu\n",
-+                                      i, path[i].p_idx->ei_block,
-+                                      path[i].p_idx->ei_leaf, newblock);
++                                i, path[i].p_idx->ei_block,
++                                path[i].p_idx->ei_leaf, newblock);
 +                      memmove(++fidx, path[i].p_idx++,
-+                                      sizeof(struct ext3_extent_idx));
++                              sizeof(struct ext3_extent_idx));
 +                      neh->eh_entries++;
 +                      EXT_ASSERT(neh->eh_entries <= neh->eh_max);
 +                      m++;
@@ -731,7 +762,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* insert new index */
 +      if (!err)
 +              err = ext3_ext_insert_index(handle, tree, path + at,
-+                                              border, newblock);
++                                          border, newblock);
 +
 +cleanup:
 +      if (bh) {
@@ -761,9 +792,9 @@ Index: linux-stage/fs/ext3/extents.c
 + *    just created block
 + */
 +static int ext3_ext_grow_indepth(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                               struct ext3_extents_tree *tree,
++                               struct ext3_ext_path *path,
++                               struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp = path;
 +      struct ext3_extent_header *neh;
@@ -795,7 +826,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* set size of new block */
 +      neh = EXT_BLOCK_HDR(bh);
 +      /* old root could have indexes or leaves
-+       * so calculate e_max right way */
++       * so calculate eh_max right way */
 +      if (EXT_DEPTH(tree))
 +              neh->eh_max = ext3_ext_space_block_idx(tree);
 +      else
@@ -822,7 +853,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      neh = EXT_ROOT_HDR(tree);
 +      fidx = EXT_FIRST_INDEX(neh);
 +      ext_debug(tree, "new root: num %d(%d), lblock %d, ptr %d\n",
-+                      neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
++                neh->eh_entries, neh->eh_max, fidx->ei_block, fidx->ei_leaf); 
 +
 +      neh->eh_depth = path->p_depth + 1;
 +      err = ext3_ext_dirty(handle, tree, curp);
@@ -837,9 +868,9 @@ Index: linux-stage/fs/ext3/extents.c
 + * then it requests in-depth growing
 + */
 +static int ext3_ext_create_new_leaf(handle_t *handle,
-+                                      struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path,
-+                                      struct ext3_extent *newext)
++                                  struct ext3_extents_tree *tree,
++                                  struct ext3_ext_path *path,
++                                  struct ext3_extent *newext)
 +{
 +      struct ext3_ext_path *curp;
 +      int depth, i, err = 0;
@@ -915,12 +946,12 @@ Index: linux-stage/fs/ext3/extents.c
 +              if (depth == path->p_depth) {
 +                      /* leaf */
 +                      if (path[depth].p_ext !=
-+                                      EXT_LAST_EXTENT(path[depth].p_hdr))
++                          EXT_LAST_EXTENT(path[depth].p_hdr))
 +                              return path[depth].p_ext[1].ee_block;
 +              } else {
 +                      /* index */
 +                      if (path[depth].p_idx !=
-+                                      EXT_LAST_INDEX(path[depth].p_hdr))
++                          EXT_LAST_INDEX(path[depth].p_hdr))
 +                              return path[depth].p_idx[1].ei_block;
 +              }
 +              depth--;        
@@ -933,7 +964,7 @@ Index: linux-stage/fs/ext3/extents.c
 + * returns first allocated block from next leaf or EXT_MAX_BLOCK
 + */
 +static unsigned ext3_ext_next_leaf_block(struct ext3_extents_tree *tree,
-+                                               struct ext3_ext_path *path)
++                                       struct ext3_ext_path *path)
 +{
 +      int depth;
 +
@@ -949,7 +980,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      
 +      while (depth >= 0) {
 +              if (path[depth].p_idx !=
-+                              EXT_LAST_INDEX(path[depth].p_hdr))
++                  EXT_LAST_INDEX(path[depth].p_hdr))
 +                      return path[depth].p_idx[1].ei_block;
 +              depth--;        
 +      }
@@ -963,7 +994,7 @@ Index: linux-stage/fs/ext3/extents.c
 + * TODO: do we need to correct tree in all cases?
 + */
 +int ext3_ext_correct_indexes(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path)
++                           struct ext3_ext_path *path)
 +{
 +      struct ext3_extent_header *eh;
 +      int depth = EXT_DEPTH(tree);    
@@ -1013,8 +1044,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int inline
 +ext3_can_extents_be_merged(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                         struct ext3_extent *ex1,
++                         struct ext3_extent *ex2)
 +{
 +      if (ex1->ee_block + ex1->ee_len != ex2->ee_block)
 +              return 0;
@@ -1036,8 +1067,8 @@ Index: linux-stage/fs/ext3/extents.c
 + * creating new leaf in no-space case
 + */
 +int ext3_ext_insert_extent(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *newext)
++                         struct ext3_ext_path *path,
++                         struct ext3_extent *newext)
 +{
 +      struct ext3_extent_header * eh;
 +      struct ext3_extent *ex, *fex;
@@ -1046,7 +1077,6 @@ Index: linux-stage/fs/ext3/extents.c
 +      int depth, len, err, next;
 +
 +      EXT_ASSERT(newext->ee_len > 0);
-+      EXT_ASSERT(newext->ee_len < EXT_CACHE_MARK);
 +      depth = EXT_DEPTH(tree);
 +      ex = path[depth].p_ext;
 +      EXT_ASSERT(path[depth].p_hdr);
@@ -1054,8 +1084,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* try to insert block into found extent and return */
 +      if (ex && ext3_can_extents_be_merged(tree, ex, newext)) {
 +              ext_debug(tree, "append %d block to %d:%d (from %d)\n",
-+                              newext->ee_len, ex->ee_block, ex->ee_len,
-+                              ex->ee_start);
++                        newext->ee_len, ex->ee_block, ex->ee_len,
++                        ex->ee_start);
 +              if ((err = ext3_ext_get_access(handle, tree, path + depth)))
 +                      return err;
 +              ex->ee_len += newext->ee_len;
@@ -1083,12 +1113,12 @@ Index: linux-stage/fs/ext3/extents.c
 +              eh = npath[depth].p_hdr;
 +              if (eh->eh_entries < eh->eh_max) {
 +                      ext_debug(tree, "next leaf isnt full(%d)\n",
-+                                      eh->eh_entries);
++                                eh->eh_entries);
 +                      path = npath;
 +                      goto repeat;
 +              }
 +              ext_debug(tree, "next leaf hasno free space(%d,%d)\n",
-+                              eh->eh_entries, eh->eh_max);
++                        eh->eh_entries, eh->eh_max);
 +      }
 +
 +      /*
@@ -1110,8 +1140,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      if (!nearex) {
 +              /* there is no extent in this leaf, create first one */
 +              ext_debug(tree, "first extent in the leaf: %d:%d:%d\n",
-+                              newext->ee_block, newext->ee_start,
-+                              newext->ee_len);
++                        newext->ee_block, newext->ee_start,
++                        newext->ee_len);
 +              path[depth].p_ext = EXT_FIRST_EXTENT(eh);
 +      } else if (newext->ee_block > nearex->ee_block) {
 +              EXT_ASSERT(newext->ee_block != nearex->ee_block);
@@ -1120,10 +1150,10 @@ Index: linux-stage/fs/ext3/extents.c
 +                      len = (len - 1) * sizeof(struct ext3_extent);
 +                      len = len < 0 ? 0 : len;
 +                      ext_debug(tree, "insert %d:%d:%d after: nearest 0x%p, "
-+                                      "move %d from 0x%p to 0x%p\n",
-+                                      newext->ee_block, newext->ee_start,
-+                                      newext->ee_len,
-+                                      nearex, len, nearex + 1, nearex + 2);
++                                "move %d from 0x%p to 0x%p\n",
++                                newext->ee_block, newext->ee_start,
++                                newext->ee_len,
++                                nearex, len, nearex + 1, nearex + 2);
 +                      memmove(nearex + 2, nearex + 1, len);
 +              }
 +              path[depth].p_ext = nearex + 1;
@@ -1132,9 +1162,9 @@ Index: linux-stage/fs/ext3/extents.c
 +              len = (EXT_MAX_EXTENT(eh) - nearex) * sizeof(struct ext3_extent);
 +              len = len < 0 ? 0 : len;
 +              ext_debug(tree, "insert %d:%d:%d before: nearest 0x%p, "
-+                              "move %d from 0x%p to 0x%p\n",
-+                              newext->ee_block, newext->ee_start, newext->ee_len,
-+                              nearex, len, nearex + 1, nearex + 2);
++                        "move %d from 0x%p to 0x%p\n",
++                        newext->ee_block, newext->ee_start, newext->ee_len,
++                        nearex, len, nearex + 1, nearex + 2);
 +              memmove(nearex + 1, nearex, len);
 +              path[depth].p_ext = nearex;
 +      }
@@ -1155,8 +1185,8 @@ Index: linux-stage/fs/ext3/extents.c
 +              /* merge with next extent! */
 +              nearex->ee_len += nearex[1].ee_len;
 +              if (nearex + 1 < EXT_LAST_EXTENT(eh)) {
-+                      len = (EXT_LAST_EXTENT(eh) - nearex - 1)
-+                                      * sizeof(struct ext3_extent);
++                      len = (EXT_LAST_EXTENT(eh) - nearex - 1) *
++                              sizeof(struct ext3_extent);
 +                      memmove(nearex + 1, nearex + 2, len);
 +              }
 +              eh->eh_entries--;
@@ -1186,7 +1216,8 @@ Index: linux-stage/fs/ext3/extents.c
 +                      unsigned long num, ext_prepare_callback func)
 +{
 +      struct ext3_ext_path *path = NULL;
-+      struct ext3_extent *ex, cbex;
++      struct ext3_ext_cache cbex;
++      struct ext3_extent *ex;
 +      unsigned long next, start = 0, end = 0;
 +      unsigned long last = block + num;
 +      int depth, exists, err = 0;
@@ -1245,14 +1276,20 @@ Index: linux-stage/fs/ext3/extents.c
 +              EXT_ASSERT(end > start);
 +
 +              if (!exists) {
-+                      cbex.ee_block = start;
-+                      cbex.ee_len = end - start;
-+                      cbex.ee_start = 0;
-+              } else
-+                      cbex = *ex;
++                      cbex.ec_block = start;
++                      cbex.ec_len = end - start;
++                      cbex.ec_start = 0;
++                      cbex.ec_type = EXT3_EXT_CACHE_GAP;
++              } else {
++                      cbex.ec_block = ex->ee_block;
++                      cbex.ec_len = ex->ee_len;
++                      cbex.ec_start = ex->ee_start;
++                      cbex.ec_type = EXT3_EXT_CACHE_EXTENT;
++              }
 +
++              EXT_ASSERT(cbex.ec_len > 0);
 +              EXT_ASSERT(path[depth].p_hdr);
-+              err = func(tree, path, &cbex, exists);
++              err = func(tree, path, &cbex);
 +              ext3_ext_drop_refs(path);
 +
 +              if (err < 0)
@@ -1270,7 +1307,7 @@ Index: linux-stage/fs/ext3/extents.c
 +                      path = NULL;
 +              }
 +
-+              block = cbex.ee_block + cbex.ee_len;
++              block = cbex.ec_block + cbex.ec_len;
 +      }
 +
 +      if (path) {
@@ -1283,7 +1320,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static inline void
 +ext3_ext_put_in_cache(struct ext3_extents_tree *tree, __u32 block,
-+                      __u32 len, __u32 start, int type)
++                    __u32 len, __u32 start, int type)
 +{
 +      EXT_ASSERT(len > 0);
 +      if (tree->cex) {
@@ -1300,8 +1337,8 @@ Index: linux-stage/fs/ext3/extents.c
 + */
 +static inline void
 +ext3_ext_put_gap_in_cache(struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              unsigned long block)
++                        struct ext3_ext_path *path,
++                        unsigned long block)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      unsigned long lblock, len;
@@ -1320,16 +1357,16 @@ Index: linux-stage/fs/ext3/extents.c
 +              lblock = block;
 +              len = ex->ee_block - block;
 +              ext_debug(tree, "cache gap(before): %lu [%lu:%lu]",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len);
 +      } else if (block >= ex->ee_block + ex->ee_len) {
 +              lblock = ex->ee_block + ex->ee_len;
 +              len = ext3_ext_next_allocated_block(path);
 +              ext_debug(tree, "cache gap(after): [%lu:%lu] %lu",
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) block);
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) block);
 +              EXT_ASSERT(len > lblock);
 +              len = len - lblock;
 +      } else {
@@ -1343,7 +1380,7 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static inline int
 +ext3_ext_in_cache(struct ext3_extents_tree *tree, unsigned long block,
-+                      struct ext3_extent *ex)
++                struct ext3_extent *ex)
 +{
 +      struct ext3_ext_cache *cex = tree->cex;
 +
@@ -1356,16 +1393,16 @@ Index: linux-stage/fs/ext3/extents.c
 +              return EXT3_EXT_CACHE_NO;
 +
 +      EXT_ASSERT(cex->ec_type == EXT3_EXT_CACHE_GAP ||
-+                      cex->ec_type == EXT3_EXT_CACHE_EXTENT);
++                 cex->ec_type == EXT3_EXT_CACHE_EXTENT);
 +      if (block >= cex->ec_block && block < cex->ec_block + cex->ec_len) {
 +              ex->ee_block = cex->ec_block;
 +              ex->ee_start = cex->ec_start;
 +              ex->ee_len = cex->ec_len;
 +              ext_debug(tree, "%lu cached by %lu:%lu:%lu\n",
-+                              (unsigned long) block,
-+                              (unsigned long) ex->ee_block,
-+                              (unsigned long) ex->ee_len,
-+                              (unsigned long) ex->ee_start);
++                        (unsigned long) block,
++                        (unsigned long) ex->ee_block,
++                        (unsigned long) ex->ee_len,
++                        (unsigned long) ex->ee_start);
 +              return cex->ec_type;
 +      }
 +
@@ -1379,7 +1416,7 @@ Index: linux-stage/fs/ext3/extents.c
 + * last index in the block only
 + */
 +int ext3_ext_rm_idx(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path)
++                  struct ext3_ext_path *path)
 +{
 +      struct buffer_head *bh;
 +      int err;
@@ -1393,7 +1430,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      if ((err = ext3_ext_dirty(handle, tree, path)))
 +              return err;
 +      ext_debug(tree, "index is empty, remove it, free block %d\n",
-+                      path->p_idx->ei_leaf);
++                path->p_idx->ei_leaf);
 +      bh = sb_find_get_block(tree->inode->i_sb, path->p_idx->ei_leaf);
 +      ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
 +      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
@@ -1401,7 +1438,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *tree,
-+                                      struct ext3_ext_path *path)
++                                   struct ext3_ext_path *path)
 +{
 +      int depth = EXT_DEPTH(tree);
 +      int needed;
@@ -1438,8 +1475,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_split_for_rm(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++                    struct ext3_ext_path *path, unsigned long start,
++                    unsigned long end)
 +{
 +      struct ext3_extent *ex, tex;
 +      struct ext3_ext_path *npath;
@@ -1473,7 +1510,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      /* FIXME: some callback to free underlying resource
 +       * and correct ee_start? */
 +      ext_debug(tree, "split extent: head %u:%u, tail %u:%u\n",
-+                      ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
++                ex->ee_block, ex->ee_len, tex.ee_block, tex.ee_len);
 +
 +      npath = ext3_ext_find_extent(tree, ex->ee_block, NULL);
 +      if (IS_ERR(npath))
@@ -1487,13 +1524,12 @@ Index: linux-stage/fs/ext3/extents.c
 +      kfree(npath);
 +
 +      return err;
-+                      
 +}
 +
 +static int
 +ext3_ext_rm_leaf(handle_t *handle, struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path, unsigned long start,
-+                      unsigned long end)
++               struct ext3_ext_path *path, unsigned long start,
++               unsigned long end)
 +{
 +      struct ext3_extent *ex, *fu = NULL, *lu, *le;
 +      int err = 0, correct_index = 0;
@@ -1526,8 +1562,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      }
 +      
 +      lu = ex;
-+      while (ex >= EXT_FIRST_EXTENT(eh) &&
-+                      ex->ee_block + ex->ee_len > start) {
++      while (ex >= EXT_FIRST_EXTENT(eh) && ex->ee_block + ex->ee_len > start) {
 +              ext_debug(tree, "remove ext %u:%u\n", ex->ee_block, ex->ee_len);
 +              path[depth].p_ext = ex;
 +      
@@ -1554,7 +1589,7 @@ Index: linux-stage/fs/ext3/extents.c
 +                      block = ex->ee_block; 
 +                      num = 0;
 +                      EXT_ASSERT(a == ex->ee_block &&
-+                                      b == ex->ee_block + ex->ee_len - 1);
++                                 b == ex->ee_block + ex->ee_len - 1);
 +              }
 +
 +              if (ex == EXT_FIRST_EXTENT(eh))
@@ -1596,7 +1631,7 @@ Index: linux-stage/fs/ext3/extents.c
 +                      goto out;
 +
 +              ext_debug(tree, "new extent: %u:%u:%u\n",
-+                              ex->ee_block, ex->ee_len, ex->ee_start);
++                        ex->ee_block, ex->ee_len, ex->ee_start);
 +              ex--;
 +      }
 +
@@ -1660,7 +1695,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_remove_space(struct ext3_extents_tree *tree,
-+                              unsigned long start, unsigned long end)
++                        unsigned long start, unsigned long end)
 +{
 +      struct inode *inode = tree->inode;
 +      struct super_block *sb = inode->i_sb;
@@ -1684,8 +1719,7 @@ Index: linux-stage/fs/ext3/extents.c
 +       */
 +      path = kmalloc(sizeof(struct ext3_ext_path) * (depth + 1), GFP_KERNEL);
 +      if (IS_ERR(path)) {
-+              ext3_error(sb, "ext3_ext_remove_space",
-+                              "Can't allocate path array");
++              ext3_error(sb, __FUNCTION__, "Can't allocate path array");
 +              ext3_journal_stop(handle);
 +              return -ENOMEM;
 +      }
@@ -1717,19 +1751,19 @@ Index: linux-stage/fs/ext3/extents.c
 +                              ext3_ext_last_covered(path[i].p_hdr, end);
 +                      path[i].p_block = path[i].p_hdr->eh_entries + 1;
 +                      ext_debug(tree, "init index ptr: hdr 0x%p, num %d\n",
-+                                      path[i].p_hdr, path[i].p_hdr->eh_entries);
++                                path[i].p_hdr, path[i].p_hdr->eh_entries);
 +              } else {
 +                      /* we've already was here, see at next index */
 +                      path[i].p_idx--;
 +              }
 +
 +              ext_debug(tree, "level %d - index, first 0x%p, cur 0x%p\n",
-+                              i, EXT_FIRST_INDEX(path[i].p_hdr),
-+                              path[i].p_idx);
++                        i, EXT_FIRST_INDEX(path[i].p_hdr),
++                        path[i].p_idx);
 +              if (ext3_ext_more_to_rm(path + i)) {
 +                      /* go to the next level */
 +                      ext_debug(tree, "move to level %d (block %d)\n",
-+                                      i + 1, path[i].p_idx->ei_leaf);
++                                i + 1, path[i].p_idx->ei_leaf);
 +                      memset(path + i + 1, 0, sizeof(*path));
 +                      path[i+1].p_bh = sb_bread(sb, path[i].p_idx->ei_leaf);
 +                      if (!path[i+1].p_bh) {
@@ -1852,7 +1886,7 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static int ext3_ext_mergable(struct ext3_extent *ex1,
-+                              struct ext3_extent *ex2)
++                           struct ext3_extent *ex2)
 +{
 +      /* FIXME: support for large fs */
 +      if (ex1->ee_start + ex1->ee_len == ex2->ee_start)
@@ -1862,8 +1896,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks_credits(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                         struct ext3_extent *ex,
++                         unsigned long from, unsigned long to)
 +{
 +      int needed;
 +      
@@ -1878,8 +1912,8 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_remove_blocks(struct ext3_extents_tree *tree,
-+                              struct ext3_extent *ex,
-+                              unsigned long from, unsigned long to)
++                 struct ext3_extent *ex,
++                 unsigned long from, unsigned long to)
 +{
 +      int needed = ext3_remove_blocks_credits(tree, ex, from, to);
 +      handle_t *handle = ext3_journal_start(tree->inode, needed);
@@ -1894,7 +1928,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              num = ex->ee_block + ex->ee_len - from;
 +              start = ex->ee_start + ex->ee_len - num;
 +              ext_debug(tree, "free last %lu blocks starting %lu\n",
-+                              num, start);
++                        num, start);
 +              for (i = 0; i < num; i++) {
 +                      bh = sb_find_get_block(tree->inode->i_sb, start + i);
 +                      ext3_forget(handle, 0, tree->inode, bh, start + i);
@@ -1902,17 +1936,17 @@ Index: linux-stage/fs/ext3/extents.c
 +              ext3_free_blocks(handle, tree->inode, start, num);
 +      } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
 +              printk("strange request: removal %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      } else {
 +              printk("strange request: removal(2) %lu-%lu from %u:%u\n",
-+                      from, to, ex->ee_block, ex->ee_len);
++                     from, to, ex->ee_block, ex->ee_len);
 +      }
 +      ext3_journal_stop(handle);
 +      return 0;
 +}
 +
 +static int ext3_ext_find_goal(struct inode *inode,
-+                              struct ext3_ext_path *path, unsigned long block)
++                            struct ext3_ext_path *path, unsigned long block)
 +{
 +      struct ext3_inode_info *ei = EXT3_I(inode);
 +      unsigned long bg_start;
@@ -1942,8 +1976,8 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +static int ext3_new_block_cb(handle_t *handle, struct ext3_extents_tree *tree,
-+                              struct ext3_ext_path *path,
-+                              struct ext3_extent *ex, int *err)
++                           struct ext3_ext_path *path,
++                           struct ext3_extent *ex, int *err)
 +{
 +      struct inode *inode = tree->inode;
 +      int newblock, goal;
@@ -1980,7 +2014,7 @@ Index: linux-stage/fs/ext3/extents.c
 +};
 +
 +void ext3_init_tree_desc(struct ext3_extents_tree *tree,
-+                              struct inode *inode)
++                       struct inode *inode)
 +{
 +      tree->inode = inode;
 +      tree->root = (void *) EXT3_I(inode)->i_data;
@@ -1991,8 +2025,8 @@ Index: linux-stage/fs/ext3/extents.c
 +}
 +
 +int ext3_ext_get_block(handle_t *handle, struct inode *inode,
-+                      long iblock, struct buffer_head *bh_result,
-+                      int create, int extend_disksize)
++                     long iblock, struct buffer_head *bh_result,
++                     int create, int extend_disksize)
 +{
 +      struct ext3_ext_path *path = NULL;
 +      struct ext3_extent newex;
@@ -2003,7 +2037,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      clear_buffer_new(bh_result);
 +      ext3_init_tree_desc(&tree, inode);
 +      ext_debug(&tree, "block %d requested for inode %u\n",
-+                      (int) iblock, (unsigned) inode->i_ino);
++                (int) iblock, (unsigned) inode->i_ino);
 +      down(&EXT3_I(inode)->truncate_sem);
 +
 +      /* check in cache */
@@ -2046,11 +2080,11 @@ Index: linux-stage/fs/ext3/extents.c
 +              if (iblock >= ex->ee_block && iblock < ex->ee_block + ex->ee_len) {
 +                      newblock = iblock - ex->ee_block + ex->ee_start;
 +                      ext_debug(&tree, "%d fit into %d:%d -> %d\n",
-+                                      (int) iblock, ex->ee_block, ex->ee_len,
-+                                      newblock);
++                                (int) iblock, ex->ee_block, ex->ee_len,
++                                newblock);
 +                      ext3_ext_put_in_cache(&tree, ex->ee_block,
-+                                              ex->ee_len, ex->ee_start,
-+                                              EXT3_EXT_CACHE_EXTENT);
++                                            ex->ee_len, ex->ee_start,
++                                            EXT3_EXT_CACHE_EXTENT);
 +                      goto out;
 +              }
 +      }
@@ -2071,7 +2105,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      if (!newblock)
 +              goto out2;
 +      ext_debug(&tree, "allocate new block: goal %d, found %d\n",
-+                      goal, newblock);
++                goal, newblock);
 +
 +      /* try to insert new extent into found leaf and return */
 +      newex.ee_block = iblock;
@@ -2089,7 +2123,7 @@ Index: linux-stage/fs/ext3/extents.c
 +      set_buffer_new(bh_result);
 +
 +      ext3_ext_put_in_cache(&tree, newex.ee_block, newex.ee_len,
-+                              newex.ee_start, EXT3_EXT_CACHE_EXTENT);
++                            newex.ee_start, EXT3_EXT_CACHE_EXTENT);
 +out:
 +      ext3_ext_show_leaf(&tree, path);
 +      map_bh(bh_result, inode->i_sb, newblock);
@@ -2147,8 +2181,8 @@ Index: linux-stage/fs/ext3/extents.c
 +      EXT3_I(inode)->i_disksize = inode->i_size;
 +      ext3_mark_inode_dirty(handle, inode);
 +
-+      last_block = (inode->i_size + sb->s_blocksize - 1)
-+                      >> EXT3_BLOCK_SIZE_BITS(sb);
++      last_block = (inode->i_size + sb->s_blocksize - 1) >>
++                      EXT3_BLOCK_SIZE_BITS(sb);
 +      err = ext3_ext_remove_space(&tree, last_block, EXT_MAX_BLOCK);
 +      
 +      /* In a multi-transaction truncate, we only make the final
@@ -2216,13 +2250,14 @@ Index: linux-stage/fs/ext3/extents.c
 +      
 +static int
 +ext3_ext_store_extent_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *newex, int exist)
++                       struct ext3_ext_path *path,
++                       struct ext3_ext_cache *newex)
 +{
 +      struct ext3_extent_buf *buf = (struct ext3_extent_buf *) tree->private;
 +
-+      if (!exist)
++      if (newex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
++
 +      if (buf->err < 0)
 +              return EXT_BREAK;
 +      if (buf->cur - buf->buffer + sizeof(*newex) > buf->buflen)
@@ -2240,14 +2275,14 @@ Index: linux-stage/fs/ext3/extents.c
 +
 +static int
 +ext3_ext_collect_stats_cb(struct ext3_extents_tree *tree,
-+                      struct ext3_ext_path *path,
-+                      struct ext3_extent *ex, int exist)
++                        struct ext3_ext_path *path,
++                        struct ext3_ext_cache *ex)
 +{
 +      struct ext3_extent_tree_stats *buf =
 +              (struct ext3_extent_tree_stats *) tree->private;
 +      int depth;
 +
-+      if (!exist)
++      if (ex->ec_type != EXT3_EXT_CACHE_EXTENT)
 +              return EXT_CONTINUE;
 +
 +      depth = EXT_DEPTH(tree);
@@ -2278,7 +2313,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              tree.private = &buf;
 +              down(&EXT3_I(inode)->truncate_sem);
 +              err = ext3_ext_walk_space(&tree, buf.start, EXT_MAX_BLOCK,
-+                                              ext3_ext_store_extent_cb);
++                                        ext3_ext_store_extent_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (err == 0)
 +                      err = buf.err;
@@ -2293,7 +2328,7 @@ Index: linux-stage/fs/ext3/extents.c
 +              buf.leaf_num = 0;
 +              tree.private = &buf;
 +              err = ext3_ext_walk_space(&tree, 0, EXT_MAX_BLOCK,
-+                                              ext3_ext_collect_stats_cb);
++                                        ext3_ext_collect_stats_cb);
 +              up(&EXT3_I(inode)->truncate_sem);
 +              if (!err)
 +                      err = copy_to_user((void *) arg, &buf, sizeof(buf));
@@ -2315,19 +2350,26 @@ Index: linux-stage/fs/ext3/extents.c
 +EXPORT_SYMBOL(ext3_ext_walk_space);
 +EXPORT_SYMBOL(ext3_ext_find_goal);
 +EXPORT_SYMBOL(ext3_ext_calc_credits_for_insert);
-+
 Index: linux-stage/fs/ext3/ialloc.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/ialloc.c  2005-02-25 14:50:50.304202816 +0200
 +++ linux-stage/fs/ext3/ialloc.c       2005-02-25 15:33:48.920193600 +0200
-@@ -646,6 +646,10 @@
+@@ -646,6 +646,18 @@
                DQUOT_FREE_INODE(inode);
                goto fail2;
        }
-+      if (test_opt(sb, EXTENTS)) {
-+              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
-+              ext3_extents_initialize_blockmap(handle, inode);
-+      }
++      if (test_opt(sb, EXTENTS) && S_ISREG(inode->i_mode)) {
++              EXT3_I(inode)->i_flags |= EXT3_EXTENTS_FL;
++              ext3_extents_initialize_blockmap(handle, inode);
++              if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS)) {
++                      err = ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
++                      if (err) goto fail;
++                      EXT3_SET_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_EXTENTS);
++                      BUFFER_TRACE(EXT3_SB(sb)->s_sbh, "call ext3_journal_dirty_metadata");
++                      err = ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
++              }
++      }
++
        err = ext3_mark_inode_dirty(handle, inode);
        if (err) {
                ext3_std_error(sb, err);
@@ -2341,13 +2383,13 @@ Index: linux-stage/fs/ext3/inode.c
  
 +static inline int
 +ext3_get_block_wrap(handle_t *handle, struct inode *inode, long block,
-+              struct buffer_head *bh, int create, int extend_disksize)
++                  struct buffer_head *bh, int create, int extend_disksize)
 +{
 +      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
 +              return ext3_ext_get_block(handle, inode, block, bh, create,
-+                                              extend_disksize);
++                                        extend_disksize);
 +      return ext3_get_block_handle(handle, inode, block, bh, create,
-+                                      extend_disksize);
++                                   extend_disksize);
 +}
 +
  static int ext3_get_block(struct inode *inode, sector_t iblock,
@@ -2360,7 +2402,7 @@ Index: linux-stage/fs/ext3/inode.c
 -      ret = ext3_get_block_handle(handle, inode, iblock,
 -                              bh_result, create, 1);
 +      ret = ext3_get_block_wrap(handle, inode, iblock,
-+                                      bh_result, create, 1);
++                                bh_result, create, 1);
        return ret;
  }
  
@@ -2405,9 +2447,9 @@ Index: linux-stage/fs/ext3/inode.c
        int indirects = (EXT3_NDIR_BLOCKS % bpp) ? 5 : 3;
        int ret;
  
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
-+              return ext3_ext_writepage_trans_blocks(inode, bpp);
-+ 
++      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL)
++              return ext3_ext_writepage_trans_blocks(inode, bpp);
++
        if (ext3_should_journal_data(inode))
                ret = 3 * (bpp + indirects) + 2;
        else
@@ -2432,18 +2474,16 @@ Index: linux-stage/fs/ext3/super.c
        struct ext3_super_block *es = sbi->s_es;
        int i;
  
-+      ext3_ext_release(sb);
++      ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
        if (!(sb->s_flags & MS_RDONLY)) {
-@@ -457,6 +458,10 @@
+@@ -457,6 +458,8 @@
  #endif
        ei->i_rsv_window.rsv_end = EXT3_RESERVE_WINDOW_NOT_ALLOCATED;
        ei->vfs_inode.i_version = 1;
-+      ei->i_cached_extent[0] = 0;
-+      ei->i_cached_extent[1] = 0;
-+      ei->i_cached_extent[2] = 0;
-+      ei->i_cached_extent[3] = 0;
++      
++      memset(&ei->i_cached_extent, 0, sizeof(ei->i_cached_extent));
        return &ei->vfs_inode;
  }
  
@@ -2482,8 +2522,8 @@ Index: linux-stage/fs/ext3/super.c
        percpu_counter_mod(&sbi->s_dirs_counter,
                ext3_count_dirs(sb));
  
-+      ext3_ext_init(sb);
-+ 
++      ext3_ext_init(sb);
++
        return 0;
  
  failed_mount3:
@@ -2506,14 +2546,17 @@ Index: linux-stage/include/linux/ext3_fs.h
 ===================================================================
 --- linux-stage.orig/include/linux/ext3_fs.h   2005-02-25 14:53:56.424908168 +0200
 +++ linux-stage/include/linux/ext3_fs.h        2005-02-25 15:39:12.841950008 +0200
-@@ -186,6 +186,7 @@
+@@ -186,8 +186,9 @@
  #define EXT3_DIRSYNC_FL                       0x00010000 /* dirsync behaviour (directories only) */
  #define EXT3_TOPDIR_FL                        0x00020000 /* Top of directory hierarchies*/
  #define EXT3_RESERVED_FL              0x80000000 /* reserved for ext3 lib */
 +#define EXT3_EXTENTS_FL                       0x00080000 /* Inode uses extents */
  
- #define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
+-#define EXT3_FL_USER_VISIBLE          0x0003DFFF /* User visible flags */
++#define EXT3_FL_USER_VISIBLE          0x000BDFFF /* User visible flags */
  #define EXT3_FL_USER_MODIFIABLE               0x000380FF /* User modifiable flags */
+ /*
 @@ -237,6 +238,9 @@
  #endif
  #define EXT3_IOC_GETRSVSZ             _IOR('f', 5, long)
@@ -2524,16 +2567,30 @@ Index: linux-stage/include/linux/ext3_fs.h
  
  /*
   * Structure of an inode on the disk
-@@ -359,6 +363,9 @@
+@@ -359,6 +363,8 @@
  #define EXT3_MOUNT_RESERVATION                0x20000 /* Preallocation */
  #define EXT3_MOUNT_IOPEN              0x40000 /* Allow access via iopen */
  #define EXT3_MOUNT_IOPEN_NOPRIV               0x80000 /* Make iopen world-readable */
 +#define EXT3_MOUNT_EXTENTS            0x100000/* Extents support */
 +#define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
-+
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
  #ifndef _LINUX_EXT2_FS_H
+@@ -503,11 +509,13 @@
+ #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
+ #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
+ #define EXT3_FEATURE_INCOMPAT_META_BG         0x0010
++#define EXT3_FEATURE_INCOMPAT_EXTENTS         0x0040 /* extents support */
+ #define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
+ #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
+                                        EXT3_FEATURE_INCOMPAT_RECOVER| \
+-                                       EXT3_FEATURE_INCOMPAT_META_BG)
++                                       EXT3_FEATURE_INCOMPAT_META_BG| \
++                                       EXT3_FEATURE_INCOMPAT_EXTENTS)
+ #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
+                                        EXT3_FEATURE_RO_COMPAT_LARGE_FILE| \
+                                        EXT3_FEATURE_RO_COMPAT_BTREE_DIR)
 @@ -756,6 +763,7 @@
  
  
@@ -2549,7 +2606,7 @@ Index: linux-stage/include/linux/ext3_fs.h
 +/* extents.c */
 +extern int ext3_ext_writepage_trans_blocks(struct inode *, int);
 +extern int ext3_ext_get_block(handle_t *, struct inode *, long,
-+                              struct buffer_head *, int, int);
++                            struct buffer_head *, int, int);
 +extern void ext3_ext_truncate(struct inode *, struct page *);
 +extern void ext3_ext_init(struct super_block *);
 +extern void ext3_ext_release(struct super_block *);
@@ -2563,7 +2620,7 @@ Index: linux-stage/include/linux/ext3_extents.h
 ===================================================================
 --- linux-stage.orig/include/linux/ext3_extents.h      2005-02-25 15:33:48.891198008 +0200
 +++ linux-stage/include/linux/ext3_extents.h   2005-02-25 15:33:48.944189952 +0200
-@@ -0,0 +1,252 @@
+@@ -0,0 +1,264 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -2605,7 +2662,7 @@ Index: linux-stage/include/linux/ext3_extents.h
 + */
 +#define EXT_DEBUG_
 +#ifdef EXT_DEBUG
-+#define ext_debug(tree,fmt,a...)                      \
++#define ext_debug(tree,fmt,a...)                      \
 +do {                                                  \
 +      if (test_opt((tree)->inode->i_sb, EXTDEBUG))    \
 +              printk(fmt, ##a);                       \
@@ -2718,14 +2775,14 @@ Index: linux-stage/include/linux/ext3_extents.h
 +      int (*mark_buffer_dirty)(handle_t *h, void *buffer);
 +      int (*mergable)(struct ext3_extent *ex1, struct ext3_extent *ex2);
 +      int (*remove_extent_credits)(struct ext3_extents_tree *,
-+                                      struct ext3_extent *, unsigned long,
-+                                      unsigned long);
++                                   struct ext3_extent *, unsigned long,
++                                   unsigned long);
 +      int (*remove_extent)(struct ext3_extents_tree *,
-+                              struct ext3_extent *, unsigned long,
-+                              unsigned long);
++                           struct ext3_extent *, unsigned long,
++                           unsigned long);
 +      int (*new_block)(handle_t *, struct ext3_extents_tree *,
-+                              struct ext3_ext_path *, struct ext3_extent *,
-+                              int *);
++                       struct ext3_ext_path *, struct ext3_extent *,
++                       int *);
 +};
 +
 +/*
@@ -2735,8 +2792,8 @@ Index: linux-stage/include/linux/ext3_extents.h
 + * callback must return valid extent (passed or newly created)
 + */
 +typedef int (*ext_prepare_callback)(struct ext3_extents_tree *,
-+                                      struct ext3_ext_path *,
-+                                      struct ext3_extent *, int);
++                                  struct ext3_ext_path *,
++                                  struct ext3_ext_cache *);
 +
 +#define EXT_CONTINUE  0
 +#define EXT_BREAK     1
@@ -2744,7 +2801,6 @@ Index: linux-stage/include/linux/ext3_extents.h
 +
 +
 +#define EXT_MAX_BLOCK 0xffffffff
-+#define EXT_CACHE_MARK        0xffff
 +
 +
 +#define EXT_FIRST_EXTENT(__hdr__) \
@@ -2776,6 +2832,20 @@ Index: linux-stage/include/linux/ext3_extents.h
 +
 +#define EXT_ASSERT(__x__) if (!(__x__)) BUG();
 +
++#define EXT_CHECK_PATH(tree,path)                                     \
++{                                                                     \
++      int depth = EXT_DEPTH(tree);                                    \
++      BUG_ON((unsigned long) (path) < __PAGE_OFFSET);                 \
++      BUG_ON((unsigned long) (path)[depth].p_idx <                    \
++                      __PAGE_OFFSET && (path)[depth].p_idx != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_ext <                    \
++                      __PAGE_OFFSET && (path)[depth].p_ext != NULL);  \
++      BUG_ON((unsigned long) (path)[depth].p_hdr < __PAGE_OFFSET);    \
++      BUG_ON((unsigned long) (path)[depth].p_bh < __PAGE_OFFSET       \
++                      && depth != 0);                                 \
++      BUG_ON((path)[0].p_depth != depth);                             \
++}
++
 +
 +/*
 + * this structure is used to gather extents from the tree via ioctl
@@ -2797,13 +2867,13 @@ Index: linux-stage/include/linux/ext3_extents.h
 +      int leaf_num;
 +};
 +
++extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_extent_tree_init(handle_t *, struct ext3_extents_tree *);
 +extern int ext3_ext_calc_credits_for_insert(struct ext3_extents_tree *, struct ext3_ext_path *);
 +extern int ext3_ext_insert_extent(handle_t *, struct ext3_extents_tree *, struct ext3_ext_path *, struct ext3_extent *);
 +extern int ext3_ext_walk_space(struct ext3_extents_tree *, unsigned long, unsigned long, ext_prepare_callback);
 +extern int ext3_ext_remove_space(struct ext3_extents_tree *, unsigned long, unsigned long);
 +extern struct ext3_ext_path * ext3_ext_find_extent(struct ext3_extents_tree *, int, struct ext3_ext_path *);
-+extern void ext3_init_tree_desc(struct ext3_extents_tree *, struct inode *);
 +extern int ext3_ext_calc_blockmap_metadata(struct inode *, int);
 +
 +static inline void
@@ -2815,7 +2885,6 @@ Index: linux-stage/include/linux/ext3_extents.h
 +
 +
 +#endif /* _LINUX_EXT3_EXTENTS */
-+
 Index: linux-stage/include/linux/ext3_fs_i.h
 ===================================================================
 --- linux-stage.orig/include/linux/ext3_fs_i.h 2005-02-25 14:50:50.320200384 +0200
@@ -2825,7 +2894,7 @@ Index: linux-stage/include/linux/ext3_fs_i.h
        struct semaphore truncate_sem;
        struct inode vfs_inode;
 +
-+      __u32 i_cached_extent[4];
++      __u32 i_cached_extent[4];
  };
  
  #endif        /* _LINUX_EXT3_FS_I */
diff --git a/lustre/kernel_patches/patches/ext3-extents-asyncdel-2.4.20-rh.patch b/lustre/kernel_patches/patches/ext3-extents-asyncdel-2.4.20-rh.patch
deleted file mode 100644 (file)
index 20eac0a..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-Index: linux-2.4.20-30.9/fs/ext3/inode.c
-===================================================================
---- linux-2.4.20-30.9.orig/fs/ext3/inode.c     2004-05-18 13:55:49.000000000 -0700
-+++ linux-2.4.20-30.9/fs/ext3/inode.c  2004-05-18 13:59:46.000000000 -0700
-@@ -2217,6 +2217,10 @@
-       memcpy(nei->i_data, oei->i_data, sizeof(nei->i_data));
-       memset(oei->i_data, 0, sizeof(oei->i_data));
-+      if (EXT3_I(old_inode)->i_flags & EXT3_EXTENTS_FL) {
-+              EXT3_I(new_inode)->i_flags |= EXT3_EXTENTS_FL;
-+              ext3_extents_initialize_blockmap(handle, old_inode);
-+      }
-       nei->i_disksize = oei->i_disksize;
-       nei->i_state |= EXT3_STATE_DELETE;
-@@ -2447,6 +2451,13 @@
-       brelse (iloc.bh);
-+      if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL) {
-+              inode->u.ext3_i.i_cached_extent[0] = 0;
-+              inode->u.ext3_i.i_cached_extent[1] = 0;
-+              inode->u.ext3_i.i_cached_extent[2] = 0;
-+              inode->u.ext3_i.i_cached_extent[3] = 0;
-+      }
-+
-       if (S_ISREG(inode->i_mode)) {
-               inode->i_op = &ext3_file_inode_operations;
-               inode->i_fop = &ext3_file_operations;
index d425fe6..e5a5616 100644 (file)
@@ -6,10 +6,10 @@ Index: 57chaos/fs/ext3/inode.c
  
        memcpy(nei->i_data, oei->i_data, sizeof(nei->i_data));
        memset(oei->i_data, 0, sizeof(oei->i_data));
-+      if (EXT3_I(old_inode)->i_flags & EXT3_EXTENTS_FL) {
-+              EXT3_I(new_inode)->i_flags |= EXT3_EXTENTS_FL;
-+              ext3_extents_initialize_blockmap(handle, old_inode);
-+      }
++      if (EXT3_I(old_inode)->i_flags & EXT3_EXTENTS_FL) {
++              EXT3_I(new_inode)->i_flags |= EXT3_EXTENTS_FL;
++              ext3_extents_initialize_blockmap(handle, old_inode);
++      }
  
        nei->i_disksize = oei->i_disksize;
        nei->i_state |= EXT3_STATE_DELETE;
index 44432fc..43681a6 100644 (file)
@@ -22,7 +22,7 @@ Index: linux-2.4.24/fs/ext3/inode.c
        memset(oei->i_data, 0, sizeof(oei->i_data));
 +      if (EXT3_I(old_inode)->i_flags & EXT3_EXTENTS_FL) {
 +              EXT3_I(new_inode)->i_flags |= EXT3_EXTENTS_FL;
-+              ext3_extents_initialize_blockmap(handle, old_inode);
++              ext3_extents_initialize_blockmap(handle, old_inode);
 +      }
  
        nei->i_disksize = oei->i_disksize;
diff --git a/lustre/kernel_patches/patches/ext3-htree-suse.patch b/lustre/kernel_patches/patches/ext3-htree-suse.patch
deleted file mode 100644 (file)
index 3e5148e..0000000
+++ /dev/null
@@ -1,2557 +0,0 @@
- fs/ext3/Makefile           |    2 
- fs/ext3/dir.c              |  302 +++++++++
- fs/ext3/file.c             |    3 
- fs/ext3/hash.c             |  215 ++++++
- fs/ext3/namei.c            | 1420 ++++++++++++++++++++++++++++++++++++++++-----
- fs/ext3/super.c            |    7 
- include/linux/ext3_fs.h    |   85 ++
- include/linux/ext3_fs_sb.h |    2 
- include/linux/ext3_jbd.h   |    2 
- include/linux/rbtree.h     |    2 
- lib/rbtree.c               |   42 +
- 11 files changed, 1921 insertions(+), 161 deletions(-)
-
-Index: linux-2.4.21-suse/fs/ext3/dir.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/dir.c       2001-11-10 01:25:04.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/dir.c    2003-10-29 23:17:20.000000000 +0300
-@@ -21,12 +21,16 @@
- #include <linux/fs.h>
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
-+#include <linux/slab.h>
-+#include <linux/rbtree.h>
- static unsigned char ext3_filetype_table[] = {
-       DT_UNKNOWN, DT_REG, DT_DIR, DT_CHR, DT_BLK, DT_FIFO, DT_SOCK, DT_LNK
- };
- static int ext3_readdir(struct file *, void *, filldir_t);
-+static int ext3_dx_readdir(struct file * filp,
-+                         void * dirent, filldir_t filldir);
- struct file_operations ext3_dir_operations = {
-       read:           generic_read_dir,
-@@ -35,6 +39,17 @@
-       fsync:          ext3_sync_file,         /* BKL held */
- };
-+
-+static unsigned char get_dtype(struct super_block *sb, int filetype)
-+{
-+      if (!EXT3_HAS_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_FILETYPE) ||
-+          (filetype >= EXT3_FT_MAX))
-+              return DT_UNKNOWN;
-+
-+      return (ext3_filetype_table[filetype]);
-+}
-+                             
-+
- int ext3_check_dir_entry (const char * function, struct inode * dir,
-                         struct ext3_dir_entry_2 * de,
-                         struct buffer_head * bh,
-@@ -79,6 +94,16 @@
-       sb = inode->i_sb;
-+      if (is_dx(inode)) {
-+              err = ext3_dx_readdir(filp, dirent, filldir);
-+              if (err != ERR_BAD_DX_DIR)
-+                      return err;
-+              /*
-+               * We don't set the inode dirty flag since it's not
-+               * critical that it get flushed back to the disk.
-+               */
-+              EXT3_I(filp->f_dentry->d_inode)->i_flags &= ~EXT3_INDEX_FL;
-+      }
-       stored = 0;
-       bh = NULL;
-       offset = filp->f_pos & (sb->s_blocksize - 1);
-@@ -162,18 +187,12 @@
-                                * during the copy operation.
-                                */
-                               unsigned long version = filp->f_version;
--                              unsigned char d_type = DT_UNKNOWN;
--                              if (EXT3_HAS_INCOMPAT_FEATURE(sb,
--                                              EXT3_FEATURE_INCOMPAT_FILETYPE)
--                                              && de->file_type < EXT3_FT_MAX)
--                                      d_type =
--                                        ext3_filetype_table[de->file_type];
-                               error = filldir(dirent, de->name,
-                                               de->name_len,
-                                               filp->f_pos,
-                                               le32_to_cpu(de->inode),
--                                              d_type);
-+                                              get_dtype(sb, de->file_type));
-                               if (error)
-                                       break;
-                               if (version != filp->f_version)
-@@ -188,3 +207,272 @@
-       UPDATE_ATIME(inode);
-       return 0;
- }
-+
-+#ifdef CONFIG_EXT3_INDEX
-+/*
-+ * These functions convert from the major/minor hash to an f_pos
-+ * value.
-+ * 
-+ * Currently we only use major hash numer.  This is unfortunate, but
-+ * on 32-bit machines, the same VFS interface is used for lseek and
-+ * llseek, so if we use the 64 bit offset, then the 32-bit versions of
-+ * lseek/telldir/seekdir will blow out spectacularly, and from within
-+ * the ext2 low-level routine, we don't know if we're being called by
-+ * a 64-bit version of the system call or the 32-bit version of the
-+ * system call.  Worse yet, NFSv2 only allows for a 32-bit readdir
-+ * cookie.  Sigh.
-+ */
-+#define hash2pos(major, minor)        (major >> 1)
-+#define pos2maj_hash(pos)     ((pos << 1) & 0xffffffff)
-+#define pos2min_hash(pos)     (0)
-+
-+/*
-+ * This structure holds the nodes of the red-black tree used to store
-+ * the directory entry in hash order.
-+ */
-+struct fname {
-+      __u32           hash;
-+      __u32           minor_hash;
-+      rb_node_t       rb_hash; 
-+      struct fname    *next;
-+      __u32           inode;
-+      __u8            name_len;
-+      __u8            file_type;
-+      char            name[0];
-+};
-+
-+/*
-+ * This functoin implements a non-recursive way of freeing all of the
-+ * nodes in the red-black tree.
-+ */
-+static void free_rb_tree_fname(rb_root_t *root)
-+{
-+      rb_node_t       *n = root->rb_node;
-+      rb_node_t       *parent;
-+      struct fname    *fname;
-+
-+      while (n) {
-+              /* Do the node's children first */
-+              if ((n)->rb_left) {
-+                      n = n->rb_left;
-+                      continue;
-+              }
-+              if (n->rb_right) {
-+                      n = n->rb_right;
-+                      continue;
-+              }
-+              /*
-+               * The node has no children; free it, and then zero
-+               * out parent's link to it.  Finally go to the
-+               * beginning of the loop and try to free the parent
-+               * node.
-+               */
-+              parent = n->rb_parent;
-+              fname = rb_entry(n, struct fname, rb_hash);
-+              kfree(fname);
-+              if (!parent)
-+                      root->rb_node = 0;
-+              else if (parent->rb_left == n)
-+                      parent->rb_left = 0;
-+              else if (parent->rb_right == n)
-+                      parent->rb_right = 0;
-+              n = parent;
-+      }
-+      root->rb_node = 0;
-+}
-+
-+
-+struct dir_private_info *create_dir_info(loff_t pos)
-+{
-+      struct dir_private_info *p;
-+
-+      p = kmalloc(sizeof(struct dir_private_info), GFP_KERNEL);
-+      if (!p)
-+              return NULL;
-+      p->root.rb_node = 0;
-+      p->curr_node = 0;
-+      p->extra_fname = 0;
-+      p->last_pos = 0;
-+      p->curr_hash = pos2maj_hash(pos);
-+      p->curr_minor_hash = pos2min_hash(pos);
-+      p->next_hash = 0;
-+      return p;
-+}
-+
-+void ext3_htree_free_dir_info(struct dir_private_info *p)
-+{
-+      free_rb_tree_fname(&p->root);
-+      kfree(p);
-+}
-+              
-+/*
-+ * Given a directory entry, enter it into the fname rb tree.
-+ */
-+int ext3_htree_store_dirent(struct file *dir_file, __u32 hash,
-+                           __u32 minor_hash,
-+                           struct ext3_dir_entry_2 *dirent)
-+{
-+      rb_node_t **p, *parent = NULL;
-+      struct fname * fname, *new_fn;
-+      struct dir_private_info *info;
-+      int len;
-+
-+      info = (struct dir_private_info *) dir_file->private_data;
-+      p = &info->root.rb_node;
-+
-+      /* Create and allocate the fname structure */
-+      len = sizeof(struct fname) + dirent->name_len + 1;
-+      new_fn = kmalloc(len, GFP_KERNEL);
-+      if (!new_fn)
-+              return -ENOMEM;
-+      memset(new_fn, 0, len);
-+      new_fn->hash = hash;
-+      new_fn->minor_hash = minor_hash;
-+      new_fn->inode = le32_to_cpu(dirent->inode);
-+      new_fn->name_len = dirent->name_len;
-+      new_fn->file_type = dirent->file_type;
-+      memcpy(new_fn->name, dirent->name, dirent->name_len);
-+      new_fn->name[dirent->name_len] = 0;
-+      
-+      while (*p) {
-+              parent = *p;
-+              fname = rb_entry(parent, struct fname, rb_hash);
-+
-+              /*
-+               * If the hash and minor hash match up, then we put
-+               * them on a linked list.  This rarely happens...
-+               */
-+              if ((new_fn->hash == fname->hash) &&
-+                  (new_fn->minor_hash == fname->minor_hash)) {
-+                      new_fn->next = fname->next;
-+                      fname->next = new_fn;
-+                      return 0;
-+              }
-+                      
-+              if (new_fn->hash < fname->hash)
-+                      p = &(*p)->rb_left;
-+              else if (new_fn->hash > fname->hash)
-+                      p = &(*p)->rb_right;
-+              else if (new_fn->minor_hash < fname->minor_hash)
-+                      p = &(*p)->rb_left;
-+              else /* if (new_fn->minor_hash > fname->minor_hash) */
-+                      p = &(*p)->rb_right;
-+      }
-+
-+      rb_link_node(&new_fn->rb_hash, parent, p);
-+      rb_insert_color(&new_fn->rb_hash, &info->root);
-+      return 0;
-+}
-+
-+
-+
-+/*
-+ * This is a helper function for ext3_dx_readdir.  It calls filldir
-+ * for all entres on the fname linked list.  (Normally there is only
-+ * one entry on the linked list, unless there are 62 bit hash collisions.)
-+ */
-+static int call_filldir(struct file * filp, void * dirent,
-+                      filldir_t filldir, struct fname *fname)
-+{
-+      struct dir_private_info *info = filp->private_data;
-+      loff_t  curr_pos;
-+      struct inode *inode = filp->f_dentry->d_inode;
-+      struct super_block * sb;
-+      int error;
-+
-+      sb = inode->i_sb;
-+      
-+      if (!fname) {
-+              printk("call_filldir: called with null fname?!?\n");
-+              return 0;
-+      }
-+      curr_pos = hash2pos(fname->hash, fname->minor_hash);
-+      while (fname) {
-+              error = filldir(dirent, fname->name,
-+                              fname->name_len, curr_pos, 
-+                              fname->inode,
-+                              get_dtype(sb, fname->file_type));
-+              if (error) {
-+                      filp->f_pos = curr_pos;
-+                      info->extra_fname = fname->next;
-+                      return error;
-+              }
-+              fname = fname->next;
-+      }
-+      return 0;
-+}
-+
-+static int ext3_dx_readdir(struct file * filp,
-+                       void * dirent, filldir_t filldir)
-+{
-+      struct dir_private_info *info = filp->private_data;
-+      struct inode *inode = filp->f_dentry->d_inode;
-+      struct fname *fname;
-+      int     ret;
-+
-+      if (!info) {
-+              info = create_dir_info(filp->f_pos);
-+              if (!info)
-+                      return -ENOMEM;
-+              filp->private_data = info;
-+      }
-+
-+      /* Some one has messed with f_pos; reset the world */
-+      if (info->last_pos != filp->f_pos) {
-+              free_rb_tree_fname(&info->root);
-+              info->curr_node = 0;
-+              info->extra_fname = 0;
-+              info->curr_hash = pos2maj_hash(filp->f_pos);
-+              info->curr_minor_hash = pos2min_hash(filp->f_pos);
-+      }
-+
-+      /*
-+       * If there are any leftover names on the hash collision
-+       * chain, return them first.
-+       */
-+      if (info->extra_fname &&
-+          call_filldir(filp, dirent, filldir, info->extra_fname))
-+              goto finished;
-+
-+      if (!info->curr_node)
-+              info->curr_node = rb_get_first(&info->root);
-+
-+      while (1) {
-+              /*
-+               * Fill the rbtree if we have no more entries,
-+               * or the inode has changed since we last read in the
-+               * cached entries. 
-+               */
-+              if ((!info->curr_node) ||
-+                  (filp->f_version != inode->i_version)) {
-+                      info->curr_node = 0;
-+                      free_rb_tree_fname(&info->root);
-+                      filp->f_version = inode->i_version;
-+                      ret = ext3_htree_fill_tree(filp, info->curr_hash,
-+                                                 info->curr_minor_hash,
-+                                                 &info->next_hash);
-+                      if (ret < 0)
-+                              return ret;
-+                      if (ret == 0)
-+                              break;
-+                      info->curr_node = rb_get_first(&info->root);
-+              }
-+
-+              fname = rb_entry(info->curr_node, struct fname, rb_hash);
-+              info->curr_hash = fname->hash;
-+              info->curr_minor_hash = fname->minor_hash;
-+              if (call_filldir(filp, dirent, filldir, fname))
-+                      break;
-+
-+              info->curr_node = rb_get_next(info->curr_node);
-+              if (!info->curr_node) {
-+                      info->curr_hash = info->next_hash;
-+                      info->curr_minor_hash = 0;
-+              }
-+      }
-+finished:
-+      info->last_pos = filp->f_pos;
-+      UPDATE_ATIME(inode);
-+      return 0;
-+}
-+#endif
-Index: linux-2.4.21-suse/fs/ext3/file.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/file.c      2002-11-29 02:53:15.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/file.c   2003-10-29 23:17:20.000000000 +0300
-@@ -35,6 +35,9 @@
- {
-       if (filp->f_mode & FMODE_WRITE)
-               ext3_discard_prealloc (inode);
-+      if (is_dx(inode) && filp->private_data)
-+              ext3_htree_free_dir_info(filp->private_data);
-+
-       return 0;
- }
-Index: linux-2.4.21-suse/fs/ext3/hash.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/hash.c      2003-10-29 23:17:20.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/hash.c   2003-10-29 23:17:20.000000000 +0300
-@@ -0,0 +1,215 @@
-+/*
-+ *  linux/fs/ext3/hash.c
-+ *
-+ * Copyright (C) 2002 by Theodore Ts'o
-+ *
-+ * This file is released under the GPL v2.
-+ * 
-+ * This file may be redistributed under the terms of the GNU Public
-+ * License.
-+ */
-+
-+#include <linux/fs.h>
-+#include <linux/jbd.h>
-+#include <linux/sched.h>
-+#include <linux/ext3_fs.h>
-+
-+#define DELTA 0x9E3779B9
-+
-+static void TEA_transform(__u32 buf[4], __u32 const in[])
-+{
-+      __u32   sum = 0;
-+      __u32   b0 = buf[0], b1 = buf[1];
-+      __u32   a = in[0], b = in[1], c = in[2], d = in[3];
-+      int     n = 16;
-+
-+      do {                                                    
-+              sum += DELTA;                                   
-+              b0 += ((b1 << 4)+a) ^ (b1+sum) ^ ((b1 >> 5)+b); 
-+              b1 += ((b0 << 4)+c) ^ (b0+sum) ^ ((b0 >> 5)+d); 
-+      } while(--n);
-+
-+      buf[0] += b0;
-+      buf[1] += b1;
-+}
-+
-+/* F, G and H are basic MD4 functions: selection, majority, parity */
-+#define F(x, y, z) ((z) ^ ((x) & ((y) ^ (z))))
-+#define G(x, y, z) (((x) & (y)) + (((x) ^ (y)) & (z)))
-+#define H(x, y, z) ((x) ^ (y) ^ (z))
-+
-+/*
-+ * The generic round function.  The application is so specific that
-+ * we don't bother protecting all the arguments with parens, as is generally
-+ * good macro practice, in favor of extra legibility.
-+ * Rotation is separate from addition to prevent recomputation
-+ */
-+#define ROUND(f, a, b, c, d, x, s)    \
-+      (a += f(b, c, d) + x, a = (a << s) | (a >> (32-s)))
-+#define K1 0
-+#define K2 013240474631UL
-+#define K3 015666365641UL
-+
-+/*
-+ * Basic cut-down MD4 transform.  Returns only 32 bits of result.
-+ */
-+static void halfMD4Transform (__u32 buf[4], __u32 const in[])
-+{
-+      __u32   a = buf[0], b = buf[1], c = buf[2], d = buf[3];
-+
-+      /* Round 1 */
-+      ROUND(F, a, b, c, d, in[0] + K1,  3);
-+      ROUND(F, d, a, b, c, in[1] + K1,  7);
-+      ROUND(F, c, d, a, b, in[2] + K1, 11);
-+      ROUND(F, b, c, d, a, in[3] + K1, 19);
-+      ROUND(F, a, b, c, d, in[4] + K1,  3);
-+      ROUND(F, d, a, b, c, in[5] + K1,  7);
-+      ROUND(F, c, d, a, b, in[6] + K1, 11);
-+      ROUND(F, b, c, d, a, in[7] + K1, 19);
-+
-+      /* Round 2 */
-+      ROUND(G, a, b, c, d, in[1] + K2,  3);
-+      ROUND(G, d, a, b, c, in[3] + K2,  5);
-+      ROUND(G, c, d, a, b, in[5] + K2,  9);
-+      ROUND(G, b, c, d, a, in[7] + K2, 13);
-+      ROUND(G, a, b, c, d, in[0] + K2,  3);
-+      ROUND(G, d, a, b, c, in[2] + K2,  5);
-+      ROUND(G, c, d, a, b, in[4] + K2,  9);
-+      ROUND(G, b, c, d, a, in[6] + K2, 13);
-+
-+      /* Round 3 */
-+      ROUND(H, a, b, c, d, in[3] + K3,  3);
-+      ROUND(H, d, a, b, c, in[7] + K3,  9);
-+      ROUND(H, c, d, a, b, in[2] + K3, 11);
-+      ROUND(H, b, c, d, a, in[6] + K3, 15);
-+      ROUND(H, a, b, c, d, in[1] + K3,  3);
-+      ROUND(H, d, a, b, c, in[5] + K3,  9);
-+      ROUND(H, c, d, a, b, in[0] + K3, 11);
-+      ROUND(H, b, c, d, a, in[4] + K3, 15);
-+
-+      buf[0] += a;
-+      buf[1] += b;
-+      buf[2] += c;
-+      buf[3] += d;
-+}
-+
-+#undef ROUND
-+#undef F
-+#undef G
-+#undef H
-+#undef K1
-+#undef K2
-+#undef K3
-+
-+/* The old legacy hash */
-+static __u32 dx_hack_hash (const char *name, int len)
-+{
-+      __u32 hash0 = 0x12a3fe2d, hash1 = 0x37abe8f9;
-+      while (len--) {
-+              __u32 hash = hash1 + (hash0 ^ (*name++ * 7152373));
-+              
-+              if (hash & 0x80000000) hash -= 0x7fffffff;
-+              hash1 = hash0;
-+              hash0 = hash;
-+      }
-+      return (hash0 << 1);
-+}
-+
-+static void str2hashbuf(const char *msg, int len, __u32 *buf, int num)
-+{
-+      __u32   pad, val;
-+      int     i;
-+
-+      pad = (__u32)len | ((__u32)len << 8);
-+      pad |= pad << 16;
-+
-+      val = pad;
-+      if (len > num*4)
-+              len = num * 4;
-+      for (i=0; i < len; i++) {
-+              if ((i % 4) == 0)
-+                      val = pad;
-+              val = msg[i] + (val << 8);
-+              if ((i % 4) == 3) {
-+                      *buf++ = val;
-+                      val = pad;
-+                      num--;
-+              }
-+      }
-+      if (--num >= 0)
-+              *buf++ = val;
-+      while (--num >= 0)
-+              *buf++ = pad;
-+}
-+
-+/*
-+ * Returns the hash of a filename.  If len is 0 and name is NULL, then
-+ * this function can be used to test whether or not a hash version is
-+ * supported.
-+ * 
-+ * The seed is an 4 longword (32 bits) "secret" which can be used to
-+ * uniquify a hash.  If the seed is all zero's, then some default seed
-+ * may be used.
-+ * 
-+ * A particular hash version specifies whether or not the seed is
-+ * represented, and whether or not the returned hash is 32 bits or 64
-+ * bits.  32 bit hashes will return 0 for the minor hash.
-+ */
-+int ext3fs_dirhash(const char *name, int len, struct dx_hash_info *hinfo)
-+{
-+      __u32   hash;
-+      __u32   minor_hash = 0;
-+      const char      *p;
-+      int             i;
-+      __u32           in[8], buf[4];
-+
-+      /* Initialize the default seed for the hash checksum functions */
-+      buf[0] = 0x67452301;
-+      buf[1] = 0xefcdab89;
-+      buf[2] = 0x98badcfe;
-+      buf[3] = 0x10325476;
-+
-+      /* Check to see if the seed is all zero's */
-+      if (hinfo->seed) {
-+              for (i=0; i < 4; i++) {
-+                      if (hinfo->seed[i])
-+                              break;
-+              }
-+              if (i < 4)
-+                      memcpy(buf, hinfo->seed, sizeof(buf));
-+      }
-+              
-+      switch (hinfo->hash_version) {
-+      case DX_HASH_LEGACY:
-+              hash = dx_hack_hash(name, len);
-+              break;
-+      case DX_HASH_HALF_MD4:
-+              p = name;
-+              while (len > 0) {
-+                      str2hashbuf(p, len, in, 8);
-+                      halfMD4Transform(buf, in);
-+                      len -= 32;
-+                      p += 32;
-+              }
-+              minor_hash = buf[2];
-+              hash = buf[1];
-+              break;
-+      case DX_HASH_TEA:
-+              p = name;
-+              while (len > 0) {
-+                      str2hashbuf(p, len, in, 4);
-+                      TEA_transform(buf, in);
-+                      len -= 16;
-+                      p += 16;
-+              }
-+              hash = buf[0];
-+              minor_hash = buf[1];
-+              break;
-+      default:
-+              hinfo->hash = 0;
-+              return -1;
-+      }
-+      hinfo->hash = hash & ~1;
-+      hinfo->minor_hash = minor_hash;
-+      return 0;
-+}
-Index: linux-2.4.21-suse/fs/ext3/Makefile
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/Makefile    2003-10-29 22:39:14.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/Makefile 2003-10-29 23:17:20.000000000 +0300
-@@ -12,7 +12,7 @@
- export-objs :=        super.o inode.o
- obj-y    := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o \
--              ioctl.o namei.o super.o symlink.o
-+              ioctl.o namei.o super.o symlink.o hash.o
- obj-m    := $(O_TARGET)
- include $(TOPDIR)/Rules.make
-Index: linux-2.4.21-suse/fs/ext3/namei.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/namei.c     2003-06-13 18:51:37.000000000 +0400
-+++ linux-2.4.21-suse/fs/ext3/namei.c  2003-10-29 23:25:23.000000000 +0300
-@@ -16,6 +16,12 @@
-  *        David S. Miller (davem@caip.rutgers.edu), 1995
-  *  Directory entry file type support and forward compatibility hooks
-  *    for B-tree directories by Theodore Ts'o (tytso@mit.edu), 1998
-+ *  Hash Tree Directory indexing (c)
-+ *    Daniel Phillips, 2001
-+ *  Hash Tree Directory indexing porting
-+ *    Christopher Li, 2002
-+ *  Hash Tree Directory indexing cleanup
-+ *    Theodore Ts'o, 2002
-  */
- #include <linux/fs.h>
-@@ -38,6 +44,642 @@
- #define NAMEI_RA_SIZE        (NAMEI_RA_CHUNKS * NAMEI_RA_BLOCKS)
- #define NAMEI_RA_INDEX(c,b)  (((c) * NAMEI_RA_BLOCKS) + (b))
-+static struct buffer_head *ext3_append(handle_t *handle,
-+                                      struct inode *inode,
-+                                      u32 *block, int *err)
-+{
-+      struct buffer_head *bh;
-+
-+      *block = inode->i_size >> inode->i_sb->s_blocksize_bits;
-+
-+      if ((bh = ext3_bread(handle, inode, *block, 1, err))) {
-+              inode->i_size += inode->i_sb->s_blocksize;
-+              EXT3_I(inode)->i_disksize = inode->i_size;
-+              ext3_journal_get_write_access(handle,bh);
-+      }
-+      return bh;
-+}
-+
-+#ifndef assert
-+#define assert(test) J_ASSERT(test)
-+#endif
-+
-+#ifndef swap
-+#define swap(x, y) do { typeof(x) z = x; x = y; y = z; } while (0)
-+#endif
-+
-+typedef struct { u32 v; } le_u32;
-+typedef struct { u16 v; } le_u16;
-+
-+#ifdef DX_DEBUG
-+#define dxtrace(command) command
-+#else
-+#define dxtrace(command) 
-+#endif
-+
-+struct fake_dirent
-+{
-+      /*le*/u32 inode;
-+      /*le*/u16 rec_len;
-+      u8 name_len;
-+      u8 file_type;
-+};
-+
-+struct dx_countlimit
-+{
-+      le_u16 limit;
-+      le_u16 count;
-+};
-+
-+struct dx_entry
-+{
-+      le_u32 hash;
-+      le_u32 block;
-+};
-+
-+/*
-+ * dx_root_info is laid out so that if it should somehow get overlaid by a
-+ * dirent the two low bits of the hash version will be zero.  Therefore, the
-+ * hash version mod 4 should never be 0.  Sincerely, the paranoia department.
-+ */
-+
-+struct dx_root
-+{
-+      struct fake_dirent dot;
-+      char dot_name[4];
-+      struct fake_dirent dotdot;
-+      char dotdot_name[4];
-+      struct dx_root_info
-+      {
-+              le_u32 reserved_zero;
-+              u8 hash_version;
-+              u8 info_length; /* 8 */
-+              u8 indirect_levels;
-+              u8 unused_flags;
-+      }
-+      info;
-+      struct dx_entry entries[0];
-+};
-+
-+struct dx_node
-+{
-+      struct fake_dirent fake;
-+      struct dx_entry entries[0];
-+};
-+
-+
-+struct dx_frame
-+{
-+      struct buffer_head *bh;
-+      struct dx_entry *entries;
-+      struct dx_entry *at;
-+};
-+
-+struct dx_map_entry
-+{
-+      u32 hash;
-+      u32 offs;
-+};
-+
-+#ifdef CONFIG_EXT3_INDEX
-+static inline unsigned dx_get_block (struct dx_entry *entry);
-+static void dx_set_block (struct dx_entry *entry, unsigned value);
-+static inline unsigned dx_get_hash (struct dx_entry *entry);
-+static void dx_set_hash (struct dx_entry *entry, unsigned value);
-+static unsigned dx_get_count (struct dx_entry *entries);
-+static unsigned dx_get_limit (struct dx_entry *entries);
-+static void dx_set_count (struct dx_entry *entries, unsigned value);
-+static void dx_set_limit (struct dx_entry *entries, unsigned value);
-+static unsigned dx_root_limit (struct inode *dir, unsigned infosize);
-+static unsigned dx_node_limit (struct inode *dir);
-+static struct dx_frame *dx_probe(struct dentry *dentry,
-+                               struct inode *dir,
-+                               struct dx_hash_info *hinfo,
-+                               struct dx_frame *frame,
-+                               int *err);
-+static void dx_release (struct dx_frame *frames);
-+static int dx_make_map (struct ext3_dir_entry_2 *de, int size,
-+                      struct dx_hash_info *hinfo, struct dx_map_entry map[]);
-+static void dx_sort_map(struct dx_map_entry *map, unsigned count);
-+static struct ext3_dir_entry_2 *dx_move_dirents (char *from, char *to,
-+              struct dx_map_entry *offsets, int count);
-+static struct ext3_dir_entry_2* dx_pack_dirents (char *base, int size);
-+static void dx_insert_block (struct dx_frame *frame, u32 hash, u32 block);
-+static int ext3_htree_next_block(struct inode *dir, __u32 hash,
-+                               struct dx_frame *frame,
-+                               struct dx_frame *frames, int *err,
-+                               __u32 *start_hash);
-+static struct buffer_head * ext3_dx_find_entry(struct dentry *dentry,
-+                     struct ext3_dir_entry_2 **res_dir, int *err);
-+static int ext3_dx_add_entry(handle_t *handle, struct dentry *dentry,
-+                           struct inode *inode);
-+
-+/*
-+ * Future: use high four bits of block for coalesce-on-delete flags
-+ * Mask them off for now.
-+ */
-+
-+static inline unsigned dx_get_block (struct dx_entry *entry)
-+{
-+      return le32_to_cpu(entry->block.v) & 0x00ffffff;
-+}
-+
-+static inline void dx_set_block (struct dx_entry *entry, unsigned value)
-+{
-+      entry->block.v = cpu_to_le32(value);
-+}
-+
-+static inline unsigned dx_get_hash (struct dx_entry *entry)
-+{
-+      return le32_to_cpu(entry->hash.v);
-+}
-+
-+static inline void dx_set_hash (struct dx_entry *entry, unsigned value)
-+{
-+      entry->hash.v = cpu_to_le32(value);
-+}
-+
-+static inline unsigned dx_get_count (struct dx_entry *entries)
-+{
-+      return le16_to_cpu(((struct dx_countlimit *) entries)->count.v);
-+}
-+
-+static inline unsigned dx_get_limit (struct dx_entry *entries)
-+{
-+      return le16_to_cpu(((struct dx_countlimit *) entries)->limit.v);
-+}
-+
-+static inline void dx_set_count (struct dx_entry *entries, unsigned value)
-+{
-+      ((struct dx_countlimit *) entries)->count.v = cpu_to_le16(value);
-+}
-+
-+static inline void dx_set_limit (struct dx_entry *entries, unsigned value)
-+{
-+      ((struct dx_countlimit *) entries)->limit.v = cpu_to_le16(value);
-+}
-+
-+static inline unsigned dx_root_limit (struct inode *dir, unsigned infosize)
-+{
-+      unsigned entry_space = dir->i_sb->s_blocksize - EXT3_DIR_REC_LEN(1) -
-+              EXT3_DIR_REC_LEN(2) - infosize;
-+      return 0? 20: entry_space / sizeof(struct dx_entry);
-+}
-+
-+static inline unsigned dx_node_limit (struct inode *dir)
-+{
-+      unsigned entry_space = dir->i_sb->s_blocksize - EXT3_DIR_REC_LEN(0);
-+      return 0? 22: entry_space / sizeof(struct dx_entry);
-+}
-+
-+/*
-+ * Debug
-+ */
-+#ifdef DX_DEBUG
-+struct stats
-+{ 
-+      unsigned names;
-+      unsigned space;
-+      unsigned bcount;
-+};
-+
-+static struct stats dx_show_leaf(struct dx_hash_info *hinfo, struct ext3_dir_entry_2 *de,
-+                               int size, int show_names)
-+{
-+      unsigned names = 0, space = 0;
-+      char *base = (char *) de;
-+      struct dx_hash_info h = *hinfo;
-+      
-+      printk("names: ");
-+      while ((char *) de < base + size)
-+      {
-+              if (de->inode)
-+              {
-+                      if (show_names)
-+                      {
-+                              int len = de->name_len;
-+                              char *name = de->name;
-+                              while (len--) printk("%c", *name++);
-+                              ext3fs_dirhash(de->name, de->name_len, &h);
-+                              printk(":%x.%u ", h.hash,
-+                                     ((char *) de - base));
-+                      }
-+                      space += EXT3_DIR_REC_LEN(de->name_len);
-+                      names++;
-+              }
-+              de = (struct ext3_dir_entry_2 *) ((char *) de + le16_to_cpu(de->rec_len));
-+      }
-+      printk("(%i)\n", names);
-+      return (struct stats) { names, space, 1 };
-+}
-+
-+struct stats dx_show_entries(struct dx_hash_info *hinfo, struct inode *dir,
-+                           struct dx_entry *entries, int levels)
-+{
-+      unsigned blocksize = dir->i_sb->s_blocksize;
-+      unsigned count = dx_get_count (entries), names = 0, space = 0, i;
-+      unsigned bcount = 0;
-+      struct buffer_head *bh;
-+      int err;
-+      printk("%i indexed blocks...\n", count);
-+      for (i = 0; i < count; i++, entries++)
-+      {
-+              u32 block = dx_get_block(entries), hash = i? dx_get_hash(entries): 0;
-+              u32 range = i < count - 1? (dx_get_hash(entries + 1) - hash): ~hash;
-+              struct stats stats;
-+              printk("%s%3u:%03u hash %8x/%8x ",levels?"":"   ", i, block, hash, range);
-+              if (!(bh = ext3_bread (NULL,dir, block, 0,&err))) continue;
-+              stats = levels?
-+                 dx_show_entries(hinfo, dir, ((struct dx_node *) bh->b_data)->entries, levels - 1):
-+                 dx_show_leaf(hinfo, (struct ext3_dir_entry_2 *) bh->b_data, blocksize, 0);
-+              names += stats.names;
-+              space += stats.space;
-+              bcount += stats.bcount;
-+              brelse (bh);
-+      }
-+      if (bcount)
-+              printk("%snames %u, fullness %u (%u%%)\n", levels?"":"   ",
-+                      names, space/bcount,(space/bcount)*100/blocksize);
-+      return (struct stats) { names, space, bcount};
-+}
-+#endif /* DX_DEBUG */
-+
-+/*
-+ * Probe for a directory leaf block to search.
-+ *
-+ * dx_probe can return ERR_BAD_DX_DIR, which means there was a format
-+ * error in the directory index, and the caller should fall back to
-+ * searching the directory normally.  The callers of dx_probe **MUST**
-+ * check for this error code, and make sure it never gets reflected
-+ * back to userspace.
-+ */
-+static struct dx_frame *
-+dx_probe(struct dentry *dentry, struct inode *dir,
-+       struct dx_hash_info *hinfo, struct dx_frame *frame_in, int *err)
-+{
-+      unsigned count, indirect;
-+      struct dx_entry *at, *entries, *p, *q, *m;
-+      struct dx_root *root;
-+      struct buffer_head *bh;
-+      struct dx_frame *frame = frame_in;
-+      u32 hash;
-+
-+      frame->bh = NULL;
-+      if (dentry)
-+              dir = dentry->d_parent->d_inode;
-+      if (!(bh = ext3_bread (NULL,dir, 0, 0, err)))
-+              goto fail;
-+      root = (struct dx_root *) bh->b_data;
-+      if (root->info.hash_version != DX_HASH_TEA &&
-+          root->info.hash_version != DX_HASH_HALF_MD4 &&
-+          root->info.hash_version != DX_HASH_LEGACY) {
-+              ext3_warning(dir->i_sb, __FUNCTION__,
-+                           "Unrecognised inode hash code %d",
-+                           root->info.hash_version);
-+              brelse(bh);
-+              *err = ERR_BAD_DX_DIR;
-+              goto fail;
-+      }
-+      hinfo->hash_version = root->info.hash_version;
-+      hinfo->seed = dir->i_sb->u.ext3_sb.s_hash_seed;
-+      if (dentry)
-+              ext3fs_dirhash(dentry->d_name.name, dentry->d_name.len, hinfo);
-+      hash = hinfo->hash;
-+
-+      if (root->info.unused_flags & 1) {
-+              ext3_warning(dir->i_sb, __FUNCTION__,
-+                           "Unimplemented inode hash flags: %#06x",
-+                           root->info.unused_flags);
-+              brelse(bh);
-+              *err = ERR_BAD_DX_DIR;
-+              goto fail;
-+      }
-+
-+      if ((indirect = root->info.indirect_levels) > 1) {
-+              ext3_warning(dir->i_sb, __FUNCTION__,
-+                           "Unimplemented inode hash depth: %#06x",
-+                           root->info.indirect_levels);
-+              brelse(bh);
-+              *err = ERR_BAD_DX_DIR;
-+              goto fail;
-+      }
-+
-+      entries = (struct dx_entry *) (((char *)&root->info) +
-+                                     root->info.info_length);
-+      assert(dx_get_limit(entries) == dx_root_limit(dir,
-+                                                    root->info.info_length));
-+      dxtrace (printk("Look up %x", hash));
-+      while (1)
-+      {
-+              count = dx_get_count(entries);
-+              assert (count && count <= dx_get_limit(entries));
-+              p = entries + 1;
-+              q = entries + count - 1;
-+              while (p <= q)
-+              {
-+                      m = p + (q - p)/2;
-+                      dxtrace(printk("."));
-+                      if (dx_get_hash(m) > hash)
-+                              q = m - 1;
-+                      else
-+                              p = m + 1;
-+              }
-+
-+              if (0) // linear search cross check
-+              {
-+                      unsigned n = count - 1;
-+                      at = entries;
-+                      while (n--)
-+                      {
-+                              dxtrace(printk(","));
-+                              if (dx_get_hash(++at) > hash)
-+                              {
-+                                      at--;
-+                                      break;
-+                              }
-+                      }
-+                      assert (at == p - 1);
-+              }
-+
-+              at = p - 1;
-+              dxtrace(printk(" %x->%u\n", at == entries? 0: dx_get_hash(at), dx_get_block(at)));
-+              frame->bh = bh;
-+              frame->entries = entries;
-+              frame->at = at;
-+              if (!indirect--) return frame;
-+              if (!(bh = ext3_bread (NULL,dir, dx_get_block(at), 0, err)))
-+                      goto fail2;
-+              at = entries = ((struct dx_node *) bh->b_data)->entries;
-+              assert (dx_get_limit(entries) == dx_node_limit (dir));
-+              frame++;
-+      }
-+fail2:
-+      while (frame >= frame_in) {
-+              brelse(frame->bh);
-+              frame--;
-+      }
-+fail:
-+      return NULL;
-+}
-+
-+static void dx_release (struct dx_frame *frames)
-+{
-+      if (frames[0].bh == NULL)
-+              return;
-+
-+      if (((struct dx_root *) frames[0].bh->b_data)->info.indirect_levels)
-+              brelse(frames[1].bh);
-+      brelse(frames[0].bh);
-+}
-+
-+/*
-+ * This function increments the frame pointer to search the next leaf
-+ * block, and reads in the necessary intervening nodes if the search
-+ * should be necessary.  Whether or not the search is necessary is
-+ * controlled by the hash parameter.  If the hash value is even, then
-+ * the search is only continued if the next block starts with that
-+ * hash value.  This is used if we are searching for a specific file.
-+ *
-+ * If the hash value is HASH_NB_ALWAYS, then always go to the next block.
-+ *
-+ * This function returns 1 if the caller should continue to search,
-+ * or 0 if it should not.  If there is an error reading one of the
-+ * index blocks, it will return -1.
-+ *
-+ * If start_hash is non-null, it will be filled in with the starting
-+ * hash of the next page.
-+ */
-+static int ext3_htree_next_block(struct inode *dir, __u32 hash,
-+                               struct dx_frame *frame,
-+                               struct dx_frame *frames, int *err,
-+                               __u32 *start_hash)
-+{
-+      struct dx_frame *p;
-+      struct buffer_head *bh;
-+      int num_frames = 0;
-+      __u32 bhash;
-+
-+      *err = ENOENT;
-+      p = frame;
-+      /*
-+       * Find the next leaf page by incrementing the frame pointer.
-+       * If we run out of entries in the interior node, loop around and
-+       * increment pointer in the parent node.  When we break out of
-+       * this loop, num_frames indicates the number of interior
-+       * nodes need to be read.
-+       */
-+      while (1) {
-+              if (++(p->at) < p->entries + dx_get_count(p->entries))
-+                      break;
-+              if (p == frames)
-+                      return 0;
-+              num_frames++;
-+              p--;
-+      }
-+
-+      /*
-+       * If the hash is 1, then continue only if the next page has a
-+       * continuation hash of any value.  This is used for readdir
-+       * handling.  Otherwise, check to see if the hash matches the
-+       * desired contiuation hash.  If it doesn't, return since
-+       * there's no point to read in the successive index pages.
-+       */
-+      bhash = dx_get_hash(p->at);
-+      if (start_hash)
-+              *start_hash = bhash;
-+      if ((hash & 1) == 0) {
-+              if ((bhash & ~1) != hash)
-+                      return 0;
-+      }
-+      /*
-+       * If the hash is HASH_NB_ALWAYS, we always go to the next
-+       * block so no check is necessary
-+       */
-+      while (num_frames--) {
-+              if (!(bh = ext3_bread(NULL, dir, dx_get_block(p->at),
-+                                    0, err)))
-+                      return -1; /* Failure */
-+              p++;
-+              brelse (p->bh);
-+              p->bh = bh;
-+              p->at = p->entries = ((struct dx_node *) bh->b_data)->entries;
-+      }
-+      return 1;
-+}
-+
-+
-+/*
-+ * p is at least 6 bytes before the end of page
-+ */
-+static inline struct ext3_dir_entry_2 *ext3_next_entry(struct ext3_dir_entry_2 *p)
-+{
-+      return (struct ext3_dir_entry_2 *)((char*)p + le16_to_cpu(p->rec_len));
-+}
-+
-+/*
-+ * This function fills a red-black tree with information from a
-+ * directory.  We start scanning the directory in hash order, starting
-+ * at start_hash and start_minor_hash.
-+ *
-+ * This function returns the number of entries inserted into the tree,
-+ * or a negative error code.
-+ */
-+int ext3_htree_fill_tree(struct file *dir_file, __u32 start_hash,
-+                       __u32 start_minor_hash, __u32 *next_hash)
-+{
-+      struct dx_hash_info hinfo;
-+      struct buffer_head *bh;
-+      struct ext3_dir_entry_2 *de, *top;
-+      static struct dx_frame frames[2], *frame;
-+      struct inode *dir;
-+      int block, err;
-+      int count = 0;
-+      int ret;
-+      __u32 hashval;
-+      
-+      dxtrace(printk("In htree_fill_tree, start hash: %x:%x\n", start_hash,
-+                     start_minor_hash));
-+      dir = dir_file->f_dentry->d_inode;
-+      hinfo.hash = start_hash;
-+      hinfo.minor_hash = 0;
-+      frame = dx_probe(0, dir_file->f_dentry->d_inode, &hinfo, frames, &err);
-+      if (!frame)
-+              return err;
-+
-+      /* Add '.' and '..' from the htree header */
-+      if (!start_hash && !start_minor_hash) {
-+              de = (struct ext3_dir_entry_2 *) frames[0].bh->b_data;
-+              if ((err = ext3_htree_store_dirent(dir_file, 0, 0, de)) != 0)
-+                      goto errout;
-+              de = ext3_next_entry(de);
-+              if ((err = ext3_htree_store_dirent(dir_file, 0, 0, de)) != 0)
-+                      goto errout;
-+              count += 2;
-+      }
-+
-+      while (1) {
-+              block = dx_get_block(frame->at);
-+              dxtrace(printk("Reading block %d\n", block));
-+              if (!(bh = ext3_bread (NULL, dir, block, 0, &err)))
-+                      goto errout;
-+      
-+              de = (struct ext3_dir_entry_2 *) bh->b_data;
-+              top = (struct ext3_dir_entry_2 *) ((char *) de + dir->i_sb->s_blocksize -
-+                                     EXT3_DIR_REC_LEN(0));
-+              for (; de < top; de = ext3_next_entry(de)) {
-+                      ext3fs_dirhash(de->name, de->name_len, &hinfo);
-+                      if ((hinfo.hash < start_hash) ||
-+                          ((hinfo.hash == start_hash) &&
-+                           (hinfo.minor_hash < start_minor_hash)))
-+                              continue;
-+                      if ((err = ext3_htree_store_dirent(dir_file,
-+                                 hinfo.hash, hinfo.minor_hash, de)) != 0)
-+                              goto errout;
-+                      count++;
-+              }
-+              brelse (bh);
-+              hashval = ~1;
-+              ret = ext3_htree_next_block(dir, HASH_NB_ALWAYS, 
-+                                          frame, frames, &err, &hashval);
-+              if (next_hash)
-+                      *next_hash = hashval;
-+              if (ret == -1)
-+                      goto errout;
-+              /*
-+               * Stop if:  (a) there are no more entries, or
-+               * (b) we have inserted at least one entry and the
-+               * next hash value is not a continuation
-+               */
-+              if ((ret == 0) ||
-+                  (count && ((hashval & 1) == 0)))
-+                      break;
-+      }
-+      dx_release(frames);
-+      dxtrace(printk("Fill tree: returned %d entries\n", count));
-+      return count;
-+errout:
-+      dx_release(frames);
-+      return (err);
-+}
-+
-+
-+/*
-+ * Directory block splitting, compacting
-+ */
-+
-+static int dx_make_map (struct ext3_dir_entry_2 *de, int size,
-+                      struct dx_hash_info *hinfo, struct dx_map_entry *map_tail)
-+{
-+      int count = 0;
-+      char *base = (char *) de;
-+      struct dx_hash_info h = *hinfo;
-+      
-+      while ((char *) de < base + size)
-+      {
-+              if (de->name_len && de->inode) {
-+                      ext3fs_dirhash(de->name, de->name_len, &h);
-+                      map_tail--;
-+                      map_tail->hash = h.hash;
-+                      map_tail->offs = (u32) ((char *) de - base);
-+                      count++;
-+              }
-+              /* XXX: do we need to check rec_len == 0 case? -Chris */
-+              de = (struct ext3_dir_entry_2 *) ((char *) de + le16_to_cpu(de->rec_len));
-+      }
-+      return count;
-+}
-+
-+static void dx_sort_map (struct dx_map_entry *map, unsigned count)
-+{
-+        struct dx_map_entry *p, *q, *top = map + count - 1;
-+        int more;
-+        /* Combsort until bubble sort doesn't suck */
-+        while (count > 2)
-+      {
-+                count = count*10/13;
-+                if (count - 9 < 2) /* 9, 10 -> 11 */
-+                        count = 11;
-+                for (p = top, q = p - count; q >= map; p--, q--)
-+                        if (p->hash < q->hash)
-+                                swap(*p, *q);
-+        }
-+        /* Garden variety bubble sort */
-+        do {
-+                more = 0;
-+                q = top;
-+                while (q-- > map)
-+              {
-+                        if (q[1].hash >= q[0].hash)
-+                              continue;
-+                        swap(*(q+1), *q);
-+                        more = 1;
-+              }
-+      } while(more);
-+}
-+
-+static void dx_insert_block(struct dx_frame *frame, u32 hash, u32 block)
-+{
-+      struct dx_entry *entries = frame->entries;
-+      struct dx_entry *old = frame->at, *new = old + 1;
-+      int count = dx_get_count(entries);
-+
-+      assert(count < dx_get_limit(entries));
-+      assert(old < entries + count);
-+      memmove(new + 1, new, (char *)(entries + count) - (char *)(new));
-+      dx_set_hash(new, hash);
-+      dx_set_block(new, block);
-+      dx_set_count(entries, count + 1);
-+}
-+#endif
-+
-+
-+static void ext3_update_dx_flag(struct inode *inode)
-+{
-+      if (!EXT3_HAS_COMPAT_FEATURE(inode->i_sb,
-+                                   EXT3_FEATURE_COMPAT_DIR_INDEX))
-+              EXT3_I(inode)->i_flags &= ~EXT3_INDEX_FL;
-+}
-+
- /*
-  * NOTE! unlike strncmp, ext3_match returns 1 for success, 0 for failure.
-  *
-@@ -94,6 +736,7 @@
-       return 0;
- }
-+
- /*
-  *    ext3_find_entry()
-  *
-@@ -105,6 +748,8 @@
-  * The returned buffer_head has ->b_count elevated.  The caller is expected
-  * to brelse() it when appropriate.
-  */
-+
-+      
- static struct buffer_head * ext3_find_entry (struct dentry *dentry,
-                                       struct ext3_dir_entry_2 ** res_dir)
- {
-@@ -119,12 +764,32 @@
-       int num = 0;
-       int nblocks, i, err;
-       struct inode *dir = dentry->d_parent->d_inode;
-+      int namelen;
-+      const u8 *name;
-+      unsigned blocksize;
-       *res_dir = NULL;
-       sb = dir->i_sb;
--
-+      blocksize = sb->s_blocksize;
-+      namelen = dentry->d_name.len;
-+      name = dentry->d_name.name;
-+      if (namelen > EXT3_NAME_LEN)
-+              return NULL;
-+#ifdef CONFIG_EXT3_INDEX
-+      if (is_dx(dir)) {
-+              bh = ext3_dx_find_entry(dentry, res_dir, &err);
-+              /*
-+               * On success, or if the error was file not found,
-+               * return.  Otherwise, fall back to doing a search the
-+               * old fashioned way.
-+               */
-+              if (bh || (err != ERR_BAD_DX_DIR))
-+                      return bh;
-+              dxtrace(printk("ext3_find_entry: dx failed, falling back\n"));
-+      }
-+#endif
-       nblocks = dir->i_size >> EXT3_BLOCK_SIZE_BITS(sb);
--      start = dir->u.ext3_i.i_dir_start_lookup;
-+      start = EXT3_I(dir)->i_dir_start_lookup;
-       if (start >= nblocks)
-               start = 0;
-       block = start;
-@@ -165,7 +830,7 @@
-               i = search_dirblock(bh, dir, dentry,
-                           block << EXT3_BLOCK_SIZE_BITS(sb), res_dir);
-               if (i == 1) {
--                      dir->u.ext3_i.i_dir_start_lookup = block;
-+                      EXT3_I(dir)->i_dir_start_lookup = block;
-                       ret = bh;
-                       goto cleanup_and_exit;
-               } else {
-@@ -196,6 +861,66 @@
-       return ret;
- }
-+#ifdef CONFIG_EXT3_INDEX
-+static struct buffer_head * ext3_dx_find_entry(struct dentry *dentry,
-+                     struct ext3_dir_entry_2 **res_dir, int *err)
-+{
-+      struct super_block * sb;
-+      struct dx_hash_info     hinfo;
-+      u32 hash;
-+      struct dx_frame frames[2], *frame;
-+      struct ext3_dir_entry_2 *de, *top;
-+      struct buffer_head *bh;
-+      unsigned long block;
-+      int retval;
-+      int namelen = dentry->d_name.len;
-+      const u8 *name = dentry->d_name.name;
-+      struct inode *dir = dentry->d_parent->d_inode;
-+      
-+      sb = dir->i_sb;
-+      if (!(frame = dx_probe (dentry, 0, &hinfo, frames, err)))
-+              return NULL;
-+      hash = hinfo.hash;
-+      do {
-+              block = dx_get_block(frame->at);
-+              if (!(bh = ext3_bread (NULL,dir, block, 0, err)))
-+                      goto errout;
-+              de = (struct ext3_dir_entry_2 *) bh->b_data;
-+              top = (struct ext3_dir_entry_2 *) ((char *) de + sb->s_blocksize -
-+                                     EXT3_DIR_REC_LEN(0));
-+              for (; de < top; de = ext3_next_entry(de))
-+              if (ext3_match (namelen, name, de)) {
-+                      if (!ext3_check_dir_entry("ext3_find_entry",
-+                                                dir, de, bh,
-+                                (block<<EXT3_BLOCK_SIZE_BITS(sb))
-+                                        +((char *)de - bh->b_data))) {
-+                              brelse (bh);
-+                              goto errout;
-+                      }
-+                      *res_dir = de;
-+                      dx_release (frames);
-+                      return bh;
-+              }
-+              brelse (bh);
-+              /* Check to see if we should continue to search */
-+              retval = ext3_htree_next_block(dir, hash, frame,
-+                                             frames, err, 0);
-+              if (retval == -1) {
-+                      ext3_warning(sb, __FUNCTION__,
-+                           "error reading index page in directory #%lu",
-+                           dir->i_ino);
-+                      goto errout;
-+              }
-+      } while (retval == 1);
-+      
-+      *err = -ENOENT;
-+errout:
-+      dxtrace(printk("%s not found\n", name));
-+      dx_release (frames);
-+      return NULL;
-+}
-+#endif
-+
- static struct dentry *ext3_lookup(struct inode * dir, struct dentry *dentry)
- {
-       struct inode * inode;
-@@ -212,8 +937,9 @@
-               brelse (bh);
-               inode = iget(dir->i_sb, ino);
--              if (!inode)
-+              if (!inode) {
-                       return ERR_PTR(-EACCES);
-+              }
-       }
-       d_add(dentry, inode);
-       return NULL;
-@@ -237,6 +963,301 @@
-               de->file_type = ext3_type_by_mode[(mode & S_IFMT)>>S_SHIFT];
- }
-+#ifdef CONFIG_EXT3_INDEX
-+static struct ext3_dir_entry_2 *
-+dx_move_dirents(char *from, char *to, struct dx_map_entry *map, int count)
-+{
-+      unsigned rec_len = 0;
-+
-+      while (count--) {
-+              struct ext3_dir_entry_2 *de = (struct ext3_dir_entry_2 *) (from + map->offs);
-+              rec_len = EXT3_DIR_REC_LEN(de->name_len);
-+              memcpy (to, de, rec_len);
-+              ((struct ext3_dir_entry_2 *)to)->rec_len = cpu_to_le16(rec_len);
-+              de->inode = 0;
-+              map++;
-+              to += rec_len;
-+      }
-+      return (struct ext3_dir_entry_2 *) (to - rec_len);
-+}
-+
-+static struct ext3_dir_entry_2* dx_pack_dirents(char *base, int size)
-+{
-+      struct ext3_dir_entry_2 *next, *to, *prev, *de = (struct ext3_dir_entry_2 *) base;
-+      unsigned rec_len = 0;
-+
-+      prev = to = de;
-+      while ((char*)de < base + size) {
-+              next = (struct ext3_dir_entry_2 *) ((char *) de +
-+                                                  le16_to_cpu(de->rec_len));
-+              if (de->inode && de->name_len) {
-+                      rec_len = EXT3_DIR_REC_LEN(de->name_len);
-+                      if (de > to)
-+                              memmove(to, de, rec_len);
-+                      to->rec_len = cpu_to_le16(rec_len);
-+                      prev = to;
-+                      to = (struct ext3_dir_entry_2 *)((char *)to + rec_len);
-+              }
-+              de = next;
-+      }
-+      return prev;
-+}
-+
-+static struct ext3_dir_entry_2 *do_split(handle_t *handle, struct inode *dir,
-+                      struct buffer_head **bh,struct dx_frame *frame,
-+                      struct dx_hash_info *hinfo, int *error)
-+{
-+      unsigned blocksize = dir->i_sb->s_blocksize;
-+      unsigned count, continued;
-+      struct buffer_head *bh2;
-+      u32 newblock;
-+      u32 hash2;
-+      struct dx_map_entry *map;
-+      char *data1 = (*bh)->b_data, *data2;
-+      unsigned split;
-+      struct ext3_dir_entry_2 *de = NULL, *de2;
-+      int     err;
-+
-+      bh2 = ext3_append (handle, dir, &newblock, error);
-+      if (!(bh2)) {
-+              brelse(*bh);
-+              *bh = NULL;
-+              goto errout;
-+      }
-+
-+      BUFFER_TRACE(*bh, "get_write_access");
-+      err = ext3_journal_get_write_access(handle, *bh);
-+      if (err) {
-+      journal_error:
-+              brelse(*bh);
-+              brelse(bh2);
-+              *bh = NULL;
-+              ext3_std_error(dir->i_sb, err);
-+              goto errout;
-+      }
-+      BUFFER_TRACE(frame->bh, "get_write_access");
-+      err = ext3_journal_get_write_access(handle, frame->bh);
-+      if (err)
-+              goto journal_error;
-+
-+      data2 = bh2->b_data;
-+
-+      /* create map in the end of data2 block */
-+      map = (struct dx_map_entry *) (data2 + blocksize);
-+      count = dx_make_map ((struct ext3_dir_entry_2 *) data1,
-+                           blocksize, hinfo, map);
-+      map -= count;
-+      split = count/2; // need to adjust to actual middle
-+      dx_sort_map (map, count);
-+      hash2 = map[split].hash;
-+      continued = hash2 == map[split - 1].hash;
-+      dxtrace(printk("Split block %i at %x, %i/%i\n",
-+              dx_get_block(frame->at), hash2, split, count-split));
-+
-+      /* Fancy dance to stay within two buffers */
-+      de2 = dx_move_dirents(data1, data2, map + split, count - split);
-+      de = dx_pack_dirents(data1,blocksize);
-+      de->rec_len = cpu_to_le16(data1 + blocksize - (char *) de);
-+      de2->rec_len = cpu_to_le16(data2 + blocksize - (char *) de2);
-+      dxtrace(dx_show_leaf (hinfo, (struct ext3_dir_entry_2 *) data1, blocksize, 1));
-+      dxtrace(dx_show_leaf (hinfo, (struct ext3_dir_entry_2 *) data2, blocksize, 1));
-+
-+      /* Which block gets the new entry? */
-+      if (hinfo->hash >= hash2)
-+      {
-+              swap(*bh, bh2);
-+              de = de2;
-+      }
-+      dx_insert_block (frame, hash2 + continued, newblock);
-+      err = ext3_journal_dirty_metadata (handle, bh2);
-+      if (err)
-+              goto journal_error;
-+      err = ext3_journal_dirty_metadata (handle, frame->bh);
-+      if (err)
-+              goto journal_error;
-+      brelse (bh2);
-+      dxtrace(dx_show_index ("frame", frame->entries));
-+errout:
-+      return de;
-+}
-+#endif
-+
-+
-+/*
-+ * Add a new entry into a directory (leaf) block.  If de is non-NULL,
-+ * it points to a directory entry which is guaranteed to be large
-+ * enough for new directory entry.  If de is NULL, then
-+ * add_dirent_to_buf will attempt search the directory block for
-+ * space.  It will return -ENOSPC if no space is available, and -EIO
-+ * and -EEXIST if directory entry already exists.
-+ * 
-+ * NOTE!  bh is NOT released in the case where ENOSPC is returned.  In
-+ * all other cases bh is released.
-+ */
-+static int add_dirent_to_buf(handle_t *handle, struct dentry *dentry,
-+                           struct inode *inode, struct ext3_dir_entry_2 *de,
-+                           struct buffer_head * bh)
-+{
-+      struct inode    *dir = dentry->d_parent->d_inode;
-+      const char      *name = dentry->d_name.name;
-+      int             namelen = dentry->d_name.len;
-+      unsigned long   offset = 0;
-+      unsigned short  reclen;
-+      int             nlen, rlen, err;
-+      char            *top;
-+      
-+      reclen = EXT3_DIR_REC_LEN(namelen);
-+      if (!de) {
-+              de = (struct ext3_dir_entry_2 *)bh->b_data;
-+              top = bh->b_data + dir->i_sb->s_blocksize - reclen;
-+              while ((char *) de <= top) {
-+                      if (!ext3_check_dir_entry("ext3_add_entry", dir, de,
-+                                                bh, offset)) {
-+                              brelse (bh);
-+                              return -EIO;
-+                      }
-+                      if (ext3_match (namelen, name, de)) {
-+                              brelse (bh);
-+                              return -EEXIST;
-+                      }
-+                      nlen = EXT3_DIR_REC_LEN(de->name_len);
-+                      rlen = le16_to_cpu(de->rec_len);
-+                      if ((de->inode? rlen - nlen: rlen) >= reclen)
-+                              break;
-+                      de = (struct ext3_dir_entry_2 *)((char *)de + rlen);
-+                      offset += rlen;
-+              }
-+              if ((char *) de > top)
-+                      return -ENOSPC;
-+      }
-+      BUFFER_TRACE(bh, "get_write_access");
-+      err = ext3_journal_get_write_access(handle, bh);
-+      if (err) {
-+              ext3_std_error(dir->i_sb, err);
-+              brelse(bh);
-+              return err;
-+      }
-+      
-+      /* By now the buffer is marked for journaling */
-+      nlen = EXT3_DIR_REC_LEN(de->name_len);
-+      rlen = le16_to_cpu(de->rec_len);
-+      if (de->inode) {
-+              struct ext3_dir_entry_2 *de1 = (struct ext3_dir_entry_2 *)((char *)de + nlen);
-+              de1->rec_len = cpu_to_le16(rlen - nlen);
-+              de->rec_len = cpu_to_le16(nlen);
-+              de = de1;
-+      }
-+      de->file_type = EXT3_FT_UNKNOWN;
-+      if (inode) {
-+              de->inode = cpu_to_le32(inode->i_ino);
-+              ext3_set_de_type(dir->i_sb, de, inode->i_mode);
-+      } else
-+              de->inode = 0;
-+      de->name_len = namelen;
-+      memcpy (de->name, name, namelen);
-+      /*
-+       * XXX shouldn't update any times until successful
-+       * completion of syscall, but too many callers depend
-+       * on this.
-+       *
-+       * XXX similarly, too many callers depend on
-+       * ext3_new_inode() setting the times, but error
-+       * recovery deletes the inode, so the worst that can
-+       * happen is that the times are slightly out of date
-+       * and/or different from the directory change time.
-+       */
-+      dir->i_mtime = dir->i_ctime = CURRENT_TIME;
-+      ext3_update_dx_flag(dir);
-+      dir->i_version = ++event;
-+      ext3_mark_inode_dirty(handle, dir);
-+      BUFFER_TRACE(bh, "call ext3_journal_dirty_metadata");
-+      err = ext3_journal_dirty_metadata(handle, bh);
-+      if (err)
-+              ext3_std_error(dir->i_sb, err);
-+      brelse(bh);
-+      return 0;
-+}
-+
-+#ifdef CONFIG_EXT3_INDEX
-+/*
-+ * This converts a one block unindexed directory to a 3 block indexed
-+ * directory, and adds the dentry to the indexed directory.
-+ */
-+static int make_indexed_dir(handle_t *handle, struct dentry *dentry,
-+                          struct inode *inode, struct buffer_head *bh)
-+{
-+      struct inode    *dir = dentry->d_parent->d_inode;
-+      const char      *name = dentry->d_name.name;
-+      int             namelen = dentry->d_name.len;
-+      struct buffer_head *bh2;
-+      struct dx_root  *root;
-+      struct dx_frame frames[2], *frame;
-+      struct dx_entry *entries;
-+      struct ext3_dir_entry_2 *de, *de2;
-+      char            *data1, *top;
-+      unsigned        len;
-+      int             retval;
-+      unsigned        blocksize;
-+      struct dx_hash_info hinfo;
-+      u32             block;
-+              
-+      blocksize =  dir->i_sb->s_blocksize;
-+      dxtrace(printk("Creating index\n"));
-+      retval = ext3_journal_get_write_access(handle, bh);
-+      if (retval) {
-+              ext3_std_error(dir->i_sb, retval);
-+              brelse(bh);
-+              return retval;
-+      }
-+      root = (struct dx_root *) bh->b_data;
-+              
-+      EXT3_I(dir)->i_flags |= EXT3_INDEX_FL;
-+      bh2 = ext3_append (handle, dir, &block, &retval);
-+      if (!(bh2)) {
-+              brelse(bh);
-+              return retval;
-+      }
-+      data1 = bh2->b_data;
-+
-+      /* The 0th block becomes the root, move the dirents out */
-+      de = (struct ext3_dir_entry_2 *)&root->dotdot;
-+      de = (struct ext3_dir_entry_2 *)((char *)de + le16_to_cpu(de->rec_len));
-+      len = ((char *) root) + blocksize - (char *) de;
-+      memcpy (data1, de, len);
-+      de = (struct ext3_dir_entry_2 *) data1;
-+      top = data1 + len;
-+      while (((char *) de2=(char*)de+le16_to_cpu(de->rec_len)) < top)
-+              de = de2;
-+      de->rec_len = cpu_to_le16(data1 + blocksize - (char *) de);
-+      /* Initialize the root; the dot dirents already exist */
-+      de = (struct ext3_dir_entry_2 *) (&root->dotdot);
-+      de->rec_len = cpu_to_le16(blocksize - EXT3_DIR_REC_LEN(2));
-+      memset (&root->info, 0, sizeof(root->info));
-+      root->info.info_length = sizeof(root->info);
-+      root->info.hash_version = dir->i_sb->u.ext3_sb.s_def_hash_version;
-+      entries = root->entries;
-+      dx_set_block (entries, 1);
-+      dx_set_count (entries, 1);
-+      dx_set_limit (entries, dx_root_limit(dir, sizeof(root->info)));
-+
-+      /* Initialize as for dx_probe */
-+      hinfo.hash_version = root->info.hash_version;
-+      hinfo.seed = dir->i_sb->u.ext3_sb.s_hash_seed;
-+      ext3fs_dirhash(name, namelen, &hinfo);
-+      frame = frames;
-+      frame->entries = entries;
-+      frame->at = entries;
-+      frame->bh = bh;
-+      bh = bh2;
-+      de = do_split(handle,dir, &bh, frame, &hinfo, &retval);
-+      dx_release (frames);
-+      if (!(de))
-+              return retval;
-+
-+      return add_dirent_to_buf(handle, dentry, inode, de, bh);
-+}
-+#endif
-+
- /*
-  *    ext3_add_entry()
-  *
-@@ -247,127 +1268,198 @@
-  * may not sleep between calling this and putting something into
-  * the entry, as someone else might have used it while you slept.
-  */
--
--/*
-- * AKPM: the journalling code here looks wrong on the error paths
-- */
- static int ext3_add_entry (handle_t *handle, struct dentry *dentry,
-       struct inode *inode)
- {
-       struct inode *dir = dentry->d_parent->d_inode;
--      const char *name = dentry->d_name.name;
--      int namelen = dentry->d_name.len;
-       unsigned long offset;
--      unsigned short rec_len;
-       struct buffer_head * bh;
--      struct ext3_dir_entry_2 * de, * de1;
-+      struct ext3_dir_entry_2 *de;
-       struct super_block * sb;
-       int     retval;
-+#ifdef CONFIG_EXT3_INDEX
-+      int     dx_fallback=0;
-+#endif
-+      unsigned blocksize;
-+      unsigned nlen, rlen;
-+      u32 block, blocks;
-       sb = dir->i_sb;
--
--      if (!namelen)
-+      blocksize = sb->s_blocksize;
-+      if (!dentry->d_name.len)
-               return -EINVAL;
--      bh = ext3_bread (handle, dir, 0, 0, &retval);
-+#ifdef CONFIG_EXT3_INDEX
-+      if (is_dx(dir)) {
-+              retval = ext3_dx_add_entry(handle, dentry, inode);
-+              if (!retval || (retval != ERR_BAD_DX_DIR))
-+                      return retval;
-+              EXT3_I(dir)->i_flags &= ~EXT3_INDEX_FL;
-+              dx_fallback++;
-+              ext3_mark_inode_dirty(handle, dir);
-+      }
-+#endif
-+      blocks = dir->i_size >> sb->s_blocksize_bits;
-+      for (block = 0, offset = 0; block < blocks; block++) {
-+              bh = ext3_bread(handle, dir, block, 0, &retval);
-+              if(!bh)
-+                      return retval;
-+              retval = add_dirent_to_buf(handle, dentry, inode, 0, bh);
-+              if (retval != -ENOSPC)
-+                      return retval;
-+
-+#ifdef CONFIG_EXT3_INDEX
-+              if (blocks == 1 && !dx_fallback &&
-+                  EXT3_HAS_COMPAT_FEATURE(sb, EXT3_FEATURE_COMPAT_DIR_INDEX))
-+                      return make_indexed_dir(handle, dentry, inode, bh);
-+#endif
-+              brelse(bh);
-+      }
-+      bh = ext3_append(handle, dir, &block, &retval);
-       if (!bh)
-               return retval;
--      rec_len = EXT3_DIR_REC_LEN(namelen);
--      offset = 0;
-       de = (struct ext3_dir_entry_2 *) bh->b_data;
--      while (1) {
--              if ((char *)de >= sb->s_blocksize + bh->b_data) {
--                      brelse (bh);
--                      bh = NULL;
--                      bh = ext3_bread (handle, dir,
--                              offset >> EXT3_BLOCK_SIZE_BITS(sb), 1, &retval);
--                      if (!bh)
--                              return retval;
--                      if (dir->i_size <= offset) {
--                              if (dir->i_size == 0) {
--                                      brelse(bh);
--                                      return -ENOENT;
--                              }
-+      de->inode = 0;
-+      de->rec_len = cpu_to_le16(rlen = blocksize);
-+      nlen = 0;
-+      return add_dirent_to_buf(handle, dentry, inode, de, bh);
-+}
--                              ext3_debug ("creating next block\n");
-+#ifdef CONFIG_EXT3_INDEX
-+/*
-+ * Returns 0 for success, or a negative error value
-+ */
-+static int ext3_dx_add_entry(handle_t *handle, struct dentry *dentry,
-+                           struct inode *inode)
-+{
-+      struct dx_frame frames[2], *frame;
-+      struct dx_entry *entries, *at;
-+      struct dx_hash_info hinfo;
-+      struct buffer_head * bh;
-+      struct inode *dir = dentry->d_parent->d_inode;
-+      struct super_block * sb = dir->i_sb;
-+      struct ext3_dir_entry_2 *de;
-+      int err;
--                              BUFFER_TRACE(bh, "get_write_access");
--                              ext3_journal_get_write_access(handle, bh);
--                              de = (struct ext3_dir_entry_2 *) bh->b_data;
--                              de->inode = 0;
--                              de->rec_len = le16_to_cpu(sb->s_blocksize);
--                              dir->u.ext3_i.i_disksize =
--                                      dir->i_size = offset + sb->s_blocksize;
--                              dir->u.ext3_i.i_flags &= ~EXT3_INDEX_FL;
--                              ext3_mark_inode_dirty(handle, dir);
--                      } else {
-+      frame = dx_probe(dentry, 0, &hinfo, frames, &err);
-+      if (!frame)
-+              return err;
-+      entries = frame->entries;
-+      at = frame->at;
--                              ext3_debug ("skipping to next block\n");
-+      if (!(bh = ext3_bread(handle,dir, dx_get_block(frame->at), 0, &err)))
-+              goto cleanup;
--                              de = (struct ext3_dir_entry_2 *) bh->b_data;
--                      }
--              }
--              if (!ext3_check_dir_entry ("ext3_add_entry", dir, de, bh,
--                                         offset)) {
--                      brelse (bh);
--                      return -ENOENT;
--              }
--              if (ext3_match (namelen, name, de)) {
--                              brelse (bh);
--                              return -EEXIST;
-+      BUFFER_TRACE(bh, "get_write_access");
-+      err = ext3_journal_get_write_access(handle, bh);
-+      if (err)
-+              goto journal_error;
-+
-+      err = add_dirent_to_buf(handle, dentry, inode, 0, bh);
-+      if (err != -ENOSPC) {
-+              bh = 0;
-+              goto cleanup;
-+      }
-+
-+      /* Block full, should compress but for now just split */
-+      dxtrace(printk("using %u of %u node entries\n",
-+                     dx_get_count(entries), dx_get_limit(entries)));
-+      /* Need to split index? */
-+      if (dx_get_count(entries) == dx_get_limit(entries)) {
-+              u32 newblock;
-+              unsigned icount = dx_get_count(entries);
-+              int levels = frame - frames;
-+              struct dx_entry *entries2;
-+              struct dx_node *node2;
-+              struct buffer_head *bh2;
-+
-+              if (levels && (dx_get_count(frames->entries) ==
-+                             dx_get_limit(frames->entries))) {
-+                      ext3_warning(sb, __FUNCTION__,
-+                                   "Directory index full!\n");
-+                      err = -ENOSPC;
-+                      goto cleanup;
-               }
--              if ((le32_to_cpu(de->inode) == 0 &&
--                              le16_to_cpu(de->rec_len) >= rec_len) ||
--                  (le16_to_cpu(de->rec_len) >=
--                              EXT3_DIR_REC_LEN(de->name_len) + rec_len)) {
--                      BUFFER_TRACE(bh, "get_write_access");
--                      ext3_journal_get_write_access(handle, bh);
--                      /* By now the buffer is marked for journaling */
--                      offset += le16_to_cpu(de->rec_len);
--                      if (le32_to_cpu(de->inode)) {
--                              de1 = (struct ext3_dir_entry_2 *) ((char *) de +
--                                      EXT3_DIR_REC_LEN(de->name_len));
--                              de1->rec_len =
--                                      cpu_to_le16(le16_to_cpu(de->rec_len) -
--                                      EXT3_DIR_REC_LEN(de->name_len));
--                              de->rec_len = cpu_to_le16(
--                                              EXT3_DIR_REC_LEN(de->name_len));
--                              de = de1;
-+              bh2 = ext3_append (handle, dir, &newblock, &err);
-+              if (!(bh2))
-+                      goto cleanup;
-+              node2 = (struct dx_node *)(bh2->b_data);
-+              entries2 = node2->entries;
-+              node2->fake.rec_len = cpu_to_le16(sb->s_blocksize);
-+              node2->fake.inode = 0;
-+              BUFFER_TRACE(frame->bh, "get_write_access");
-+              err = ext3_journal_get_write_access(handle, frame->bh);
-+              if (err)
-+                      goto journal_error;
-+              if (levels) {
-+                      unsigned icount1 = icount/2, icount2 = icount - icount1;
-+                      unsigned hash2 = dx_get_hash(entries + icount1);
-+                      dxtrace(printk("Split index %i/%i\n", icount1, icount2));
-+                              
-+                      BUFFER_TRACE(frame->bh, "get_write_access"); /* index root */
-+                      err = ext3_journal_get_write_access(handle,
-+                                                           frames[0].bh);
-+                      if (err)
-+                              goto journal_error;
-+                              
-+                      memcpy ((char *) entries2, (char *) (entries + icount1),
-+                              icount2 * sizeof(struct dx_entry));
-+                      dx_set_count (entries, icount1);
-+                      dx_set_count (entries2, icount2);
-+                      dx_set_limit (entries2, dx_node_limit(dir));
-+
-+                      /* Which index block gets the new entry? */
-+                      if (at - entries >= icount1) {
-+                              frame->at = at = at - entries - icount1 + entries2;
-+                              frame->entries = entries = entries2;
-+                              swap(frame->bh, bh2);
-                       }
--                      de->file_type = EXT3_FT_UNKNOWN;
--                      if (inode) {
--                              de->inode = cpu_to_le32(inode->i_ino);
--                              ext3_set_de_type(dir->i_sb, de, inode->i_mode);
--                      } else
--                              de->inode = 0;
--                      de->name_len = namelen;
--                      memcpy (de->name, name, namelen);
--                      /*
--                       * XXX shouldn't update any times until successful
--                       * completion of syscall, but too many callers depend
--                       * on this.
--                       *
--                       * XXX similarly, too many callers depend on
--                       * ext3_new_inode() setting the times, but error
--                       * recovery deletes the inode, so the worst that can
--                       * happen is that the times are slightly out of date
--                       * and/or different from the directory change time.
--                       */
--                      dir->i_mtime = dir->i_ctime = CURRENT_TIME;
--                      dir->u.ext3_i.i_flags &= ~EXT3_INDEX_FL;
--                      dir->i_version = ++event;
--                      ext3_mark_inode_dirty(handle, dir);
--                      BUFFER_TRACE(bh, "call ext3_journal_dirty_metadata");
--                      ext3_journal_dirty_metadata(handle, bh);
--                      brelse(bh);
--                      return 0;
-+                      dx_insert_block (frames + 0, hash2, newblock);
-+                      dxtrace(dx_show_index ("node", frames[1].entries));
-+                      dxtrace(dx_show_index ("node",
-+                             ((struct dx_node *) bh2->b_data)->entries));
-+                      err = ext3_journal_dirty_metadata(handle, bh2);
-+                      if (err)
-+                              goto journal_error;
-+                      brelse (bh2);
-+              } else {
-+                      dxtrace(printk("Creating second level index...\n"));
-+                      memcpy((char *) entries2, (char *) entries,
-+                             icount * sizeof(struct dx_entry));
-+                      dx_set_limit(entries2, dx_node_limit(dir));
-+
-+                      /* Set up root */
-+                      dx_set_count(entries, 1);
-+                      dx_set_block(entries + 0, newblock);
-+                      ((struct dx_root *) frames[0].bh->b_data)->info.indirect_levels = 1;
-+
-+                      /* Add new access path frame */
-+                      frame = frames + 1;
-+                      frame->at = at = at - entries + entries2;
-+                      frame->entries = entries = entries2;
-+                      frame->bh = bh2;
-+                      err = ext3_journal_get_write_access(handle,
-+                                                           frame->bh);
-+                      if (err)
-+                              goto journal_error;
-               }
--              offset += le16_to_cpu(de->rec_len);
--              de = (struct ext3_dir_entry_2 *)
--                      ((char *) de + le16_to_cpu(de->rec_len));
-+              ext3_journal_dirty_metadata(handle, frames[0].bh);
-       }
--      brelse (bh);
--      return -ENOSPC;
-+      de = do_split(handle, dir, &bh, frame, &hinfo, &err);
-+      if (!de)
-+              goto cleanup;
-+      err = add_dirent_to_buf(handle, dentry, inode, de, bh);
-+      bh = 0;
-+      goto cleanup;
-+      
-+journal_error:
-+      ext3_std_error(dir->i_sb, err);
-+cleanup:
-+      if (bh)
-+              brelse(bh);
-+      dx_release(frames);
-+      return err;
- }
-+#endif
- /*
-  * ext3_delete_entry deletes a directory entry by merging it with the
-@@ -454,9 +1546,11 @@
-       struct inode * inode;
-       int err;
--      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS + 3);
--      if (IS_ERR(handle))
-+      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS +
-+                                      EXT3_INDEX_EXTRA_TRANS_BLOCKS + 3);
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
-@@ -480,9 +1574,11 @@
-       struct inode *inode;
-       int err;
--      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS + 3);
--      if (IS_ERR(handle))
-+      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS +
-+                                      EXT3_INDEX_EXTRA_TRANS_BLOCKS + 3);
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
-@@ -508,9 +1604,11 @@
-       if (dir->i_nlink >= EXT3_LINK_MAX)
-               return -EMLINK;
--      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS + 3);
--      if (IS_ERR(handle))
-+      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS +
-+                                      EXT3_INDEX_EXTRA_TRANS_BLOCKS + 3);
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
-@@ -522,7 +1620,7 @@
-       inode->i_op = &ext3_dir_inode_operations;
-       inode->i_fop = &ext3_dir_operations;
--      inode->i_size = inode->u.ext3_i.i_disksize = inode->i_sb->s_blocksize;
-+      inode->i_size = EXT3_I(inode)->i_disksize = inode->i_sb->s_blocksize;
-       inode->i_blocks = 0;    
-       dir_block = ext3_bread (handle, inode, 0, 1, &err);
-       if (!dir_block) {
-@@ -555,21 +1653,19 @@
-               inode->i_mode |= S_ISGID;
-       ext3_mark_inode_dirty(handle, inode);
-       err = ext3_add_entry (handle, dentry, inode);
--      if (err)
--              goto out_no_entry;
-+      if (err) {
-+              inode->i_nlink = 0;
-+              ext3_mark_inode_dirty(handle, inode);
-+              iput (inode);
-+              goto out_stop;
-+      }
-       dir->i_nlink++;
--      dir->u.ext3_i.i_flags &= ~EXT3_INDEX_FL;
-+      ext3_update_dx_flag(dir);
-       ext3_mark_inode_dirty(handle, dir);
-       d_instantiate(dentry, inode);
- out_stop:
-       ext3_journal_stop(handle, dir);
-       return err;
--
--out_no_entry:
--      inode->i_nlink = 0;
--      ext3_mark_inode_dirty(handle, inode);
--      iput (inode);
--      goto out_stop;
- }
- /*
-@@ -656,7 +1752,7 @@
-       int err = 0, rc;
-       
-       lock_super(sb);
--      if (!list_empty(&inode->u.ext3_i.i_orphan))
-+      if (!list_empty(&EXT3_I(inode)->i_orphan))
-               goto out_unlock;
-       /* Orphan handling is only valid for files with data blocks
-@@ -697,7 +1793,7 @@
-        * This is safe: on error we're going to ignore the orphan list
-        * anyway on the next recovery. */
-       if (!err)
--              list_add(&inode->u.ext3_i.i_orphan, &EXT3_SB(sb)->s_orphan);
-+              list_add(&EXT3_I(inode)->i_orphan, &EXT3_SB(sb)->s_orphan);
-       jbd_debug(4, "superblock will point to %ld\n", inode->i_ino);
-       jbd_debug(4, "orphan inode %ld will point to %d\n",
-@@ -794,8 +1890,9 @@
-       handle_t *handle;
-       handle = ext3_journal_start(dir, EXT3_DELETE_TRANS_BLOCKS);
--      if (IS_ERR(handle))
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       retval = -ENOENT;
-       bh = ext3_find_entry (dentry, &de);
-@@ -833,7 +1930,7 @@
-       dir->i_nlink--;
-       inode->i_ctime = dir->i_ctime = dir->i_mtime = CURRENT_TIME;
-       ext3_mark_inode_dirty(handle, inode);
--      dir->u.ext3_i.i_flags &= ~EXT3_INDEX_FL;
-+      ext3_update_dx_flag(dir);
-       ext3_mark_inode_dirty(handle, dir);
- end_rmdir:
-@@ -851,8 +1948,9 @@
-       handle_t *handle;
-       handle = ext3_journal_start(dir, EXT3_DELETE_TRANS_BLOCKS);
--      if (IS_ERR(handle))
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
-@@ -879,7 +1977,7 @@
-       if (retval)
-               goto end_unlink;
-       dir->i_ctime = dir->i_mtime = CURRENT_TIME;
--      dir->u.ext3_i.i_flags &= ~EXT3_INDEX_FL;
-+      ext3_update_dx_flag(dir);
-       ext3_mark_inode_dirty(handle, dir);
-       inode->i_nlink--;
-       if (!inode->i_nlink)
-@@ -905,9 +2003,11 @@
-       if (l > dir->i_sb->s_blocksize)
-               return -ENAMETOOLONG;
--      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS + 5);
--      if (IS_ERR(handle))
-+      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS +
-+                                      EXT3_INDEX_EXTRA_TRANS_BLOCKS + 5);
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
-@@ -917,7 +2017,7 @@
-       if (IS_ERR(inode))
-               goto out_stop;
--      if (l > sizeof (inode->u.ext3_i.i_data)) {
-+      if (l > sizeof (EXT3_I(inode)->i_data)) {
-               inode->i_op = &page_symlink_inode_operations;
-               inode->i_mapping->a_ops = &ext3_aops;
-               /*
-@@ -926,8 +2026,12 @@
-                * i_size in generic_commit_write().
-                */
-               err = block_symlink(inode, symname, l);
--              if (err)
--                      goto out_no_entry;
-+              if (err) {
-+                      ext3_dec_count(handle, inode);
-+                      ext3_mark_inode_dirty(handle, inode);
-+                      iput (inode);
-+                      goto out_stop;
-+              }
-       } else {
-               inode->i_op = &ext3_fast_symlink_inode_operations;
-               memcpy((char*)&inode->u.ext3_i.i_data,symname,l);
-@@ -938,12 +2042,6 @@
- out_stop:
-       ext3_journal_stop(handle, dir);
-       return err;
--
--out_no_entry:
--      ext3_dec_count(handle, inode);
--      ext3_mark_inode_dirty(handle, inode);
--      iput (inode);
--      goto out_stop;
- }
- static int ext3_link (struct dentry * old_dentry,
-@@ -956,12 +2054,15 @@
-       if (S_ISDIR(inode->i_mode))
-               return -EPERM;
--      if (inode->i_nlink >= EXT3_LINK_MAX)
-+      if (inode->i_nlink >= EXT3_LINK_MAX) {
-               return -EMLINK;
-+      }
--      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS);
--      if (IS_ERR(handle))
-+      handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS +
-+                                      EXT3_INDEX_EXTRA_TRANS_BLOCKS);
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
-@@ -994,9 +2095,11 @@
-       old_bh = new_bh = dir_bh = NULL;
--      handle = ext3_journal_start(old_dir, 2 * EXT3_DATA_TRANS_BLOCKS + 2);
--      if (IS_ERR(handle))
-+      handle = ext3_journal_start(old_dir, 2 * EXT3_DATA_TRANS_BLOCKS +
-+                                      EXT3_INDEX_EXTRA_TRANS_BLOCKS + 2);
-+      if (IS_ERR(handle)) {
-               return PTR_ERR(handle);
-+      }
-       if (IS_SYNC(old_dir) || IS_SYNC(new_dir))
-               handle->h_sync = 1;
-@@ -1069,14 +2172,37 @@
-       /*
-        * ok, that's it
-        */
--      ext3_delete_entry(handle, old_dir, old_de, old_bh);
-+      if (le32_to_cpu(old_de->inode) != old_inode->i_ino ||
-+          old_de->name_len != old_dentry->d_name.len ||
-+          strncmp(old_de->name, old_dentry->d_name.name, old_de->name_len) ||
-+          (retval = ext3_delete_entry(handle, old_dir,
-+                                      old_de, old_bh)) == -ENOENT) {
-+              /* old_de could have moved from under us during htree split, so
-+               * make sure that we are deleting the right entry.  We might
-+               * also be pointing to a stale entry in the unused part of
-+               * old_bh so just checking inum and the name isn't enough. */
-+              struct buffer_head *old_bh2;
-+              struct ext3_dir_entry_2 *old_de2;
-+
-+              old_bh2 = ext3_find_entry(old_dentry, &old_de2);
-+              if (old_bh2) {
-+                      retval = ext3_delete_entry(handle, old_dir,
-+                                                 old_de2, old_bh2);
-+                      brelse(old_bh2);
-+              }
-+      }
-+      if (retval) {
-+              ext3_warning(old_dir->i_sb, "ext3_rename",
-+                              "Deleting old file (%lu), %d, error=%d",
-+                              old_dir->i_ino, old_dir->i_nlink, retval);
-+      }
-       if (new_inode) {
-               new_inode->i_nlink--;
-               new_inode->i_ctime = CURRENT_TIME;
-       }
-       old_dir->i_ctime = old_dir->i_mtime = CURRENT_TIME;
--      old_dir->u.ext3_i.i_flags &= ~EXT3_INDEX_FL;
-+      ext3_update_dx_flag(old_dir);
-       if (dir_bh) {
-               BUFFER_TRACE(dir_bh, "get_write_access");
-               ext3_journal_get_write_access(handle, dir_bh);
-@@ -1088,7 +2210,7 @@
-                       new_inode->i_nlink--;
-               } else {
-                       new_dir->i_nlink++;
--                      new_dir->u.ext3_i.i_flags &= ~EXT3_INDEX_FL;
-+                      ext3_update_dx_flag(new_dir);
-                       ext3_mark_inode_dirty(handle, new_dir);
-               }
-       }
-Index: linux-2.4.21-suse/fs/ext3/super.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/super.c     2003-10-29 22:39:14.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/super.c  2003-10-29 23:17:20.000000000 +0300
-@@ -710,6 +710,7 @@
-       es->s_mtime = cpu_to_le32(CURRENT_TIME);
-       ext3_update_dynamic_rev(sb);
-       EXT3_SET_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_RECOVER);
-+
-       ext3_commit_super (sb, es, 1);
-       if (test_opt (sb, DEBUG))
-               printk (KERN_INFO
-@@ -720,6 +721,7 @@
-                       EXT3_BLOCKS_PER_GROUP(sb),
-                       EXT3_INODES_PER_GROUP(sb),
-                       sbi->s_mount_opt);
-+
-       printk(KERN_INFO "EXT3 FS " EXT3FS_VERSION ", " EXT3FS_DATE " on %s, ",
-                               bdevname(sb->s_dev));
-       if (EXT3_SB(sb)->s_journal->j_inode == NULL) {
-@@ -893,6 +895,7 @@
-       return res;
- }
-+
- struct super_block * ext3_read_super (struct super_block * sb, void * data,
-                                     int silent)
- {
-@@ -1069,6 +1072,9 @@
-       sbi->s_mount_state = le16_to_cpu(es->s_state);
-       sbi->s_addr_per_block_bits = log2(EXT3_ADDR_PER_BLOCK(sb));
-       sbi->s_desc_per_block_bits = log2(EXT3_DESC_PER_BLOCK(sb));
-+      for (i=0; i < 4; i++)
-+              sbi->s_hash_seed[i] = le32_to_cpu(es->s_hash_seed[i]);
-+      sbi->s_def_hash_version = es->s_def_hash_version;
-       if (sbi->s_blocks_per_group > blocksize * 8) {
-               printk (KERN_ERR
-@@ -1770,6 +1776,7 @@
-       unregister_filesystem(&ext3_fs_type);
- }
-+EXPORT_SYMBOL(ext3_force_commit);
- EXPORT_SYMBOL(ext3_bread);
- MODULE_AUTHOR("Remy Card, Stephen Tweedie, Andrew Morton, Andreas Dilger, Theodore Ts'o and others");
-Index: linux-2.4.21-suse/include/linux/ext3_fs.h
-===================================================================
---- linux-2.4.21-suse.orig/include/linux/ext3_fs.h     2003-06-14 02:28:25.000000000 +0400
-+++ linux-2.4.21-suse/include/linux/ext3_fs.h  2003-10-29 23:17:20.000000000 +0300
-@@ -40,6 +40,11 @@
- #define EXT3FS_VERSION                "2.4-0.9.19"
- /*
-+ * Always enable hashed directories
-+ */
-+#define CONFIG_EXT3_INDEX
-+
-+/*
-  * Debug code
-  */
- #ifdef EXT3FS_DEBUG
-@@ -438,8 +443,11 @@
- /*E0*/        __u32   s_journal_inum;         /* inode number of journal file */
-       __u32   s_journal_dev;          /* device number of journal file */
-       __u32   s_last_orphan;          /* start of list of inodes to delete */
--
--/*EC*/        __u32   s_reserved[197];        /* Padding to the end of the block */
-+      __u32   s_hash_seed[4];         /* HTREE hash seed */
-+      __u8    s_def_hash_version;     /* Default hash version to use */
-+      __u8    s_reserved_char_pad;
-+      __u16   s_reserved_word_pad;
-+      __u32   s_reserved[192];        /* Padding to the end of the block */
- };
- #ifdef __KERNEL__
-@@ -576,9 +584,46 @@
- #define EXT3_DIR_ROUND                        (EXT3_DIR_PAD - 1)
- #define EXT3_DIR_REC_LEN(name_len)    (((name_len) + 8 + EXT3_DIR_ROUND) & \
-                                        ~EXT3_DIR_ROUND)
-+/*
-+ * Hash Tree Directory indexing
-+ * (c) Daniel Phillips, 2001
-+ */
-+
-+#ifdef CONFIG_EXT3_INDEX
-+  #define is_dx(dir) (EXT3_HAS_COMPAT_FEATURE(dir->i_sb, \
-+                                            EXT3_FEATURE_COMPAT_DIR_INDEX) && \
-+                    (EXT3_I(dir)->i_flags & EXT3_INDEX_FL))
-+#define EXT3_DIR_LINK_MAX(dir) (!is_dx(dir) && (dir)->i_nlink >= EXT3_LINK_MAX)
-+#define EXT3_DIR_LINK_EMPTY(dir) ((dir)->i_nlink == 2 || (dir)->i_nlink == 1)
-+#else
-+  #define is_dx(dir) 0
-+#define EXT3_DIR_LINK_MAX(dir) ((dir)->i_nlink >= EXT3_LINK_MAX)
-+#define EXT3_DIR_LINK_EMPTY(dir) ((dir)->i_nlink == 2)
-+#endif
-+
-+/* Legal values for the dx_root hash_version field: */
-+
-+#define DX_HASH_LEGACY                0
-+#define DX_HASH_HALF_MD4      1
-+#define DX_HASH_TEA           2
-+
-+/* hash info structure used by the directory hash */
-+struct dx_hash_info
-+{
-+      u32             hash;
-+      u32             minor_hash;
-+      int             hash_version;
-+      u32             *seed;
-+};
- #ifdef __KERNEL__
- /*
-+ * Control parameters used by ext3_htree_next_block
-+ */
-+#define HASH_NB_ALWAYS                1
-+
-+
-+/*
-  * Describe an inode's exact location on disk and in memory
-  */
- struct ext3_iloc
-@@ -588,6 +633,27 @@
-       unsigned long block_group;
- };
-+
-+/*
-+ * This structure is stuffed into the struct file's private_data field
-+ * for directories.  It is where we put information so that we can do
-+ * readdir operations in hash tree order.
-+ */
-+struct dir_private_info {
-+      rb_root_t       root;
-+      rb_node_t       *curr_node;
-+      struct fname    *extra_fname;
-+      loff_t          last_pos;
-+      __u32           curr_hash;
-+      __u32           curr_minor_hash;
-+      __u32           next_hash;
-+};
-+
-+/*
-+ * Special error return code only used by dx_probe() and its callers.
-+ */
-+#define ERR_BAD_DX_DIR        -75000
-+
- /*
-  * Function prototypes
-  */
-@@ -615,11 +681,20 @@
- /* dir.c */
- extern int ext3_check_dir_entry(const char *, struct inode *,
--                              struct ext3_dir_entry_2 *, struct buffer_head *,
--                              unsigned long);
-+                              struct ext3_dir_entry_2 *,
-+                              struct buffer_head *, unsigned long);
-+extern int ext3_htree_store_dirent(struct file *dir_file, __u32 hash,
-+                                  __u32 minor_hash,
-+                                  struct ext3_dir_entry_2 *dirent);
-+extern void ext3_htree_free_dir_info(struct dir_private_info *p);
-+
- /* fsync.c */
- extern int ext3_sync_file (struct file *, struct dentry *, int);
-+/* hash.c */
-+extern int ext3fs_dirhash(const char *name, int len, struct
-+                        dx_hash_info *hinfo);
-+
- /* ialloc.c */
- extern struct inode * ext3_new_inode (handle_t *, const struct inode *, int);
- extern void ext3_free_inode (handle_t *, struct inode *);
-@@ -652,6 +727,8 @@
- /* namei.c */
- extern int ext3_orphan_add(handle_t *, struct inode *);
- extern int ext3_orphan_del(handle_t *, struct inode *);
-+extern int ext3_htree_fill_tree(struct file *dir_file, __u32 start_hash,
-+                              __u32 start_minor_hash, __u32 *next_hash);
- /* super.c */
- extern void ext3_error (struct super_block *, const char *, const char *, ...)
-Index: linux-2.4.21-suse/include/linux/ext3_fs_sb.h
-===================================================================
---- linux-2.4.21-suse.orig/include/linux/ext3_fs_sb.h  2003-06-14 02:26:52.000000000 +0400
-+++ linux-2.4.21-suse/include/linux/ext3_fs_sb.h       2003-10-29 23:17:20.000000000 +0300
-@@ -62,6 +62,8 @@
-       int s_inode_size;
-       int s_first_ino;
-       u32 s_next_generation;
-+      u32 s_hash_seed[4];
-+      int s_def_hash_version;
-       /* Journaling */
-       struct inode * s_journal_inode;
-Index: linux-2.4.21-suse/include/linux/ext3_jbd.h
-===================================================================
---- linux-2.4.21-suse.orig/include/linux/ext3_jbd.h    2003-06-14 02:28:25.000000000 +0400
-+++ linux-2.4.21-suse/include/linux/ext3_jbd.h 2003-10-29 23:17:20.000000000 +0300
-@@ -63,6 +63,8 @@
- #define EXT3_RESERVE_TRANS_BLOCKS     12U
-+#define EXT3_INDEX_EXTRA_TRANS_BLOCKS 8
-+
- int
- ext3_mark_iloc_dirty(handle_t *handle, 
-                    struct inode *inode,
-Index: linux-2.4.21-suse/include/linux/rbtree.h
-===================================================================
---- linux-2.4.21-suse.orig/include/linux/rbtree.h      2003-06-14 02:26:51.000000000 +0400
-+++ linux-2.4.21-suse/include/linux/rbtree.h   2003-10-29 23:17:20.000000000 +0300
-@@ -120,6 +120,8 @@
- extern void rb_insert_color(rb_node_t *, rb_root_t *);
- extern void rb_erase(rb_node_t *, rb_root_t *);
-+extern rb_node_t *rb_get_first(rb_root_t *root);
-+extern rb_node_t *rb_get_next(rb_node_t *n);
- static inline void rb_link_node(rb_node_t * node, rb_node_t * parent, rb_node_t ** rb_link)
- {
-Index: linux-2.4.21-suse/lib/rbtree.c
-===================================================================
---- linux-2.4.21-suse.orig/lib/rbtree.c        2002-08-03 04:39:46.000000000 +0400
-+++ linux-2.4.21-suse/lib/rbtree.c     2003-10-29 23:17:20.000000000 +0300
-@@ -17,6 +17,8 @@
-   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
-   linux/lib/rbtree.c
-+
-+  rb_get_first and rb_get_next written by Theodore Ts'o, 9/8/2002
- */
- #include <linux/rbtree.h>
-@@ -294,3 +296,43 @@
-               __rb_erase_color(child, parent, root);
- }
- EXPORT_SYMBOL(rb_erase);
-+
-+/*
-+ * This function returns the first node (in sort order) of the tree.
-+ */
-+rb_node_t *rb_get_first(rb_root_t *root)
-+{
-+      rb_node_t       *n;
-+
-+      n = root->rb_node;
-+      if (!n)
-+              return 0;
-+      while (n->rb_left)
-+              n = n->rb_left;
-+      return n;
-+}
-+EXPORT_SYMBOL(rb_get_first);
-+
-+/*
-+ * Given a node, this function will return the next node in the tree.
-+ */
-+rb_node_t *rb_get_next(rb_node_t *n)
-+{
-+      rb_node_t       *parent;
-+
-+      if (n->rb_right) {
-+              n = n->rb_right;
-+              while (n->rb_left)
-+                      n = n->rb_left;
-+              return n;
-+      } else {
-+              while ((parent = n->rb_parent)) {
-+                      if (n == parent->rb_left)
-+                              return parent;
-+                      n = parent;
-+              }
-+              return 0;
-+      }
-+}
-+EXPORT_SYMBOL(rb_get_next);
-+
diff --git a/lustre/kernel_patches/patches/ext3-init-generation-2.6-suse.patch b/lustre/kernel_patches/patches/ext3-init-generation-2.6-suse.patch
deleted file mode 100644 (file)
index d15e397..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-Index: linux-2.6.0/fs/ext3/super.c
-===================================================================
---- linux-2.6.0.orig/fs/ext3/super.c   2003-12-31 16:00:58.000000000 +0300
-+++ linux-2.6.0/fs/ext3/super.c        2004-01-03 11:25:32.000000000 +0300
-@@ -1068,6 +1068,7 @@
-       sbi->s_mount_opt = 0;
-       sbi->s_resuid = EXT3_DEF_RESUID;
-       sbi->s_resgid = EXT3_DEF_RESGID;
-+      sbi->s_next_generation = jiffies;
-       blocksize = sb_min_blocksize(sb, EXT3_MIN_BLOCK_SIZE);
-       if (!blocksize) {
index 82957f1..b9bcfac 100644 (file)
@@ -1,10 +1,10 @@
-Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
+Index: linux-2.6.5-suse/fs/ext3/mballoc.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/mballoc.c   2005-02-17 22:07:57.023609040 +0300
-+++ linux-2.6.5-sles9/fs/ext3/mballoc.c        2005-02-23 01:56:19.101662000 +0300
-@@ -0,0 +1,1835 @@
+--- linux-2.6.5-suse.orig/fs/ext3/mballoc.c    2005-03-02 22:42:20.659360368 +0300
++++ linux-2.6.5-suse/fs/ext3/mballoc.c 2005-03-11 16:13:13.000000000 +0300
+@@ -0,0 +1,1863 @@
 +/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
++ * Copyright(c) 2003, 2004, 2005, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
 + *
 + * This program is free software; you can redistribute it and/or modify
@@ -39,6 +39,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +/*
 + * TODO:
++ *   - bitmap/buddy read-ahead (proposed by Oleg Drokin aka green)
 + *   - track min/max extents in each group for better group selection
 + *   - is it worthwhile to use buddies directly if req is 2^N blocks?
 + *   - mb_mark_used() may allocate chunk right after splitting buddy
@@ -96,7 +97,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      __u32   mh_magic;
 +};
 +
-+#define EXT3_MB_MAGIC_V1      0xbaad16fc
++#define EXT3_MB_MAGIC_V1      0xbabd16fd
 +
 +
 +struct ext3_free_extent {
@@ -109,7 +110,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      struct super_block *ac_sb;
 +
 +      /* search goals */
-+struct ext3_free_extent ac_g_ex;
++      struct ext3_free_extent ac_g_ex;
 +      
 +      /* the best found extent */
 +      struct ext3_free_extent ac_b_ex;
@@ -148,47 +149,50 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +void ext3_mb_poll_new_transaction(struct super_block *, handle_t *);
 +void ext3_mb_free_committed_blocks(struct super_block *);
 +
-+#define mb_correct_addr_and_bit(bit,addr)     \
-+{                                             \
-+      if ((unsigned long)addr & 1) {          \
-+              bit += 8;                       \
-+              addr--;                         \
-+      }                                       \
-+      if ((unsigned long)addr & 2) {          \
-+              bit += 16;                      \
-+              addr--;                         \
-+              addr--;                         \
-+      }                                       \
++#if BITS_PER_LONG == 64
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 7UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~7UL);  \
 +}
++#elif BITS_PER_LONG == 32
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 3UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~3UL);  \
++}
++#else
++#error "how many bits you are?!"
++#endif
 +
 +static inline int mb_test_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      return test_bit(bit, addr);
++      return ext2_test_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __set_bit(bit, addr);
++      ext2_set_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      set_bit(bit, addr);
++      ext2_set_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void mb_clear_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __clear_bit(bit, addr);
++      ext2_clear_bit(bit, addr);
 +}
 +
 +static inline void mb_clear_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      clear_bit(bit, addr);
++      ext2_clear_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void *mb_find_buddy(struct ext3_buddy *e3b, int order, int *max)
@@ -199,8 +203,10 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      J_ASSERT(EXT3_MB_BITMAP(e3b) != EXT3_MB_BUDDY(e3b));
 +      J_ASSERT(max != NULL);
 +
-+      if (order > e3b->bd_blkbits + 1)
++      if (order > e3b->bd_blkbits + 1) {
++              *max = 0;
 +              return NULL;
++      }
 +
 +      /* at order 0 we see each particular block */
 +      *max = 1 << (e3b->bd_blkbits + 3);
@@ -234,12 +240,6 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh)) {
-+              ll_rw_block(READ, 1, &e3b->bd_bh);
-+              wait_on_buffer(e3b->bd_bh);
-+      }
-+      J_ASSERT(buffer_uptodate(e3b->bd_bh));
-+
 +      /* load buddy */
 +      e3b->bd_bh2 = sb_getblk(sb, sbi->s_buddy_blocks[group]->bb_buddy);
 +      if (e3b->bd_bh2 == NULL) {
@@ -247,10 +247,15 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh2)) {
++
++      if (!buffer_uptodate(e3b->bd_bh))
++              ll_rw_block(READ, 1, &e3b->bd_bh);
++      if (!buffer_uptodate(e3b->bd_bh2))
 +              ll_rw_block(READ, 1, &e3b->bd_bh2);
-+              wait_on_buffer(e3b->bd_bh2);
-+      }
++
++      wait_on_buffer(e3b->bd_bh);
++      J_ASSERT(buffer_uptodate(e3b->bd_bh));
++      wait_on_buffer(e3b->bd_bh2);
 +      J_ASSERT(buffer_uptodate(e3b->bd_bh2));
 +
 +      e3b->bd_blkbits = sb->s_blocksize_bits;
@@ -300,22 +305,22 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              count = 0;
 +              for (i = 0; i < max; i++) {
 +
-+                      if (!mb_test_bit(i, buddy)) {
++                      if (mb_test_bit(i, buddy)) {
 +                              /* only single bit in buddy2 may be 1 */
-+                              if (mb_test_bit(i << 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit((i<<1)+1, buddy2));
-+                              else if (mb_test_bit((i << 1) + 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
++                              if (!mb_test_bit(i << 1, buddy2))
++                                      J_ASSERT(mb_test_bit((i<<1)+1, buddy2));
++                              else if (!mb_test_bit((i << 1) + 1, buddy2))
++                                      J_ASSERT(mb_test_bit(i << 1, buddy2));
 +                              continue;
 +                      }
 +
 +                      /* both bits in buddy2 must be 0 */
-+                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
-+                      J_ASSERT(!mb_test_bit((i << 1) + 1, buddy2));
++                      J_ASSERT(mb_test_bit(i << 1, buddy2));
++                      J_ASSERT(mb_test_bit((i << 1) + 1, buddy2));
 +
 +                      for (j = 0; j < (1 << order); j++) {
 +                              k = (i * (1 << order)) + j;
-+                              J_ASSERT(mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
++                              J_ASSERT(!mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
 +                      }
 +                      count++;
 +              }
@@ -325,14 +330,14 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +      buddy = mb_find_buddy(e3b, 0, &max);
 +      for (i = 0; i < max; i++) {
-+              if (mb_test_bit(i, buddy))
++              if (!mb_test_bit(i, buddy))
 +                      continue;
 +              /* check used bits only */
 +              for (j = 0; j < e3b->bd_blkbits + 1; j++) {
 +                      buddy2 = mb_find_buddy(e3b, j, &max2);
 +                      k = i >> j;
 +                      J_ASSERT(k < max2);
-+                      J_ASSERT(!mb_test_bit(k, buddy2));
++                      J_ASSERT(mb_test_bit(k, buddy2));
 +              }
 +      }
 +}
@@ -363,7 +368,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      bb = EXT3_MB_BUDDY(e3b);
 +      while (order <= e3b->bd_blkbits + 1) {
 +              block = block >> 1;
-+              if (mb_test_bit(block, bb)) {
++              if (!mb_test_bit(block, bb)) {
 +                      /* this block is part of buddy of order 'order' */
 +                      return order;
 +              }
@@ -424,8 +429,8 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              block = first++;
 +              order = 0;
 +
-+              J_ASSERT(!mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
-+              mb_set_bit(block, EXT3_MB_BITMAP(e3b));
++              J_ASSERT(mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
++              mb_clear_bit(block, EXT3_MB_BITMAP(e3b));
 +              e3b->bd_bd->bb_counters[order]++;
 +
 +              /* start of the buddy */
@@ -433,8 +438,8 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +              do {
 +                      block &= ~1UL;
-+                      if (!mb_test_bit(block, buddy) ||
-+                                      !mb_test_bit(block + 1, buddy))
++                      if (mb_test_bit(block, buddy) ||
++                                      mb_test_bit(block + 1, buddy))
 +                              break;
 +
 +                      /* both the buddies are free, try to coalesce them */
@@ -444,10 +449,10 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                              break;
 +
 +                      if (order > 0) {
-+                              /* for special purposes, we don't clear
++                              /* for special purposes, we don't set
 +                               * free bits in bitmap */
-+                              mb_clear_bit(block, buddy);
-+                              mb_clear_bit(block + 1, buddy);
++                              mb_set_bit(block, buddy);
++                              mb_set_bit(block + 1, buddy);
 +                      }
 +                      e3b->bd_bd->bb_counters[order]--;
 +                      e3b->bd_bd->bb_counters[order]--;
@@ -456,7 +461,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      order++;
 +                      e3b->bd_bd->bb_counters[order]++;
 +
-+                      mb_set_bit(block, buddy2);
++                      mb_clear_bit(block, buddy2);
 +                      buddy = buddy2;
 +              } while (1);
 +      }
@@ -466,7 +471,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +}
 +
 +static int mb_find_extent(struct ext3_buddy *e3b, int order, int block,
-+                              int needed, struct ext3_free_extent *ex)
++                        int needed, struct ext3_free_extent *ex)
 +{
 +      int next, max, ord;
 +      void *buddy;
@@ -476,7 +481,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      buddy = mb_find_buddy(e3b, order, &max);
 +      J_ASSERT(buddy);
 +      J_ASSERT(block < max);
-+      if (!mb_test_bit(block, buddy)) {
++      if (mb_test_bit(block, buddy)) {
 +              ex->fe_len = 0;
 +              ex->fe_start = 0;
 +              ex->fe_group = 0;
@@ -499,7 +504,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      break;
 +
 +              next = (block + 1) * (1 << order);
-+              if (!mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
++              if (mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
 +                      break;
 +
 +              ord = mb_find_order_for_block(e3b, next);
@@ -533,7 +538,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      mlen = 1 << ord;
 +                      buddy = mb_find_buddy(e3b, ord, &max);
 +                      J_ASSERT((start >> ord) < max);
-+                      mb_clear_bit(start >> ord, buddy);
++                      mb_set_bit(start >> ord, buddy);
 +                      e3b->bd_bd->bb_counters[ord]--;
 +                      start += mlen;
 +                      len -= mlen;
@@ -544,20 +549,20 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              /* we have to split large buddy */
 +              J_ASSERT(ord > 0);
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_clear_bit(start >> ord, buddy);
++              mb_set_bit(start >> ord, buddy);
 +              e3b->bd_bd->bb_counters[ord]--;
 +
 +              ord--;
 +              cur = (start >> ord) & ~1U;
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_set_bit(cur, buddy);
-+              mb_set_bit(cur + 1, buddy);
++              mb_clear_bit(cur, buddy);
++              mb_clear_bit(cur + 1, buddy);
 +              e3b->bd_bd->bb_counters[ord]++;
 +              e3b->bd_bd->bb_counters[ord]++;
 +      }
 +
 +      /* now drop all the bits in bitmap */
-+      mb_clear_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
++      mb_set_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
 +
 +      mb_check_buddy(e3b);
 +
@@ -733,7 +738,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      i = e3b->bd_bd->bb_first_free;
 +
 +      while (free && ac->ac_status != AC_STATUS_FOUND) {
-+              i = find_next_bit(bitmap, sb->s_blocksize * 8, i);
++              i = ext2_find_next_zero_bit(bitmap, sb->s_blocksize * 8, i);
 +              if (i >= sb->s_blocksize * 8) {
 +                      J_ASSERT(free == 0);
 +                      break;
@@ -951,7 +956,6 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              /*
 +               * We aren't lucky definitely
 +               */
-+              J_ASSERT(ac.ac_b_ex.fe_len == 0);
 +              DQUOT_FREE_BLOCK(inode, *len);
 +              *errp = -ENOSPC;
 +              block = 0;
@@ -1020,8 +1024,8 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              ext3_error(sb, "ext3_new_block",
 +                          "Allocating block in system zone - "
 +                          "block = %u", block);
-+#if AGGRESSIVE_CHECK
-+      for (i = 0; i < ac.ac_b_len; i++)
++#ifdef AGGRESSIVE_CHECK
++      for (i = 0; i < ac.ac_b_ex.fe_len; i++)
 +              J_ASSERT(!mb_test_bit(ac.ac_b_ex.fe_start + i, bitmap_bh->b_data));
 +#endif
 +      mb_set_bits(bitmap_bh->b_data, ac.ac_b_ex.fe_start, ac.ac_b_ex.fe_len);
@@ -1141,7 +1145,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      
 +      e3b->bd_bd->bb_first_free = grp->mgd_first_free;
 +      e3b->bd_bd->bb_free = grp->mgd_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              e3b->bd_bd->bb_counters[i] = grp->mgd_counters[i];
 +      }
@@ -1155,7 +1159,6 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              printk(KERN_ERR "EXT3-fs: mbgroup %d corrupted (%d != %d)\n",
 +                      e3b->bd_group, e3b->bd_bd->bb_free,
 +                      le16_to_cpu(gdp->bg_free_blocks_count));
-+              BUG();
 +              return -ENODATA;
 +      }
 +
@@ -1166,20 +1169,19 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +int ext3_mb_update_descr(struct ext3_buddy *e3b)
 +{
 +      struct ext3_mb_group_descr *grp;
-+      struct ext3_group_desc *ogdp;
++      struct ext3_group_desc *gdp;
 +      struct buffer_head *bh;
 +      handle_t *handle;
 +      int err, i;
 +
 +      /* additional checks against old group descriptor */
-+      ogdp = ext3_get_group_desc(e3b->bd_sb, e3b->bd_group, NULL);
-+      if (!ogdp)
++      gdp = ext3_get_group_desc(e3b->bd_sb, e3b->bd_group, NULL);
++      if (!gdp)
 +              return -EIO;
-+      if (e3b->bd_bd->bb_free != le16_to_cpu(ogdp->bg_free_blocks_count)) {
++      if (e3b->bd_bd->bb_free != le16_to_cpu(gdp->bg_free_blocks_count)) {
 +              printk(KERN_ERR "EXT3-fs: mbgroup %d corrupted (%d != %d)\n",
 +                      e3b->bd_group, e3b->bd_bd->bb_free,
-+                      le16_to_cpu(ogdp->bg_free_blocks_count));
-+              BUG();
++                      le16_to_cpu(gdp->bg_free_blocks_count));
 +              return -ENODATA;
 +      }
 +
@@ -1187,7 +1189,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      if (err)
 +              return err;
 +      
-+      handle = journal_start(EXT3_SB(e3b->bd_sb)->s_journal, 1);
++      handle = ext3_journal_start(EXT3_SB(e3b->bd_sb)->s_buddy, 1);
 +      if (IS_ERR(handle)) {
 +              err = PTR_ERR(handle);
 +              handle = NULL;
@@ -1199,7 +1201,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              goto out;
 +      grp->mgd_first_free = e3b->bd_bd->bb_first_free;
 +      grp->mgd_free = e3b->bd_bd->bb_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              grp->mgd_counters[i] = e3b->bd_bd->bb_counters[i];
 +      }
@@ -1219,16 +1221,24 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      struct super_block *sb = e3b->bd_sb;
 +      struct buffer_head *bh;
 +      int i, count = 0;
-+      
-+      memset(e3b->bd_bh->b_data, 0, sb->s_blocksize);
-+      memset(e3b->bd_bh2->b_data, 0, sb->s_blocksize);
++
++      mb_debug("generate buddy for group %d\n", e3b->bd_group);
++      memset(e3b->bd_bh->b_data, 0xff, sb->s_blocksize);
++      memset(e3b->bd_bh2->b_data, 0xff, sb->s_blocksize);
 +
 +      bh = read_block_bitmap(sb, e3b->bd_group);
 +      if (bh == NULL)
 +              return -EIO; 
 +
 +      /* mb_free_blocks will set real free */
++      e3b->bd_bd->bb_free = 0;
 +      e3b->bd_bd->bb_first_free = 1 << 15;
++      /* 
++       * if change bb_counters size, don't forget about 
++       * ext3_mb_init_backend() -bzzz
++       */
++      memset(e3b->bd_bd->bb_counters, 0,
++              sizeof(unsigned) * (sb->s_blocksize_bits + 2));
 +
 +      /* loop over the blocks, and create buddies for free ones */
 +      for (i = 0; i < sb->s_blocksize * 8; i++) {
@@ -1291,7 +1301,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              }
 +              db->d_inode->i_flags |= S_IMMUTABLE | S_NOATIME;
 +              *created = 1;
-+              printk("EXT3-fs: no buddy file, regenerate\n");
++              mb_debug("no buddy file, regenerate\n");
 +      }
 +      up(&root->i_sem);
 +      sbi->s_buddy = igrab(db->d_inode);
@@ -1304,8 +1314,10 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      len = sbi->s_groups_count * sb->s_blocksize * 2 +
 +                      buddy_offset * sb->s_blocksize;
 +      if (len != i_size_read(sbi->s_buddy)) {
-+              printk("EXT3-fs: wrong i_size (%u != %u), regenerate\n",
-+                      (unsigned) len, (unsigned) i_size_read(sbi->s_buddy));
++              if (*created == 0)
++                      printk("EXT3-fs: wrong i_size (%u != %u), regenerate\n",
++                              (unsigned) len, 
++                              (unsigned) i_size_read(sbi->s_buddy));
 +              *created = 1;
 +      }
 +
@@ -1313,14 +1325,14 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      for (i = 0; i < buddy_offset; i++) {
 +              handle = ext3_journal_start(sbi->s_buddy, MB_CREDITS);
 +              if (IS_ERR(handle)) {
-+                      printk(KERN_ERR "EXT3-fs: can't start transaction\n");
++                      printk(KERN_ERR "EXT3-fs: cant start transaction\n");
 +                      err = PTR_ERR(handle);
 +                      goto err_out;
 +              }
 +              
 +              bh = ext3_bread(handle, sbi->s_buddy, i, 1, &err);
 +              if (bh == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't getblk grp: %d\n", err);
++                      printk(KERN_ERR "EXT3-fs: cant getblk grp: %d\n", err);
 +                      goto err_out;
 +              }
 +              hdr = (struct ext3_mb_grp_header *) bh->b_data;
@@ -1328,9 +1340,11 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +                      err = ext3_journal_get_write_access(handle, bh);
 +                      if (err)
 +                              goto err_out;
++                      if (*created == 0)
++                              printk(KERN_ERR 
++                                      "EXT3-fs: invalid header 0x%x in %d,"
++                                      "regenerate\n", hdr->mh_magic, i);
 +                      *created = 1;
-+                      printk("EXT3-fs: invalid header %#x in %d regenerate\n",
-+                             hdr->mh_magic, i);
 +                      hdr->mh_magic = EXT3_MB_MAGIC_V1;
 +                      err = ext3_journal_dirty_metadata(handle, bh);
 +                      if (err)
@@ -1340,12 +1354,16 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              ext3_journal_stop(handle);
 +      }
 +
++      /* 
++       * if change bb_counters size, don't forget about ext3_mb_generate_buddy()
++       */
 +      len = sizeof(struct ext3_buddy_group_blocks);
 +      len += sizeof(unsigned) * (sb->s_blocksize_bits + 2);
 +      for (i = 0; i < sbi->s_groups_count; i++) {
++
 +              sbi->s_buddy_blocks[i] = kmalloc(len, GFP_KERNEL);
 +              if (sbi->s_buddy_blocks[i] == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't allocate buddy mem\n");
++                      printk(KERN_ERR "EXT3-fs: cant allocate mem for buddy\n");
 +                      err = -ENOMEM;
 +                      goto out2;
 +              }
@@ -1353,7 +1371,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +
 +              handle = ext3_journal_start(sbi->s_buddy, MB_CREDITS);
 +              if (IS_ERR(handle)) {
-+                      printk(KERN_ERR "EXT3-fs: can't start transaction\n");
++                      printk(KERN_ERR "EXT3-fs: cant start transaction\n");
 +                      err = PTR_ERR(handle);
 +                      goto out2;
 +              }
@@ -1362,8 +1380,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              block = buddy_offset + i * 2;
 +              bh = ext3_getblk(handle, sbi->s_buddy, block, 1, &err);
 +              if (bh == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't getblk bitmap: %d\n",
-+                             err);
++                      printk(KERN_ERR "EXT3-fs: cant getblk bitmap: %d\n", err);
 +                      goto out2;
 +              }
 +              sbi->s_buddy_blocks[i]->bb_bitmap = bh->b_blocknr;
@@ -1373,7 +1390,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              block = buddy_offset + i * 2 + 1;
 +              bh = ext3_getblk(handle, sbi->s_buddy, block, 1, &err);
 +              if (bh == NULL) {
-+                      printk(KERN_ERR "EXT3-fs: can't getblk for buddy: %d\n",+                              err);
++                      printk(KERN_ERR "EXT3-fs: cant getblk for buddy: %d\n", err);
 +                      goto out2;
 +              }
 +              sbi->s_buddy_blocks[i]->bb_buddy = bh->b_blocknr;
@@ -1736,6 +1753,19 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      if (err)
 +              goto error_return;
 +
++#ifdef AGGRESSIVE_CHECK
++      {
++              int i;
++              for (i = 0; i < count; i++)
++                      J_ASSERT(mb_test_bit(bit + i, bitmap_bh->b_data));
++      }
++#endif
++      mb_clear_bits(bitmap_bh->b_data, bit, count);
++
++      /* We dirtied the bitmap block */
++      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
++      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
++
 +      if (metadata) {
 +              /* blocks being freed are metadata. these blocks shouldn't
 +               * be used until this transaction is committed */
@@ -1745,21 +1775,18 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +              mb_free_blocks(&e3b, bit, count);
 +              ext3_unlock_group(sb, block_group);
 +      }
++
 +      spin_lock(sb_bgl_lock(sbi, block_group));
 +      gdp->bg_free_blocks_count =
 +              cpu_to_le16(le16_to_cpu(gdp->bg_free_blocks_count) + count);
 +      spin_unlock(sb_bgl_lock(sbi, block_group));
++      percpu_counter_mod(&sbi->s_freeblocks_counter, count);
 +      
 +      ext3_mb_dirty_buddy(&e3b);
 +      ext3_mb_release_desc(&e3b);
 +
-+      mb_clear_bits(bitmap_bh->b_data, bit, count);
 +      *freed = count;
 +
-+      /* We dirtied the bitmap block */
-+      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
-+      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
-+
 +      /* And the group descriptor block */
 +      BUFFER_TRACE(gd_bh, "dirtied group descriptor block");
 +      ret = ext3_journal_dirty_metadata(handle, gd_bh);
@@ -1821,6 +1848,7 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      return ret;
 +}
 +
++
 +extern void ext3_free_blocks_old(handle_t *, struct inode *,
 +                              unsigned long, unsigned long);
 +void ext3_free_blocks(handle_t *handle, struct inode * inode,
@@ -1838,19 +1866,19 @@ Index: linux-2.6.5-sles9/fs/ext3/mballoc.c
 +      return;
 +}
 +
-Index: linux-2.6.5-sles9/fs/ext3/super.c
+Index: linux-2.6.5-suse/fs/ext3/super.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/super.c     2005-02-23 01:47:15.291333736 +0300
-+++ linux-2.6.5-sles9/fs/ext3/super.c  2005-02-23 01:48:54.515249408 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/super.c      2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/super.c   2005-02-26 18:40:26.000000000 +0300
 @@ -389,6 +389,7 @@
        struct ext3_super_block *es = sbi->s_es;
        int i;
  
 +      ext3_mb_release(sb);
-       ext3_ext_release(sb);
+       ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
-@@ -540,6 +541,7 @@
+@@ -543,6 +544,7 @@
        Opt_commit, Opt_journal_update, Opt_journal_inum,
        Opt_abort, Opt_data_journal, Opt_data_ordered, Opt_data_writeback,
        Opt_ignore, Opt_barrier, Opt_iopen, Opt_noiopen, Opt_iopen_nopriv,
@@ -1858,7 +1886,7 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        Opt_err, Opt_extents, Opt_extdebug
  };
  
-@@ -587,6 +589,8 @@
+@@ -590,6 +592,8 @@
        {Opt_iopen_nopriv, "iopen_nopriv"},
        {Opt_extents, "extents"},
        {Opt_extdebug, "extdebug"},
@@ -1867,7 +1895,7 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
        {Opt_err, NULL}
  };
  
-@@ -808,6 +812,16 @@
+@@ -811,6 +815,16 @@
                case Opt_extdebug:
                        set_opt (sbi->s_mount_opt, EXTDEBUG);
                        break;
@@ -1884,20 +1912,18 @@ Index: linux-2.6.5-sles9/fs/ext3/super.c
                default:
                        printk (KERN_ERR
                                "EXT3-fs: Unrecognized mount option \"%s\" "
-@@ -1461,7 +1475,8 @@
+@@ -1464,6 +1478,7 @@
                ext3_count_dirs(sb));
  
-       ext3_ext_init(sb);
-- 
+       ext3_ext_init(sb);
 +      ext3_mb_init(sb, needs_recovery);
-+
        return 0;
  
- failed_mount3:
-Index: linux-2.6.5-sles9/fs/ext3/Makefile
+Index: linux-2.6.5-suse/fs/ext3/Makefile
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/Makefile    2005-02-23 01:02:37.405434272 +0300
-+++ linux-2.6.5-sles9/fs/ext3/Makefile 2005-02-23 01:48:54.517249104 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/Makefile     2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/Makefile  2005-02-26 18:40:26.000000000 +0300
 @@ -5,7 +5,7 @@
  obj-$(CONFIG_EXT3_FS) += ext3.o
  
@@ -1907,10 +1933,10 @@ Index: linux-2.6.5-sles9/fs/ext3/Makefile
  
  ext3-$(CONFIG_EXT3_FS_XATTR)   += xattr.o xattr_user.o xattr_trusted.o
  ext3-$(CONFIG_EXT3_FS_POSIX_ACL) += acl.o
-Index: linux-2.6.5-sles9/fs/ext3/balloc.c
+Index: linux-2.6.5-suse/fs/ext3/balloc.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/balloc.c    2004-11-03 08:36:51.000000000 +0300
-+++ linux-2.6.5-sles9/fs/ext3/balloc.c 2005-02-23 01:48:54.520248648 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/balloc.c     2005-02-02 00:55:47.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/balloc.c  2005-02-26 18:40:26.000000000 +0300
 @@ -78,7 +78,7 @@
   *
   * Return buffer_head on success or NULL in case of failure.
@@ -1938,10 +1964,10 @@ Index: linux-2.6.5-sles9/fs/ext3/balloc.c
                        unsigned long goal, int *errp)
  {
        struct buffer_head *bitmap_bh = NULL;
-Index: linux-2.6.5-sles9/fs/ext3/namei.c
+Index: linux-2.6.5-suse/fs/ext3/namei.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/namei.c     2005-02-23 01:01:46.551165296 +0300
-+++ linux-2.6.5-sles9/fs/ext3/namei.c  2005-02-23 01:48:54.523248192 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/namei.c      2005-02-26 18:40:19.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/namei.c   2005-02-26 18:40:26.000000000 +0300
 @@ -1640,7 +1640,7 @@
   * If the create succeeds, we fill in the inode information
   * with d_instantiate(). 
@@ -1951,10 +1977,10 @@ Index: linux-2.6.5-sles9/fs/ext3/namei.c
                struct nameidata *nd)
  {
        handle_t *handle; 
-Index: linux-2.6.5-sles9/fs/ext3/inode.c
+Index: linux-2.6.5-suse/fs/ext3/inode.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/inode.c     2005-02-23 01:02:37.404434424 +0300
-+++ linux-2.6.5-sles9/fs/ext3/inode.c  2005-02-23 01:48:54.529247280 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/inode.c      2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/inode.c   2005-02-26 18:40:26.000000000 +0300
 @@ -572,7 +572,7 @@
                ext3_journal_forget(handle, branch[i].bh);
        }
@@ -1973,7 +1999,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
        return err;
  }
  
-@@ -1829,7 +1829,7 @@
+@@ -1830,7 +1830,7 @@
                }
        }
  
@@ -1982,7 +2008,7 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
  }
  
  /**
-@@ -2000,7 +2000,7 @@
+@@ -2001,7 +2001,7 @@
                                ext3_journal_test_restart(handle, inode);
                        }
  
@@ -1991,10 +2017,10 @@ Index: linux-2.6.5-sles9/fs/ext3/inode.c
  
                        if (parent_bh) {
                                /*
-Index: linux-2.6.5-sles9/fs/ext3/extents.c
+Index: linux-2.6.5-suse/fs/ext3/extents.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/extents.c   2005-02-23 01:02:37.396435640 +0300
-+++ linux-2.6.5-sles9/fs/ext3/extents.c        2005-02-23 01:48:54.533246672 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/extents.c    2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/extents.c 2005-02-26 18:40:26.000000000 +0300
 @@ -774,7 +774,7 @@
                for (i = 0; i < depth; i++) {
                        if (!ablocks[i])
@@ -2036,10 +2062,10 @@ Index: linux-2.6.5-sles9/fs/ext3/extents.c
        } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
                printk("strange request: removal %lu-%lu from %u:%u\n",
                        from, to, ex->ee_block, ex->ee_len);
-Index: linux-2.6.5-sles9/fs/ext3/xattr.c
+Index: linux-2.6.5-suse/fs/ext3/xattr.c
 ===================================================================
---- linux-2.6.5-sles9.orig/fs/ext3/xattr.c     2005-02-23 01:01:52.387278072 +0300
-+++ linux-2.6.5-sles9/fs/ext3/xattr.c  2005-02-23 01:48:54.537246064 +0300
+--- linux-2.6.5-suse.orig/fs/ext3/xattr.c      2005-02-26 18:40:22.000000000 +0300
++++ linux-2.6.5-suse/fs/ext3/xattr.c   2005-02-26 18:40:26.000000000 +0300
 @@ -1366,7 +1366,7 @@
                        new_bh = sb_getblk(sb, block);
                        if (!new_bh) {
@@ -2067,10 +2093,10 @@ Index: linux-2.6.5-sles9/fs/ext3/xattr.c
                get_bh(bh);
                ext3_forget(handle, 1, inode, bh, EXT3_I(inode)->i_file_acl);
        } else {
-Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
+Index: linux-2.6.5-suse/include/linux/ext3_fs.h
 ===================================================================
---- linux-2.6.5-sles9.orig/include/linux/ext3_fs.h     2005-02-23 01:02:37.414432904 +0300
-+++ linux-2.6.5-sles9/include/linux/ext3_fs.h  2005-02-23 01:48:54.539245760 +0300
+--- linux-2.6.5-suse.orig/include/linux/ext3_fs.h      2005-02-26 18:40:25.000000000 +0300
++++ linux-2.6.5-suse/include/linux/ext3_fs.h   2005-02-26 18:40:26.000000000 +0300
 @@ -57,6 +57,14 @@
  #define ext3_debug(f, a...)   do {} while (0)
  #endif
@@ -2090,7 +2116,7 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
  #define EXT3_MOUNT_IOPEN_NOPRIV               0x80000 /* Make iopen world-readable */
  #define EXT3_MOUNT_EXTENTS            0x100000/* Extents support */
  #define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
-+#define EXT3_MOUNT_MBALLOC            0x100000/* Buddy allocation support */
++#define EXT3_MOUNT_MBALLOC            0x400000/* Buddy allocation support */
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
  #ifndef clear_opt
@@ -2141,10 +2167,10 @@ Index: linux-2.6.5-sles9/include/linux/ext3_fs.h
  #endif        /* __KERNEL__ */
  
  #define EXT3_IOC_CREATE_INUM                  _IOW('f', 5, long)
-Index: linux-2.6.5-sles9/include/linux/ext3_fs_sb.h
+Index: linux-2.6.5-suse/include/linux/ext3_fs_sb.h
 ===================================================================
---- linux-2.6.5-sles9.orig/include/linux/ext3_fs_sb.h  2005-02-23 01:01:48.242908112 +0300
-+++ linux-2.6.5-sles9/include/linux/ext3_fs_sb.h       2005-02-23 01:48:54.541245456 +0300
+--- linux-2.6.5-suse.orig/include/linux/ext3_fs_sb.h   2005-02-26 18:40:20.000000000 +0300
++++ linux-2.6.5-suse/include/linux/ext3_fs_sb.h        2005-02-26 18:40:26.000000000 +0300
 @@ -23,10 +23,30 @@
  #define EXT_INCLUDE
  #include <linux/blockgroup_lock.h>
diff --git a/lustre/kernel_patches/patches/ext3-mballoc2-2.6.7.patch b/lustre/kernel_patches/patches/ext3-mballoc2-2.6.7.patch
deleted file mode 100644 (file)
index 1c8b8d9..0000000
+++ /dev/null
@@ -1,1750 +0,0 @@
-Index: linux-2.6.7/fs/ext3/mballoc.c
-===================================================================
---- linux-2.6.7.orig/fs/ext3/mballoc.c 2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.6.7/fs/ext3/mballoc.c      2004-09-06 12:51:42.000000000 +0400
-@@ -0,0 +1,1428 @@
-+/*
-+ * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
-+ * Written by Alex Tomas <alex@clusterfs.com>
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ *
-+ * This program is distributed in the hope that it will be useful,
-+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
-+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-+ * GNU General Public License for more details.
-+ *
-+ * You should have received a copy of the GNU General Public Licens
-+ * along with this program; if not, write to the Free Software
-+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-
-+ */
-+
-+
-+/*
-+ * mballoc.c contains the multiblocks allocation routines
-+ */
-+
-+#include <linux/config.h>
-+#include <linux/time.h>
-+#include <linux/fs.h>
-+#include <linux/namei.h>
-+#include <linux/jbd.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/quotaops.h>
-+#include <linux/buffer_head.h>
-+#include <linux/module.h>
-+
-+/*
-+ * TODO:
-+ *   - do not scan from the beginning, try to remember first free block
-+ *   - mb_mark_used_* may allocate chunk right after splitting buddy
-+ *   - special flag to advice allocator to look for requested + N blocks
-+ *     this may improve interaction between extents and mballoc
-+ */
-+
-+/*
-+ * with AGRESSIVE_CHECK allocator runs consistency checks over
-+ * structures. this checks slow things down a lot
-+ */
-+#define AGGRESSIVE_CHECK__
-+
-+/*
-+ */
-+#define MB_DEBUG__
-+#ifdef MB_DEBUG
-+#define mb_debug(fmt,a...)    printk(fmt, ##a)
-+#else
-+#define mb_debug(fmt,a...)
-+#endif
-+
-+/*
-+ * where to save buddies structures beetween umount/mount (clean case only)
-+ */
-+#define EXT3_BUDDY_FILE               ".buddy"
-+
-+/*
-+ * max. number of chunks to be tracked in ext3_free_extent struct
-+ */
-+#define MB_ARR_SIZE   32
-+
-+struct ext3_allocation_context {
-+      struct super_block *ac_sb;
-+
-+      /* search goals */
-+      int ac_g_group;
-+      int ac_g_start;
-+      int ac_g_len;
-+      int ac_g_flags;
-+      
-+      /* the best found extent */
-+      int ac_b_group;
-+      int ac_b_start;
-+      int ac_b_len;
-+      
-+      /* number of iterations done. we have to track to limit searching */
-+      int ac_repeats;
-+      int ac_groups_scanned;
-+      int ac_status;
-+};
-+
-+#define AC_STATUS_CONTINUE    1
-+#define AC_STATUS_FOUND               2
-+
-+
-+struct ext3_buddy {
-+      void *bd_bitmap;
-+      void *bd_buddy;
-+      int bd_blkbits;
-+      struct buffer_head *bd_bh;
-+      struct buffer_head *bd_bh2;
-+      struct ext3_buddy_group_blocks *bd_bd;
-+      struct super_block *bd_sb;
-+};
-+
-+struct ext3_free_extent {
-+      int fe_start;
-+      int fe_len;
-+      unsigned char fe_orders[MB_ARR_SIZE];
-+      unsigned char fe_nums;
-+      unsigned char fe_back;
-+};
-+
-+#define in_range(b, first, len)       ((b) >= (first) && (b) <= (first) + (len) - 1)
-+
-+
-+int ext3_create (struct inode *, struct dentry *, int, struct nameidata *);
-+struct buffer_head * read_block_bitmap(struct super_block *, unsigned int);
-+void ext3_free_blocks_old(handle_t *, struct inode *, unsigned long, unsigned long);
-+int ext3_new_block_old(handle_t *, struct inode *, unsigned long, u32 *, u32 *, int *);
-+int ext3_mb_reserve_blocks(struct super_block *, int);
-+void ext3_mb_release_blocks(struct super_block *, int);
-+void ext3_mb_poll_new_transaction(struct super_block *, handle_t *);
-+void ext3_mb_free_committed_blocks(struct super_block *);
-+
-+#define mb_correct_addr_and_bit(bit,addr)     \
-+{                                             \
-+      if ((unsigned) addr & 1) {              \
-+              bit += 8;                       \
-+              addr--;                         \
-+      }                                       \
-+      if ((unsigned) addr & 2) {              \
-+              bit += 16;                      \
-+              addr--;                         \
-+              addr--;                         \
-+      }                                       \
-+}
-+
-+static inline int mb_test_bit(int bit, void *addr)
-+{
-+      mb_correct_addr_and_bit(bit,addr);
-+      return test_bit(bit, addr);
-+}
-+
-+static inline void mb_set_bit(int bit, void *addr)
-+{
-+      mb_correct_addr_and_bit(bit,addr);
-+      set_bit(bit, addr);
-+}
-+
-+static inline void mb_clear_bit(int bit, void *addr)
-+{
-+      mb_correct_addr_and_bit(bit,addr);
-+      clear_bit(bit, addr);
-+}
-+
-+static inline void *mb_find_buddy(struct ext3_buddy *e3b, int order, int *max)
-+{
-+      int i = 1;
-+      void *bb;
-+
-+      J_ASSERT(e3b->bd_bitmap != e3b->bd_buddy);
-+      J_ASSERT(max != NULL);
-+
-+      if (order > e3b->bd_blkbits + 1)
-+              return NULL;
-+
-+      /* at order 0 we see each particular block */
-+      *max = 1 << (e3b->bd_blkbits + 3);
-+      if (order == 0)
-+              return e3b->bd_bitmap;
-+
-+      bb = e3b->bd_buddy;
-+      *max = *max >> 1;
-+      while (i < order) {
-+              bb += 1 << (e3b->bd_blkbits - i);
-+              i++;
-+              *max = *max >> 1;
-+      }
-+      return bb;
-+}
-+
-+static int ext3_mb_load_desc(struct super_block *sb, int group,
-+                              struct ext3_buddy *e3b)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+
-+      J_ASSERT(sbi->s_buddy_blocks[group].bb_bitmap);
-+      J_ASSERT(sbi->s_buddy_blocks[group].bb_buddy);
-+
-+      /* load bitmap */
-+      e3b->bd_bh = sb_getblk(sb, sbi->s_buddy_blocks[group].bb_bitmap);
-+      if (e3b->bd_bh == NULL) {
-+              ext3_error(sb, "ext3_mb_load_desc",
-+                              "can't get block for buddy bitmap\n");
-+              goto out;
-+      }
-+      if (!buffer_uptodate(e3b->bd_bh)) {
-+              ll_rw_block(READ, 1, &e3b->bd_bh);
-+              wait_on_buffer(e3b->bd_bh);
-+      }
-+      J_ASSERT(buffer_uptodate(e3b->bd_bh));
-+
-+      /* load buddy */
-+      e3b->bd_bh2 = sb_getblk(sb, sbi->s_buddy_blocks[group].bb_buddy);
-+      if (e3b->bd_bh2 == NULL) {
-+              ext3_error(sb, "ext3_mb_load_desc",
-+                              "can't get block for buddy bitmap\n");
-+              goto out;
-+      }
-+      if (!buffer_uptodate(e3b->bd_bh2)) {
-+              ll_rw_block(READ, 1, &e3b->bd_bh2);
-+              wait_on_buffer(e3b->bd_bh2);
-+      }
-+      J_ASSERT(buffer_uptodate(e3b->bd_bh2));
-+
-+      e3b->bd_bitmap = e3b->bd_bh->b_data;
-+      e3b->bd_buddy = e3b->bd_bh2->b_data;
-+      e3b->bd_blkbits = sb->s_blocksize_bits;
-+      e3b->bd_bd = sbi->s_buddy_blocks + group;
-+      e3b->bd_sb = sb;
-+
-+      return 0;
-+out:
-+      brelse(e3b->bd_bh);
-+      brelse(e3b->bd_bh2);
-+      e3b->bd_bh = NULL;
-+      e3b->bd_bh2 = NULL;
-+      return -EIO;
-+}
-+
-+static void ext3_mb_dirty_buddy(struct ext3_buddy *e3b)
-+{
-+      mark_buffer_dirty(e3b->bd_bh);
-+      mark_buffer_dirty(e3b->bd_bh2);
-+}
-+
-+static void ext3_mb_release_desc(struct ext3_buddy *e3b)
-+{
-+      brelse(e3b->bd_bh);
-+      brelse(e3b->bd_bh2);
-+}
-+
-+#ifdef AGGRESSIVE_CHECK
-+static void mb_check_buddy(struct ext3_buddy *e3b)
-+{
-+      int order = e3b->bd_blkbits + 1;
-+      int max, max2, i, j, k, count;
-+      void *buddy, *buddy2;
-+
-+      if (!test_opt(e3b->bd_sb, MBALLOC))
-+              return;
-+
-+      while (order > 1) {
-+              buddy = mb_find_buddy(e3b, order, &max);
-+              J_ASSERT(buddy);
-+              buddy2 = mb_find_buddy(e3b, order - 1, &max2);
-+              J_ASSERT(buddy2);
-+              J_ASSERT(buddy != buddy2);
-+              J_ASSERT(max * 2 == max2);
-+
-+              count = 0;
-+              for (i = 0; i < max; i++) {
-+
-+                      if (!mb_test_bit(i, buddy)) {
-+                              /* only single bit in buddy2 may be 1 */
-+                              if (mb_test_bit(i << 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit((i<<1)+1, buddy2));
-+                              else if (mb_test_bit((i << 1) + 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
-+                              continue;
-+                      }
-+
-+                      /* both bits in buddy2 must be 0 */
-+                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
-+                      J_ASSERT(!mb_test_bit((i << 1) + 1, buddy2));
-+
-+                      for (j = 0; j < (1 << order); j++) {
-+                              k = (i * (1 << order)) + j;
-+                              J_ASSERT(mb_test_bit(k, e3b->bd_bitmap));
-+                      }
-+                      count++;
-+              }
-+              J_ASSERT(e3b->bd_bd->bb_counters[order] == count);
-+              order--;
-+      }
-+
-+      buddy = mb_find_buddy(e3b, 0, &max);
-+      for (i = 0; i < max; i++) {
-+              if (mb_test_bit(i, buddy))
-+                      continue;
-+              /* check used bits only */
-+              for (j = 0; j < e3b->bd_blkbits + 1; j++) {
-+                      buddy2 = mb_find_buddy(e3b, j, &max2);
-+                      k = i >> j;
-+                      J_ASSERT(k < max2);
-+                      J_ASSERT(!mb_test_bit(k, buddy2));
-+              }
-+      }
-+}
-+#else
-+#define mb_check_buddy(e3b)
-+#endif
-+
-+static inline void
-+ext3_lock_group(struct super_block *sb, int group)
-+{
-+      spin_lock(&EXT3_SB(sb)->s_buddy_blocks[group].bb_lock);
-+}
-+
-+static inline void
-+ext3_unlock_group(struct super_block *sb, int group)
-+{
-+      spin_unlock(&EXT3_SB(sb)->s_buddy_blocks[group].bb_lock);
-+}
-+
-+static int mb_find_order_for_block(struct ext3_buddy *e3b, int block)
-+{
-+      int order = 1;
-+      void *bb;
-+
-+      J_ASSERT(e3b->bd_bitmap != e3b->bd_buddy);
-+      J_ASSERT(block < (1 << (e3b->bd_blkbits + 3)));
-+
-+      bb = e3b->bd_buddy;
-+      while (order <= e3b->bd_blkbits + 1) {
-+              block = block >> 1;
-+              if (mb_test_bit(block, bb)) {
-+                      /* this block is part of buddy of order 'order' */
-+                      return order;
-+              }
-+              bb += 1 << (e3b->bd_blkbits - order);
-+              order++;
-+      }
-+      return 0;
-+}
-+
-+static inline void mb_clear_bits(void *bm, int cur, int len)
-+{
-+      __u32 *addr;
-+
-+      len = cur + len;
-+      while (cur < len) {
-+              if ((cur & 31) == 0 && (len - cur) >= 32) {
-+                      /* fast path: clear whole word at once */
-+                      addr = bm + (cur >> 3);
-+                      *addr = 0;
-+                      cur += 32;
-+                      continue;
-+              }
-+              mb_clear_bit(cur, bm);
-+              cur++;
-+      }
-+}
-+
-+static inline void mb_set_bits(void *bm, int cur, int len)
-+{
-+      __u32 *addr;
-+
-+      len = cur + len;
-+      while (cur < len) {
-+              if ((cur & 31) == 0 && (len - cur) >= 32) {
-+                      /* fast path: clear whole word at once */
-+                      addr = bm + (cur >> 3);
-+                      *addr = 0xffffffff;
-+                      cur += 32;
-+                      continue;
-+              }
-+              mb_set_bit(cur, bm);
-+              cur++;
-+      }
-+}
-+
-+static int mb_free_blocks(struct ext3_buddy *e3b, int first, int count)
-+{
-+      int block, max, order;
-+      void *buddy, *buddy2;
-+
-+      mb_check_buddy(e3b);
-+      while (count-- > 0) {
-+              block = first++;
-+              order = 0;
-+
-+              J_ASSERT(!mb_test_bit(block, e3b->bd_bitmap));
-+              mb_set_bit(block, e3b->bd_bitmap);
-+              e3b->bd_bd->bb_counters[order]++;
-+
-+              /* start of the buddy */
-+              buddy = mb_find_buddy(e3b, order, &max);
-+
-+              do {
-+                      block &= ~1UL;
-+                      if (!mb_test_bit(block, buddy) ||
-+                                      !mb_test_bit(block + 1, buddy))
-+                              break;
-+
-+                      /* both the buddies are free, try to coalesce them */
-+                      buddy2 = mb_find_buddy(e3b, order + 1, &max);
-+
-+                      if (!buddy2)
-+                              break;
-+
-+                      if (order > 0) {
-+                              /* for special purposes, we don't clear
-+                               * free bits in bitmap */
-+                              mb_clear_bit(block, buddy);
-+                              mb_clear_bit(block + 1, buddy);
-+                      }
-+                      e3b->bd_bd->bb_counters[order]--;
-+                      e3b->bd_bd->bb_counters[order]--;
-+
-+                      block = block >> 1;
-+                      order++;
-+                      e3b->bd_bd->bb_counters[order]++;
-+
-+                      mb_set_bit(block, buddy2);
-+                      buddy = buddy2;
-+              } while (1);
-+      }
-+      mb_check_buddy(e3b);
-+
-+      return 0;
-+}
-+
-+/*
-+ * returns 1 if out extent is enough to fill needed space
-+ */
-+int mb_make_backward_extent(struct ext3_free_extent *in,
-+                              struct ext3_free_extent *out, int needed)
-+{
-+      int i;
-+
-+      J_ASSERT(in);
-+      J_ASSERT(out);
-+      J_ASSERT(in->fe_nums < MB_ARR_SIZE);
-+
-+      out->fe_len = 0;
-+      out->fe_start = in->fe_start + in->fe_len;
-+      out->fe_nums = 0;
-+
-+      /* for single-chunk extent we need not back order
-+       * also, if an extent doesn't fill needed space
-+       * then it makes no sense to try back order becase
-+       * if we select this extent then it'll be use as is */
-+      if (in->fe_nums < 2 || in->fe_len < needed)
-+              return 0;
-+
-+      i = in->fe_nums - 1;
-+      while (i >= 0 && out->fe_len < needed) {
-+              out->fe_len += (1 << in->fe_orders[i]);
-+              out->fe_start -= (1 << in->fe_orders[i]);
-+              i--;
-+      }
-+      /* FIXME: in some situation fe_orders may be too small to hold
-+       * all the buddies */
-+      J_ASSERT(out->fe_len >= needed);
-+      
-+      for (i++; i < in->fe_nums; i++)
-+              out->fe_orders[out->fe_nums++] = in->fe_orders[i];
-+      J_ASSERT(out->fe_nums < MB_ARR_SIZE);
-+      out->fe_back = 1;
-+
-+      return 1;
-+}
-+
-+int mb_find_extent(struct ext3_buddy *e3b, int order, int block,
-+                      int needed, struct ext3_free_extent *ex)
-+{
-+      int space = needed;
-+      int next, max, ord;
-+      void *buddy;
-+
-+      J_ASSERT(ex != NULL);
-+
-+      ex->fe_nums = 0;
-+      ex->fe_len = 0;
-+      
-+      buddy = mb_find_buddy(e3b, order, &max);
-+      J_ASSERT(buddy);
-+      J_ASSERT(block < max);
-+      if (!mb_test_bit(block, buddy))
-+              goto nofree;
-+
-+      if (order == 0) {
-+              /* find actual order */
-+              order = mb_find_order_for_block(e3b, block);
-+              block = block >> order;
-+      }
-+
-+      ex->fe_orders[ex->fe_nums++] = order;
-+      ex->fe_len = 1 << order;
-+      ex->fe_start = block << order;
-+      ex->fe_back = 0;
-+
-+      while ((space = space - (1 << order)) > 0) {
-+
-+              buddy = mb_find_buddy(e3b, order, &max);
-+              J_ASSERT(buddy);
-+
-+              if (block + 1 >= max)
-+                      break;
-+
-+              next = (block + 1) * (1 << order);
-+              if (!mb_test_bit(next, e3b->bd_bitmap))
-+                      break;
-+
-+              ord = mb_find_order_for_block(e3b, next);
-+
-+              if ((1 << ord) >= needed) {
-+                      /* we dont want to coalesce with self-enough buddies */
-+                      break;
-+              }
-+              order = ord;
-+              block = next >> order;
-+              ex->fe_len += 1 << order;
-+
-+              if (ex->fe_nums < MB_ARR_SIZE)
-+                      ex->fe_orders[ex->fe_nums++] = order;
-+      }
-+
-+nofree:
-+      J_ASSERT(ex->fe_start + ex->fe_len <= (1 << (e3b->bd_blkbits + 3)));
-+      return ex->fe_len;
-+}
-+
-+static int mb_mark_used_backward(struct ext3_buddy *e3b,
-+                                      struct ext3_free_extent *ex, int len)
-+{
-+      int start = ex->fe_start, len0 = len;
-+      int ord, mlen, max, cur;
-+      void *buddy;
-+
-+      start = ex->fe_start + ex->fe_len - 1;
-+      while (len) {
-+              ord = mb_find_order_for_block(e3b, start);
-+              if (((start >> ord) << ord) == (start - (1 << ord) + 1) &&
-+                              len >= (1 << ord)) {
-+                      /* the whole chunk may be allocated at once! */
-+                      mlen = 1 << ord;
-+                      buddy = mb_find_buddy(e3b, ord, &max);
-+                      J_ASSERT((start >> ord) < max);
-+                      mb_clear_bit(start >> ord, buddy);
-+                      e3b->bd_bd->bb_counters[ord]--;
-+                      start -= mlen;
-+                      len -= mlen;
-+                      J_ASSERT(len >= 0);
-+                      J_ASSERT(start >= 0);
-+                      continue;
-+              }
-+
-+              /* we have to split large buddy */
-+              J_ASSERT(ord > 0);
-+              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_clear_bit(start >> ord, buddy);
-+              e3b->bd_bd->bb_counters[ord]--;
-+
-+              ord--;
-+              cur = (start >> ord) & ~1U;
-+              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_set_bit(cur, buddy);
-+              mb_set_bit(cur + 1, buddy);
-+              e3b->bd_bd->bb_counters[ord]++;
-+              e3b->bd_bd->bb_counters[ord]++;
-+      }
-+
-+      /* now drop all the bits in bitmap */
-+      mb_clear_bits(e3b->bd_bitmap, ex->fe_start + ex->fe_len - len0, len0);
-+
-+      mb_check_buddy(e3b);
-+
-+      return 0;
-+}
-+
-+static int mb_mark_used_forward(struct ext3_buddy *e3b,
-+                              struct ext3_free_extent *ex, int len)
-+{
-+      int start = ex->fe_start, len0 = len;
-+      int ord, mlen, max, cur;
-+      void *buddy;
-+
-+      while (len) {
-+              ord = mb_find_order_for_block(e3b, start);
-+
-+              if (((start >> ord) << ord) == start && len >= (1 << ord)) {
-+                      /* the whole chunk may be allocated at once! */
-+                      mlen = 1 << ord;
-+                      buddy = mb_find_buddy(e3b, ord, &max);
-+                      J_ASSERT((start >> ord) < max);
-+                      mb_clear_bit(start >> ord, buddy);
-+                      e3b->bd_bd->bb_counters[ord]--;
-+                      start += mlen;
-+                      len -= mlen;
-+                      J_ASSERT(len >= 0);
-+                      continue;
-+              }
-+
-+              /* we have to split large buddy */
-+              J_ASSERT(ord > 0);
-+              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_clear_bit(start >> ord, buddy);
-+              e3b->bd_bd->bb_counters[ord]--;
-+
-+              ord--;
-+              cur = (start >> ord) & ~1U;
-+              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_set_bit(cur, buddy);
-+              mb_set_bit(cur + 1, buddy);
-+              e3b->bd_bd->bb_counters[ord]++;
-+              e3b->bd_bd->bb_counters[ord]++;
-+      }
-+
-+      /* now drop all the bits in bitmap */
-+      mb_clear_bits(e3b->bd_bitmap, ex->fe_start, len0);
-+
-+      mb_check_buddy(e3b);
-+
-+      return 0;
-+}
-+
-+int inline mb_mark_used(struct ext3_buddy *e3b,
-+                      struct ext3_free_extent *ex, int len)
-+{
-+      int err;
-+
-+      J_ASSERT(ex);
-+      if (ex->fe_back == 0)
-+              err = mb_mark_used_forward(e3b, ex, len);
-+      else
-+              err = mb_mark_used_backward(e3b, ex, len);
-+      return err;
-+}
-+
-+int ext3_mb_new_in_group(struct ext3_allocation_context *ac,
-+                              struct ext3_buddy *e3b, int group)
-+{
-+      struct super_block *sb = ac->ac_sb;
-+      int err, gorder, max, i;
-+      struct ext3_free_extent curex;
-+
-+      /* let's know order of allocation */
-+      gorder = 0;
-+      while (ac->ac_g_len > (1 << gorder))
-+              gorder++;
-+
-+      if ((ac->ac_g_flags & 1) && ac->ac_g_group == group) {
-+              /* someone asks for space at this specified block
-+               * probably he wants to merge it into existing extent */
-+              if (mb_test_bit(ac->ac_g_start, e3b->bd_bitmap)) {
-+                      /* good. at least one block is free */
-+                      max = mb_find_extent(e3b, 0, ac->ac_g_start,
-+                                              ac->ac_g_len, &curex);
-+                      max = min(curex.fe_len, ac->ac_g_len);
-+                      mb_mark_used(e3b, &curex, max);
-+                      
-+                      ac->ac_b_group = group;
-+                      ac->ac_b_start = curex.fe_start;
-+                      ac->ac_b_len = max;
-+                      ac->ac_status = AC_STATUS_FOUND;
-+                      err = 0;
-+                      goto out;
-+              }
-+              /* don't try to find goal anymore */
-+              ac->ac_g_flags &= ~1;
-+      }
-+
-+      i = 0;
-+      while (1) {
-+              i = find_next_bit(e3b->bd_bitmap, sb->s_blocksize * 8, i);
-+              if (i >= sb->s_blocksize * 8)
-+                      break;
-+
-+              max = mb_find_extent(e3b, 0, i, ac->ac_g_len, &curex);
-+              if (max >= ac->ac_g_len) {
-+                      max = min(curex.fe_len, ac->ac_g_len);
-+                      mb_mark_used(e3b, &curex, max);
-+                      
-+                      ac->ac_b_group = group;
-+                      ac->ac_b_start = curex.fe_start;
-+                      ac->ac_b_len = max;
-+                      ac->ac_status = AC_STATUS_FOUND;
-+                      break;
-+              }
-+              i += max;
-+      }
-+
-+      return 0;
-+
-+out:
-+      return err;
-+}
-+
-+int mb_good_group(struct ext3_allocation_context *ac, int group, int cr)
-+{
-+      struct ext3_group_desc *gdp;
-+      int free_blocks;
-+
-+      gdp = ext3_get_group_desc(ac->ac_sb, group, NULL);
-+      if (!gdp)
-+              return 0;
-+      free_blocks = le16_to_cpu(gdp->bg_free_blocks_count);
-+      if (free_blocks == 0)
-+              return 0;
-+
-+      /* someone wants this block very much */
-+      if ((ac->ac_g_flags & 1) && ac->ac_g_group == group)
-+              return 1;
-+
-+      /* FIXME: I'd like to take fragmentation into account here */
-+      if (cr == 0) {
-+              if (free_blocks >= ac->ac_g_len >> 1)
-+                      return 1;
-+      } else if (cr == 1) {
-+              if (free_blocks >= ac->ac_g_len >> 2)
-+                      return 1;
-+      } else if (cr == 2) {
-+              return 1;
-+      } else {
-+              BUG();
-+      }
-+      return 0;
-+}
-+
-+int ext3_mb_new_blocks(handle_t *handle, struct inode *inode,
-+                      unsigned long goal, int *len, int flags, int *errp)
-+{
-+      struct buffer_head *bitmap_bh = NULL;
-+      struct ext3_allocation_context ac;
-+      int i, group, block, cr, err = 0;
-+      struct ext3_group_desc *gdp;
-+      struct ext3_super_block *es;
-+      struct buffer_head *gdp_bh;
-+      struct ext3_sb_info *sbi;
-+      struct super_block *sb;
-+      struct ext3_buddy e3b;
-+
-+      J_ASSERT(len != NULL);
-+      J_ASSERT(*len > 0);
-+
-+      sb = inode->i_sb;
-+      if (!sb) {
-+              printk("ext3_mb_new_nblocks: nonexistent device");
-+              return 0;
-+      }
-+
-+      if (!test_opt(sb, MBALLOC)) {
-+              static int ext3_mballoc_warning = 0;
-+              if (ext3_mballoc_warning == 0) {
-+                      printk(KERN_ERR "EXT3-fs: multiblock request with "
-+                              "mballoc disabled!\n");
-+                      ext3_mballoc_warning++;
-+              }
-+              *len = 1;
-+              err = ext3_new_block_old(handle, inode, goal, NULL,NULL, errp);
-+              return err;
-+      }
-+
-+      ext3_mb_poll_new_transaction(sb, handle);
-+
-+      sbi = EXT3_SB(sb);
-+      es = EXT3_SB(sb)->s_es;
-+
-+      if (!(flags & 2)) {
-+              /* someone asks for non-reserved blocks */
-+              BUG_ON(*len > 1);
-+              err = ext3_mb_reserve_blocks(sb, 1);
-+              if (err) {
-+                      *errp = err;
-+                      return 0;
-+              }
-+      }
-+
-+      /*
-+       * Check quota for allocation of this blocks.
-+       */
-+      while (*len && DQUOT_ALLOC_BLOCK(inode, *len))
-+              *len -= 1;
-+      if (*len == 0) {
-+              *errp = -EDQUOT;
-+              block = 0;
-+              goto out;
-+      }
-+
-+      /* start searching from the goal */
-+      if (goal < le32_to_cpu(es->s_first_data_block) ||
-+          goal >= le32_to_cpu(es->s_blocks_count))
-+              goal = le32_to_cpu(es->s_first_data_block);
-+      group = (goal - le32_to_cpu(es->s_first_data_block)) /
-+                      EXT3_BLOCKS_PER_GROUP(sb);
-+      block = ((goal - le32_to_cpu(es->s_first_data_block)) %
-+                      EXT3_BLOCKS_PER_GROUP(sb));
-+
-+      /* set up allocation goals */
-+      ac.ac_b_group = ac.ac_b_start = ac.ac_b_len = 0;
-+      ac.ac_status = 0;
-+      ac.ac_groups_scanned = 0;
-+      ac.ac_sb = inode->i_sb;
-+      ac.ac_g_group = group;
-+      ac.ac_g_start = block;
-+      ac.ac_g_len = *len;
-+      ac.ac_g_flags = flags;
-+
-+      /* loop over the groups */
-+      for (cr = 0; cr < 3 && ac.ac_status != AC_STATUS_FOUND; cr++) {
-+              for (i = 0; i < EXT3_SB(sb)->s_groups_count; group++, i++) {
-+                      if (group == EXT3_SB(sb)->s_groups_count)
-+                              group = 0;
-+
-+                      /* check is group good for our criteries */
-+                      if (!mb_good_group(&ac, group, cr))
-+                              continue;
-+
-+                      err = ext3_mb_load_desc(ac.ac_sb, group, &e3b);
-+                      if (err)
-+                              goto out_err;
-+
-+                      ext3_lock_group(sb, group);
-+                      if (!mb_good_group(&ac, group, cr)) {
-+                              /* someone did allocation from this group */
-+                              ext3_unlock_group(sb, group);
-+                              ext3_mb_release_desc(&e3b);
-+                              continue;
-+                      }
-+
-+                      err = ext3_mb_new_in_group(&ac, &e3b, group);
-+                      ext3_unlock_group(sb, group);
-+                      if (ac.ac_status == AC_STATUS_FOUND)
-+                              ext3_mb_dirty_buddy(&e3b);
-+                      ext3_mb_release_desc(&e3b);
-+                      if (err)
-+                              goto out_err;
-+                      if (ac.ac_status == AC_STATUS_FOUND)
-+                              break;
-+              }
-+      }
-+
-+      if (ac.ac_status != AC_STATUS_FOUND) {
-+              /* unfortunately, we can't satisfy this request */
-+              J_ASSERT(ac.ac_b_len == 0);
-+              DQUOT_FREE_BLOCK(inode, *len);
-+              *errp = -ENOSPC;
-+              block = 0;
-+              goto out;
-+      }
-+
-+      /* good news - free block(s) have been found. now it's time
-+       * to mark block(s) in good old journaled bitmap */
-+      block = ac.ac_b_group * EXT3_BLOCKS_PER_GROUP(sb)
-+                      + ac.ac_b_start + le32_to_cpu(es->s_first_data_block);
-+
-+      /* we made a desicion, now mark found blocks in good old
-+       * bitmap to be journaled */
-+
-+      ext3_debug("using block group %d(%d)\n",
-+                      ac.ac_b_group.group, gdp->bg_free_blocks_count);
-+
-+      bitmap_bh = read_block_bitmap(sb, ac.ac_b_group);
-+      if (!bitmap_bh) {
-+              *errp = -EIO;
-+              goto out_err;
-+      }
-+
-+      err = ext3_journal_get_write_access(handle, bitmap_bh);
-+      if (err) {
-+              *errp = err;
-+              goto out_err;
-+      }
-+
-+      gdp = ext3_get_group_desc(sb, ac.ac_b_group, &gdp_bh);
-+      if (!gdp) {
-+              *errp = -EIO;
-+              goto out_err;
-+      }
-+      
-+      err = ext3_journal_get_write_access(handle, gdp_bh);
-+      if (err)
-+              goto out_err;
-+
-+      block = ac.ac_b_start + ac.ac_b_group * EXT3_BLOCKS_PER_GROUP(sb)
-+                              + le32_to_cpu(es->s_first_data_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),
-+                    EXT3_SB(sb)->s_itb_per_group))
-+              ext3_error(sb, "ext3_new_block",
-+                          "Allocating block in system zone - "
-+                          "block = %u", block);
-+#if 0
-+      for (i = 0; i < ac.ac_b_len; i++)
-+              J_ASSERT(!mb_test_bit(ac.ac_b_start + i, bitmap_bh->b_data));
-+#endif
-+      mb_set_bits(bitmap_bh->b_data, ac.ac_b_start, ac.ac_b_len);
-+
-+      ext3_lock_group(sb, ac.ac_b_group);
-+      gdp->bg_free_blocks_count =
-+                      cpu_to_le16(le16_to_cpu(gdp->bg_free_blocks_count) - 
-+                                      ac.ac_b_len);
-+      ext3_unlock_group(sb, ac.ac_b_group);
-+      percpu_counter_mod(&sbi->s_freeblocks_counter, -ac.ac_b_len);
-+
-+      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
-+      if (err)
-+              goto out_err;
-+      err = ext3_journal_dirty_metadata(handle, gdp_bh);
-+      if (err)
-+              goto out_err;
-+
-+      sb->s_dirt = 1;
-+      *errp = 0;
-+      brelse(bitmap_bh);
-+
-+      /* drop non-allocated, but dquote'd blocks */
-+      J_ASSERT(*len >= ac.ac_b_len);
-+      DQUOT_FREE_BLOCK(inode, *len - ac.ac_b_len);
-+
-+      *len = ac.ac_b_len;
-+      J_ASSERT(block != 0);
-+      goto out;
-+
-+out_err:
-+      /* if we've already allocated something, roll it back */
-+      if (ac.ac_status == AC_STATUS_FOUND) {
-+              /* FIXME: free blocks here */
-+      }
-+
-+      DQUOT_FREE_BLOCK(inode, *len);
-+      brelse(bitmap_bh);
-+      *errp = err;
-+      block = 0;
-+out:
-+      if (!(flags & 2)) {
-+              /* block wasn't reserved before and we reserved it
-+               * at the beginning of allocation. it doesn't matter
-+               * whether we allocated anything or we failed: time
-+               * to release reservation. NOTE: because I expect
-+               * any multiblock request from delayed allocation
-+               * path only, here is single block always */
-+              ext3_mb_release_blocks(sb, 1);
-+      }
-+      return block;
-+}
-+
-+int ext3_mb_generate_buddy(struct super_block *sb, int group)
-+{
-+      struct buffer_head *bh;
-+      int i, err, count = 0;
-+      struct ext3_buddy e3b;
-+      
-+      err = ext3_mb_load_desc(sb, group, &e3b);
-+      if (err)
-+              goto out;
-+      memset(e3b.bd_bh->b_data, 0, sb->s_blocksize);
-+      memset(e3b.bd_bh2->b_data, 0, sb->s_blocksize);
-+
-+      bh = read_block_bitmap(sb, group);
-+      if (bh == NULL) {
-+              err = -EIO; 
-+              goto out2;
-+      }
-+
-+      /* loop over the blocks, nad create buddies for free ones */
-+      for (i = 0; i < sb->s_blocksize * 8; i++) {
-+              if (!mb_test_bit(i, (void *) bh->b_data)) {
-+                      mb_free_blocks(&e3b, i, 1);
-+                      count++;
-+              }
-+      }
-+      brelse(bh);
-+      mb_check_buddy(&e3b);
-+      ext3_mb_dirty_buddy(&e3b);
-+
-+out2:
-+      ext3_mb_release_desc(&e3b);
-+out:
-+      return err;
-+}
-+
-+EXPORT_SYMBOL(ext3_mb_new_blocks);
-+
-+#define MB_CREDITS    \
-+      (EXT3_DATA_TRANS_BLOCKS + 3 + EXT3_INDEX_EXTRA_TRANS_BLOCKS +   \
-+              2 * EXT3_QUOTA_INIT_BLOCKS)
-+
-+int ext3_mb_init_backend(struct super_block *sb)
-+{
-+      struct inode *root = sb->s_root->d_inode;
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      struct dentry *db;
-+      tid_t target;
-+      int err, i;
-+
-+      sbi->s_buddy_blocks = kmalloc(sizeof(struct ext3_buddy_group_blocks) *
-+                                      sbi->s_groups_count, GFP_KERNEL);
-+      if (sbi->s_buddy_blocks == NULL) {
-+              printk("can't allocate mem for buddy maps\n");
-+              return -ENOMEM;
-+      }
-+      memset(sbi->s_buddy_blocks, 0,
-+              sizeof(struct ext3_buddy_group_blocks) * sbi->s_groups_count);
-+      sbi->s_buddy = NULL;
-+
-+      down(&root->i_sem);
-+      db = lookup_one_len(EXT3_BUDDY_FILE, sb->s_root,
-+                              strlen(EXT3_BUDDY_FILE));
-+      if (IS_ERR(db)) {
-+              err = PTR_ERR(db);
-+              printk("can't lookup buddy file: %d\n", err);
-+              goto out;
-+      }
-+
-+      if (db->d_inode != NULL) {
-+              sbi->s_buddy = igrab(db->d_inode);
-+              goto map;
-+      }
-+
-+      err = ext3_create(root, db, S_IFREG, NULL);
-+      if (err) {
-+              printk("error while creation buddy file: %d\n", err);
-+      } else {
-+              sbi->s_buddy = igrab(db->d_inode);
-+      }
-+
-+map:
-+      for (i = 0; i < sbi->s_groups_count; i++) {
-+              struct buffer_head *bh = NULL;
-+              handle_t *handle;
-+
-+              handle = ext3_journal_start(sbi->s_buddy, MB_CREDITS);
-+              if (IS_ERR(handle)) {
-+                      err = PTR_ERR(handle);
-+                      goto out2;
-+              }
-+              
-+              /* allocate block for bitmap */
-+              bh = ext3_getblk(handle, sbi->s_buddy, i * 2, 1, &err);
-+              if (bh == NULL) {
-+                      printk("can't get block for buddy bitmap: %d\n", err);
-+                      goto out2;
-+              }
-+              sbi->s_buddy_blocks[i].bb_bitmap = bh->b_blocknr;
-+              brelse(bh);
-+
-+              /* allocate block for buddy */
-+              bh = ext3_getblk(handle, sbi->s_buddy, i * 2 + 1, 1, &err);
-+              if (bh == NULL) {
-+                      printk("can't get block for buddy: %d\n", err);
-+                      goto out2;
-+              }
-+              sbi->s_buddy_blocks[i].bb_buddy = bh->b_blocknr;
-+              brelse(bh);
-+              ext3_journal_stop(handle);
-+              spin_lock_init(&sbi->s_buddy_blocks[i].bb_lock);
-+              sbi->s_buddy_blocks[i].bb_md_cur = NULL;
-+              sbi->s_buddy_blocks[i].bb_tid = 0;
-+      }
-+
-+      if (journal_start_commit(sbi->s_journal, &target))
-+              log_wait_commit(sbi->s_journal, target);
-+
-+out2:
-+      dput(db);
-+out:
-+      up(&root->i_sem);
-+      return err;
-+}
-+
-+int ext3_mb_release(struct super_block *sb)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      
-+      if (!test_opt(sb, MBALLOC))
-+              return 0;
-+
-+      /* release freed, non-committed blocks */
-+      spin_lock(&sbi->s_md_lock);
-+      list_splice_init(&sbi->s_closed_transaction,
-+                      &sbi->s_committed_transaction);
-+      list_splice_init(&sbi->s_active_transaction,
-+                      &sbi->s_committed_transaction);
-+      spin_unlock(&sbi->s_md_lock);
-+      ext3_mb_free_committed_blocks(sb);
-+
-+      if (sbi->s_buddy_blocks)
-+              kfree(sbi->s_buddy_blocks);
-+      if (sbi->s_buddy)
-+              iput(sbi->s_buddy);
-+      if (sbi->s_blocks_reserved)
-+              printk("ext3-fs: %ld blocks being reserved at umount!\n",
-+                              sbi->s_blocks_reserved);
-+      return 0;
-+}
-+
-+int ext3_mb_init(struct super_block *sb)
-+{
-+      struct ext3_super_block *es;
-+      int i;
-+
-+      if (!test_opt(sb, MBALLOC))
-+              return 0;
-+
-+      /* init file for buddy data */
-+      clear_opt(EXT3_SB(sb)->s_mount_opt, MBALLOC);
-+      ext3_mb_init_backend(sb);
-+
-+      es = EXT3_SB(sb)->s_es;
-+      for (i = 0; i < EXT3_SB(sb)->s_groups_count; i++)
-+              ext3_mb_generate_buddy(sb, i);
-+      spin_lock_init(&EXT3_SB(sb)->s_reserve_lock);
-+      spin_lock_init(&EXT3_SB(sb)->s_md_lock);
-+      INIT_LIST_HEAD(&EXT3_SB(sb)->s_active_transaction);
-+      INIT_LIST_HEAD(&EXT3_SB(sb)->s_closed_transaction);
-+      INIT_LIST_HEAD(&EXT3_SB(sb)->s_committed_transaction);
-+      set_opt(EXT3_SB(sb)->s_mount_opt, MBALLOC);
-+      printk("EXT3-fs: mballoc enabled\n");
-+      return 0;
-+}
-+
-+void ext3_mb_free_committed_blocks(struct super_block *sb)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      int err, i, count = 0, count2 = 0;
-+      struct ext3_free_metadata *md;
-+      struct ext3_buddy e3b;
-+
-+      if (list_empty(&sbi->s_committed_transaction))
-+              return;
-+
-+      /* there is committed blocks to be freed yet */
-+      do {
-+              /* get next array of blocks */
-+              md = NULL;
-+              spin_lock(&sbi->s_md_lock);
-+              if (!list_empty(&sbi->s_committed_transaction)) {
-+                      md = list_entry(sbi->s_committed_transaction.next,
-+                                      struct ext3_free_metadata, list);
-+                      list_del(&md->list);
-+              }
-+              spin_unlock(&sbi->s_md_lock);
-+
-+              if (md == NULL)
-+                      break;
-+
-+              mb_debug("gonna free %u blocks in group %u (0x%p):",
-+                              md->num, md->group, md);
-+
-+              err = ext3_mb_load_desc(sb, md->group, &e3b);
-+              BUG_ON(err != 0);
-+
-+              /* there are blocks to put in buddy to make them really free */
-+              count += md->num;
-+              count2++;
-+              ext3_lock_group(sb, md->group);
-+              for (i = 0; i < md->num; i++) {
-+                      mb_debug(" %u", md->blocks[i]);
-+                      mb_free_blocks(&e3b, md->blocks[i], 1);
-+              }
-+              mb_debug("\n");
-+              ext3_unlock_group(sb, md->group);
-+
-+              kfree(md);
-+              ext3_mb_dirty_buddy(&e3b);
-+              ext3_mb_release_desc(&e3b);
-+
-+      } while (md);
-+      mb_debug("freed %u blocks in %u structures\n", count, count2);
-+}
-+
-+void ext3_mb_poll_new_transaction(struct super_block *sb, handle_t *handle)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+
-+      if (sbi->s_last_transaction == handle->h_transaction->t_tid)
-+              return;
-+
-+      /* new transaction! time to close last one and free blocks for
-+       * committed transaction. we know that only transaction can be
-+       * active, so previos transaction can be being logged and we
-+       * know that transaction before previous is known to be alreade
-+       * logged. this means that now we may free blocks freed in all
-+       * transactions before previous one. hope I'm clear enough ... */
-+
-+      spin_lock(&sbi->s_md_lock);
-+      if (sbi->s_last_transaction != handle->h_transaction->t_tid) {
-+              mb_debug("new transaction %lu, old %lu\n",
-+                              (unsigned long) handle->h_transaction->t_tid,
-+                              (unsigned long) sbi->s_last_transaction);
-+              list_splice_init(&sbi->s_closed_transaction,
-+                                      &sbi->s_committed_transaction);
-+              list_splice_init(&sbi->s_active_transaction,
-+                                      &sbi->s_closed_transaction);
-+              sbi->s_last_transaction = handle->h_transaction->t_tid;
-+      }
-+      spin_unlock(&sbi->s_md_lock);
-+
-+      ext3_mb_free_committed_blocks(sb);
-+}
-+
-+int ext3_mb_free_metadata(handle_t *handle, struct ext3_buddy *e3b,
-+                              int group, int block, int count)
-+{
-+      struct ext3_buddy_group_blocks *db = e3b->bd_bd;
-+      struct super_block *sb = e3b->bd_sb;
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      struct ext3_free_metadata *md;
-+      int i;
-+
-+      ext3_lock_group(sb, group);
-+      for (i = 0; i < count; i++) {
-+              md = db->bb_md_cur;
-+              if (md && db->bb_tid != handle->h_transaction->t_tid) {
-+                      db->bb_md_cur = NULL;
-+                      md = NULL;
-+              }
-+
-+              if (md == NULL) {
-+                      ext3_unlock_group(sb, group);
-+                      md = kmalloc(sizeof(*md), GFP_KERNEL);
-+                      if (md == NULL)
-+                              return -ENOMEM;
-+                      md->num = 0;
-+                      md->group = group;
-+
-+                      ext3_lock_group(sb, group);
-+                      if (db->bb_md_cur == NULL) {
-+                              spin_lock(&sbi->s_md_lock);
-+                              list_add(&md->list, &sbi->s_active_transaction);
-+                              spin_unlock(&sbi->s_md_lock);
-+                              db->bb_md_cur = md;
-+                              db->bb_tid = handle->h_transaction->t_tid;
-+                              mb_debug("new md 0x%p for group %u\n",
-+                                                      md, md->group);
-+                      } else {
-+                              kfree(md);
-+                              md = db->bb_md_cur;
-+                      }
-+              }
-+
-+              BUG_ON(md->num >= EXT3_BB_MAX_BLOCKS);
-+              md->blocks[md->num] = block + i;
-+              md->num++;
-+              if (md->num == EXT3_BB_MAX_BLOCKS) {
-+                      /* no more space, put full container on a sb's list */
-+                      db->bb_md_cur = NULL;
-+              }
-+      }
-+      ext3_unlock_group(sb, group);
-+      return 0;
-+}
-+
-+void ext3_mb_free_blocks(handle_t *handle, struct inode *inode,
-+                      unsigned long block, unsigned long count, int metadata)
-+{
-+      struct buffer_head *bitmap_bh = NULL;
-+      struct ext3_group_desc *gdp;
-+      struct ext3_super_block *es;
-+      unsigned long bit, overflow;
-+      struct buffer_head *gd_bh;
-+      unsigned long block_group;
-+      struct ext3_sb_info *sbi;
-+      struct super_block *sb;
-+      struct ext3_buddy e3b;
-+      int err = 0, ret;
-+
-+      sb = inode->i_sb;
-+      if (!sb) {
-+              printk ("ext3_free_blocks: nonexistent device");
-+              return;
-+      }
-+
-+      ext3_mb_poll_new_transaction(sb, handle);
-+
-+      sbi = EXT3_SB(sb);
-+      es = EXT3_SB(sb)->s_es;
-+      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 - "
-+                          "block = %lu, count = %lu", block, count);
-+              goto error_return;
-+      }
-+
-+      ext3_debug("freeing block %lu\n", block);
-+
-+do_more:
-+      overflow = 0;
-+      block_group = (block - le32_to_cpu(es->s_first_data_block)) /
-+                    EXT3_BLOCKS_PER_GROUP(sb);
-+      bit = (block - le32_to_cpu(es->s_first_data_block)) %
-+                    EXT3_BLOCKS_PER_GROUP(sb);
-+      /*
-+       * Check to see if we are freeing blocks across a group
-+       * boundary.
-+       */
-+      if (bit + count > EXT3_BLOCKS_PER_GROUP(sb)) {
-+              overflow = bit + count - EXT3_BLOCKS_PER_GROUP(sb);
-+              count -= overflow;
-+      }
-+      brelse(bitmap_bh);
-+      bitmap_bh = read_block_bitmap(sb, block_group);
-+      if (!bitmap_bh)
-+              goto error_return;
-+      gdp = ext3_get_group_desc (sb, block_group, &gd_bh);
-+      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),
-+                    EXT3_SB(sb)->s_itb_per_group) ||
-+          in_range (block + count - 1, le32_to_cpu(gdp->bg_inode_table),
-+                    EXT3_SB(sb)->s_itb_per_group))
-+              ext3_error (sb, "ext3_free_blocks",
-+                          "Freeing blocks in system zones - "
-+                          "Block = %lu, count = %lu",
-+                          block, count);
-+
-+      BUFFER_TRACE(bitmap_bh, "getting write access");
-+      err = ext3_journal_get_write_access(handle, bitmap_bh);
-+      if (err)
-+              goto error_return;
-+
-+      /*
-+       * We are about to modify some metadata.  Call the journal APIs
-+       * to unshare ->b_data if a currently-committing transaction is
-+       * using it
-+       */
-+      BUFFER_TRACE(gd_bh, "get_write_access");
-+      err = ext3_journal_get_write_access(handle, gd_bh);
-+      if (err)
-+              goto error_return;
-+
-+      err = ext3_mb_load_desc(sb, block_group, &e3b);
-+      if (err)
-+              goto error_return;
-+
-+      if (metadata) {
-+              /* blocks being freed are metadata. these blocks shouldn't
-+               * be used until this transaction is committed */
-+              ext3_mb_free_metadata(handle, &e3b, block_group, bit, count);
-+      } else { 
-+              ext3_lock_group(sb, block_group);
-+              mb_free_blocks(&e3b, bit, count);
-+              gdp->bg_free_blocks_count =
-+                      cpu_to_le16(le16_to_cpu(gdp->bg_free_blocks_count) + count);
-+              ext3_unlock_group(sb, block_group);
-+              percpu_counter_mod(&sbi->s_freeblocks_counter, count);
-+      }
-+      
-+      ext3_mb_dirty_buddy(&e3b);
-+      ext3_mb_release_desc(&e3b);
-+
-+      /* FIXME: undo logic will be implemented later and another way */
-+      mb_clear_bits(bitmap_bh->b_data, bit, count);
-+      DQUOT_FREE_BLOCK(inode, count);
-+
-+      /* We dirtied the bitmap block */
-+      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
-+      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
-+
-+      /* And the group descriptor block */
-+      BUFFER_TRACE(gd_bh, "dirtied group descriptor block");
-+      ret = ext3_journal_dirty_metadata(handle, gd_bh);
-+      if (!err) err = ret;
-+
-+      if (overflow && !err) {
-+              block += count;
-+              count = overflow;
-+              goto do_more;
-+      }
-+      sb->s_dirt = 1;
-+error_return:
-+      brelse(bitmap_bh);
-+      ext3_std_error(sb, err);
-+      return;
-+}
-+
-+int ext3_mb_reserve_blocks(struct super_block *sb, int blocks)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      int free, ret = -ENOSPC;
-+
-+      BUG_ON(blocks < 0);
-+      spin_lock(&sbi->s_reserve_lock);
-+      free = percpu_counter_read_positive(&sbi->s_freeblocks_counter);
-+      if (blocks <= free - sbi->s_blocks_reserved) {
-+              sbi->s_blocks_reserved += blocks;
-+              ret = 0;
-+      }
-+      spin_unlock(&sbi->s_reserve_lock);
-+      return ret;
-+}
-+
-+void ext3_mb_release_blocks(struct super_block *sb, int blocks)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+
-+      BUG_ON(blocks < 0);
-+      spin_lock(&sbi->s_reserve_lock);
-+      sbi->s_blocks_reserved -= blocks;
-+      WARN_ON(sbi->s_blocks_reserved < 0);
-+      if (sbi->s_blocks_reserved < 0)
-+              sbi->s_blocks_reserved = 0;
-+      spin_unlock(&sbi->s_reserve_lock);
-+}
-+
-+int ext3_new_block(handle_t *handle, struct inode *inode,
-+                      unsigned long goal, u32 *pc, u32 *pb, int *errp)
-+{
-+      int ret, len;
-+
-+      if (!test_opt(inode->i_sb, MBALLOC)) {
-+              ret = ext3_new_block_old(handle, inode, goal, pc, pb, errp);
-+              goto out;
-+      }
-+      len = 1;
-+      ret = ext3_mb_new_blocks(handle, inode, goal, &len, 0, errp);
-+out:
-+      return ret;
-+}
-+
-+
-+void ext3_free_blocks(handle_t *handle, struct inode * inode,
-+                      unsigned long block, unsigned long count, int metadata)
-+{
-+      if (!test_opt(inode->i_sb, MBALLOC))
-+              ext3_free_blocks_old(handle, inode, block, count);
-+      else
-+              ext3_mb_free_blocks(handle, inode, block, count, metadata);
-+      return;
-+}
-+
-Index: linux-2.6.7/fs/ext3/super.c
-===================================================================
---- linux-2.6.7.orig/fs/ext3/super.c   2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/fs/ext3/super.c        2004-09-03 08:46:59.000000000 +0400
-@@ -392,6 +392,7 @@
-       struct ext3_super_block *es = sbi->s_es;
-       int i;
-+      ext3_mb_release(sb);
-       ext3_ext_release(sb);
-       ext3_xattr_put_super(sb);
-       journal_destroy(sbi->s_journal);
-@@ -594,7 +595,7 @@
-       Opt_usrjquota, Opt_grpjquota, Opt_offusrjquota, Opt_offgrpjquota,
-       Opt_jqfmt_vfsold, Opt_jqfmt_vfsv0,
-       Opt_iopen, Opt_noiopen, Opt_iopen_nopriv,
--      Opt_ignore, Opt_err, Opt_extents, Opt_extdebug
-+      Opt_ignore, Opt_err, Opt_extents, Opt_extdebug, Opt_mballoc,
- };
- static match_table_t tokens = {
-@@ -644,6 +645,7 @@
-       {Opt_iopen_nopriv,  "iopen_nopriv"},
-       {Opt_extents, "extents"},
-       {Opt_extdebug, "extdebug"},
-+      {Opt_mballoc, "mballoc"},
-       {Opt_err, NULL}
- };
-@@ -929,6 +931,9 @@
-               case Opt_extdebug:
-                       set_opt (sbi->s_mount_opt, EXTDEBUG);
-                       break;
-+              case Opt_mballoc:
-+                      set_opt (sbi->s_mount_opt, MBALLOC);
-+                      break;
-               default:
-                       printk (KERN_ERR
-                               "EXT3-fs: Unrecognized mount option \"%s\" "
-@@ -1602,7 +1607,8 @@
-               ext3_count_dirs(sb));
-       ext3_ext_init(sb);
-- 
-+      ext3_mb_init(sb);
-+
-       return 0;
- failed_mount3:
-Index: linux-2.6.7/fs/ext3/Makefile
-===================================================================
---- linux-2.6.7.orig/fs/ext3/Makefile  2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/fs/ext3/Makefile       2004-09-03 08:46:59.000000000 +0400
-@@ -5,7 +5,7 @@
- obj-$(CONFIG_EXT3_FS) += ext3.o
- ext3-y        := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o iopen.o \
--         ioctl.o namei.o super.o symlink.o hash.o extents.o
-+         ioctl.o namei.o super.o symlink.o hash.o extents.o mballoc.o
- ext3-$(CONFIG_EXT3_FS_XATTR)   += xattr.o xattr_user.o xattr_trusted.o
- ext3-$(CONFIG_EXT3_FS_POSIX_ACL) += acl.o
-Index: linux-2.6.7/fs/ext3/balloc.c
-===================================================================
---- linux-2.6.7.orig/fs/ext3/balloc.c  2004-08-26 17:11:16.000000000 +0400
-+++ linux-2.6.7/fs/ext3/balloc.c       2004-09-03 08:46:59.000000000 +0400
-@@ -78,7 +78,7 @@
-  *
-  * Return buffer_head on success or NULL in case of failure.
-  */
--static struct buffer_head *
-+struct buffer_head *
- read_block_bitmap(struct super_block *sb, unsigned int block_group)
- {
-       struct ext3_group_desc * desc;
-@@ -98,8 +98,8 @@
- }
- /* Free given blocks, update quota and i_blocks field */
--void ext3_free_blocks (handle_t *handle, struct inode * inode,
--                      unsigned long block, unsigned long count)
-+void ext3_free_blocks_old (handle_t *handle, struct inode * inode,
-+                              unsigned long block, unsigned long count)
- {
-       struct buffer_head *bitmap_bh = NULL;
-       struct buffer_head *gd_bh;
-@@ -474,8 +474,8 @@
-  * This function also updates quota and i_blocks field.
-  */
- int
--ext3_new_block(handle_t *handle, struct inode *inode, unsigned long goal,
--              u32 *prealloc_count, u32 *prealloc_block, int *errp)
-+ext3_new_block_old(handle_t *handle, struct inode *inode, unsigned long goal,
-+                      u32 *prealloc_count, u32 *prealloc_block, int *errp)
- {
-       struct buffer_head *bitmap_bh = NULL;   /* bh */
-       struct buffer_head *gdp_bh;             /* bh2 */
-Index: linux-2.6.7/fs/ext3/namei.c
-===================================================================
---- linux-2.6.7.orig/fs/ext3/namei.c   2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/fs/ext3/namei.c        2004-09-03 08:46:59.000000000 +0400
-@@ -1640,7 +1640,7 @@
-  * If the create succeeds, we fill in the inode information
-  * with d_instantiate(). 
-  */
--static int ext3_create (struct inode * dir, struct dentry * dentry, int mode,
-+int ext3_create (struct inode * dir, struct dentry * dentry, int mode,
-               struct nameidata *nd)
- {
-       handle_t *handle; 
-Index: linux-2.6.7/fs/ext3/inode.c
-===================================================================
---- linux-2.6.7.orig/fs/ext3/inode.c   2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/fs/ext3/inode.c        2004-09-03 08:46:59.000000000 +0400
-@@ -254,7 +254,7 @@
-               ei->i_prealloc_count = 0;
-               ei->i_prealloc_block = 0;
-               /* Writer: end */
--              ext3_free_blocks (inode, block, total);
-+              ext3_free_blocks (inode, block, total, 1);
-       }
- #endif
- }
-@@ -633,7 +633,7 @@
-               ext3_journal_forget(handle, branch[i].bh);
-       }
-       for (i = 0; i < keys; i++)
--              ext3_free_blocks(handle, inode, le32_to_cpu(branch[i].key), 1);
-+              ext3_free_blocks(handle, inode, le32_to_cpu(branch[i].key), 1, 1);
-       return err;
- }
-@@ -734,7 +734,7 @@
-       if (err == -EAGAIN)
-               for (i = 0; i < num; i++)
-                       ext3_free_blocks(handle, inode, 
--                                       le32_to_cpu(where[i].key), 1);
-+                                       le32_to_cpu(where[i].key), 1, 1);
-       return err;
- }
-@@ -1911,7 +1911,7 @@
-               }
-       }
--      ext3_free_blocks(handle, inode, block_to_free, count);
-+      ext3_free_blocks(handle, inode, block_to_free, count, 1);
- }
- /**
-@@ -2082,7 +2082,7 @@
-                               ext3_journal_test_restart(handle, inode);
-                       }
--                      ext3_free_blocks(handle, inode, nr, 1);
-+                      ext3_free_blocks(handle, inode, nr, 1, 1);
-                       if (parent_bh) {
-                               /*
-Index: linux-2.6.7/fs/ext3/extents.c
-===================================================================
---- linux-2.6.7.orig/fs/ext3/extents.c 2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/fs/ext3/extents.c      2004-09-03 08:46:59.000000000 +0400
-@@ -740,7 +740,7 @@
-               for (i = 0; i < depth; i++) {
-                       if (!ablocks[i])
-                               continue;
--                      ext3_free_blocks(handle, tree->inode, ablocks[i], 1);
-+                      ext3_free_blocks(handle, tree->inode, ablocks[i], 1, 1);
-               }
-       }
-       kfree(ablocks);
-@@ -1388,7 +1388,7 @@
-                       path->p_idx->ei_leaf);
-       bh = sb_find_get_block(tree->inode->i_sb, path->p_idx->ei_leaf);
-       ext3_forget(handle, 1, tree->inode, bh, path->p_idx->ei_leaf);
--      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1);
-+      ext3_free_blocks(handle, tree->inode, path->p_idx->ei_leaf, 1, 1);
-       return err;
- }
-@@ -1876,10 +1876,12 @@
-       int needed = ext3_remove_blocks_credits(tree, ex, from, to);
-       handle_t *handle = ext3_journal_start(tree->inode, needed);
-       struct buffer_head *bh;
--      int i;
-+      int i, metadata = 0;
-       if (IS_ERR(handle))
-               return PTR_ERR(handle);
-+      if (S_ISDIR(tree->inode->i_mode))
-+              metadata = 1;
-       if (from >= ex->ee_block && to == ex->ee_block + ex->ee_len - 1) {
-               /* tail removal */
-               unsigned long num, start;
-@@ -1891,7 +1893,7 @@
-                       bh = sb_find_get_block(tree->inode->i_sb, start + i);
-                       ext3_forget(handle, 0, tree->inode, bh, start + i);
-               }
--              ext3_free_blocks(handle, tree->inode, start, num);
-+              ext3_free_blocks(handle, tree->inode, start, num, metadata);
-       } else if (from == ex->ee_block && to <= ex->ee_block + ex->ee_len - 1) {
-               printk("strange request: removal %lu-%lu from %u:%u\n",
-                       from, to, ex->ee_block, ex->ee_len);
-Index: linux-2.6.7/fs/ext3/xattr.c
-===================================================================
---- linux-2.6.7.orig/fs/ext3/xattr.c   2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/fs/ext3/xattr.c        2004-09-03 08:46:59.000000000 +0400
-@@ -1366,7 +1366,7 @@
-                       new_bh = sb_getblk(sb, block);
-                       if (!new_bh) {
- getblk_failed:
--                              ext3_free_blocks(handle, inode, block, 1);
-+                              ext3_free_blocks(handle, inode, block, 1, 1);
-                               error = -EIO;
-                               goto cleanup;
-                       }
-@@ -1408,7 +1408,7 @@
-               if (HDR(old_bh)->h_refcount == cpu_to_le32(1)) {
-                       /* Free the old block. */
-                       ea_bdebug(old_bh, "freeing");
--                      ext3_free_blocks(handle, inode, old_bh->b_blocknr, 1);
-+                      ext3_free_blocks(handle, inode, old_bh->b_blocknr, 1, 1);
-                       /* ext3_forget() calls bforget() for us, but we
-                          let our caller release old_bh, so we need to
-@@ -1497,7 +1497,7 @@
-       lock_buffer(bh);
-       if (HDR(bh)->h_refcount == cpu_to_le32(1)) {
-               ext3_xattr_cache_remove(bh);
--              ext3_free_blocks(handle, inode, EXT3_I(inode)->i_file_acl, 1);
-+              ext3_free_blocks(handle, inode, EXT3_I(inode)->i_file_acl, 1, 1);
-               get_bh(bh);
-               ext3_forget(handle, 1, inode, bh, EXT3_I(inode)->i_file_acl);
-       } else {
-Index: linux-2.6.7/include/linux/ext3_fs.h
-===================================================================
---- linux-2.6.7.orig/include/linux/ext3_fs.h   2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/include/linux/ext3_fs.h        2004-09-03 08:47:35.000000000 +0400
-@@ -57,6 +57,8 @@
- #define ext3_debug(f, a...)   do {} while (0)
- #endif
-+#define EXT3_MULTIBLOCK_ALLOCATOR     1
-+
- /*
-  * Special inodes numbers
-  */
-@@ -335,6 +337,7 @@
- #define EXT3_MOUNT_IOPEN_NOPRIV               0x80000 /* Make iopen world-readable */
- #define EXT3_MOUNT_EXTENTS            0x100000/* Extents support */
- #define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
-+#define EXT3_MOUNT_MBALLOC            0x400000/* Buddy allocation support */
- /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
- #ifndef clear_opt
-@@ -695,7 +698,7 @@
- extern int ext3_new_block (handle_t *, struct inode *, unsigned long,
-                                           __u32 *, __u32 *, int *);
- extern void ext3_free_blocks (handle_t *, struct inode *, unsigned long,
--                            unsigned long);
-+                            unsigned long, int);
- extern unsigned long ext3_count_free_blocks (struct super_block *);
- extern void ext3_check_blocks_bitmap (struct super_block *);
- extern struct ext3_group_desc * ext3_get_group_desc(struct super_block * sb,
-Index: linux-2.6.7/include/linux/ext3_fs_sb.h
-===================================================================
---- linux-2.6.7.orig/include/linux/ext3_fs_sb.h        2004-09-03 08:46:59.000000000 +0400
-+++ linux-2.6.7/include/linux/ext3_fs_sb.h     2004-09-03 08:46:59.000000000 +0400
-@@ -23,9 +23,29 @@
- #define EXT_INCLUDE
- #include <linux/blockgroup_lock.h>
- #include <linux/percpu_counter.h>
-+#include <linux/list.h>
- #endif
- #endif
-+#define EXT3_BB_MAX_BLOCKS    30
-+struct ext3_free_metadata {
-+      unsigned short group;
-+      unsigned short num;
-+      unsigned short blocks[EXT3_BB_MAX_BLOCKS];
-+      struct list_head list;
-+};
-+
-+#define EXT3_BB_MAX_ORDER     14
-+
-+struct ext3_buddy_group_blocks {
-+      sector_t        bb_bitmap;
-+      sector_t        bb_buddy;
-+      spinlock_t      bb_lock;
-+      unsigned        bb_counters[EXT3_BB_MAX_ORDER];
-+      struct ext3_free_metadata *bb_md_cur;
-+      unsigned long bb_tid;
-+};
-+
- /*
-  * third extended-fs super-block data in memory
-  */
-@@ -76,6 +96,17 @@
-       char *s_qf_names[MAXQUOTAS];            /* Names of quota files with journalled quota */
-       int s_jquota_fmt;                       /* Format of quota to use */
- #endif
-+
-+      /* for buddy allocator */
-+      struct ext3_buddy_group_blocks *s_buddy_blocks;
-+      struct inode *s_buddy;
-+      long s_blocks_reserved;
-+      spinlock_t s_reserve_lock;
-+      struct list_head s_active_transaction;
-+      struct list_head s_closed_transaction;
-+      struct list_head s_committed_transaction;
-+      spinlock_t s_md_lock;
-+      tid_t s_last_transaction;
- };
- #endif        /* _LINUX_EXT3_FS_SB */
index fcceb30..dc6ffe3 100644 (file)
@@ -2,7 +2,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/mballoc.c 2005-02-25 17:28:41.836311072 +0200
 +++ linux-stage/fs/ext3/mballoc.c      2005-02-25 17:28:41.859307576 +0200
-@@ -0,0 +1,1847 @@
+@@ -0,0 +1,1860 @@
 +/*
 + * Copyright (c) 2003, Cluster File Systems, Inc, info@clusterfs.com
 + * Written by Alex Tomas <alex@clusterfs.com>
@@ -39,6 +39,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +
 +/*
 + * TODO:
++ *   - bitmap/buddy read-ahead (proposed by Oleg Drokin aka green)
 + *   - track min/max extents in each group for better group selection
 + *   - is it worthwhile to use buddies directly if req is 2^N blocks?
 + *   - mb_mark_used() may allocate chunk right after splitting buddy
@@ -96,7 +97,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      __u32   mh_magic;
 +};
 +
-+#define EXT3_MB_MAGIC_V1      0xbaad16fc
++#define EXT3_MB_MAGIC_V1      0xbabd16fd
 +
 +
 +struct ext3_free_extent {
@@ -148,47 +149,50 @@ Index: linux-stage/fs/ext3/mballoc.c
 +void ext3_mb_poll_new_transaction(struct super_block *, handle_t *);
 +void ext3_mb_free_committed_blocks(struct super_block *);
 +
-+#define mb_correct_addr_and_bit(bit,addr)     \
-+{                                             \
-+      if ((unsigned long)addr & 1) {          \
-+              bit += 8;                       \
-+              addr--;                         \
-+      }                                       \
-+      if ((unsigned long)addr & 2) {          \
-+              bit += 16;                      \
-+              addr--;                         \
-+              addr--;                         \
-+      }                                       \
++#if BITS_PER_LONG == 64
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 7UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~7UL);  \
 +}
++#elif BITS_PER_LONG == 32
++#define mb_correct_addr_and_bit(bit,addr)             \
++{                                                     \
++      bit += ((unsigned long) addr & 3UL) << 3;       \
++      addr = (void *) ((unsigned long) addr & ~3UL);  \
++}
++#else
++#error "how many bits you are?!"
++#endif
 +
 +static inline int mb_test_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      return test_bit(bit, addr);
++      return ext2_test_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __set_bit(bit, addr);
++      ext2_set_bit(bit, addr);
 +}
 +
 +static inline void mb_set_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      set_bit(bit, addr);
++      ext2_set_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void mb_clear_bit(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      __clear_bit(bit, addr);
++      ext2_clear_bit(bit, addr);
 +}
 +
 +static inline void mb_clear_bit_atomic(int bit, void *addr)
 +{
 +      mb_correct_addr_and_bit(bit,addr);
-+      clear_bit(bit, addr);
++      ext2_clear_bit_atomic(NULL, bit, addr);
 +}
 +
 +static inline void *mb_find_buddy(struct ext3_buddy *e3b, int order, int *max)
@@ -199,8 +203,10 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      J_ASSERT(EXT3_MB_BITMAP(e3b) != EXT3_MB_BUDDY(e3b));
 +      J_ASSERT(max != NULL);
 +
-+      if (order > e3b->bd_blkbits + 1)
++      if (order > e3b->bd_blkbits + 1) {
++              *max = 0;
 +              return NULL;
++      }
 +
 +      /* at order 0 we see each particular block */
 +      *max = 1 << (e3b->bd_blkbits + 3);
@@ -234,12 +240,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh)) {
-+              ll_rw_block(READ, 1, &e3b->bd_bh);
-+              wait_on_buffer(e3b->bd_bh);
-+      }
-+      J_ASSERT(buffer_uptodate(e3b->bd_bh));
-+
 +      /* load buddy */
 +      e3b->bd_bh2 = sb_getblk(sb, sbi->s_buddy_blocks[group]->bb_buddy);
 +      if (e3b->bd_bh2 == NULL) {
@@ -247,10 +247,15 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                              "can't get block for buddy bitmap\n");
 +              goto out;
 +      }
-+      if (!buffer_uptodate(e3b->bd_bh2)) {
++
++      if (!buffer_uptodate(e3b->bd_bh))
++              ll_rw_block(READ, 1, &e3b->bd_bh);
++      if (!buffer_uptodate(e3b->bd_bh2))
 +              ll_rw_block(READ, 1, &e3b->bd_bh2);
-+              wait_on_buffer(e3b->bd_bh2);
-+      }
++
++      wait_on_buffer(e3b->bd_bh);
++      J_ASSERT(buffer_uptodate(e3b->bd_bh));
++      wait_on_buffer(e3b->bd_bh2);
 +      J_ASSERT(buffer_uptodate(e3b->bd_bh2));
 +
 +      e3b->bd_blkbits = sb->s_blocksize_bits;
@@ -300,22 +305,22 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              count = 0;
 +              for (i = 0; i < max; i++) {
 +
-+                      if (!mb_test_bit(i, buddy)) {
++                      if (mb_test_bit(i, buddy)) {
 +                              /* only single bit in buddy2 may be 1 */
-+                              if (mb_test_bit(i << 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit((i<<1)+1, buddy2));
-+                              else if (mb_test_bit((i << 1) + 1, buddy2))
-+                                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
++                              if (!mb_test_bit(i << 1, buddy2))
++                                      J_ASSERT(mb_test_bit((i<<1)+1, buddy2));
++                              else if (!mb_test_bit((i << 1) + 1, buddy2))
++                                      J_ASSERT(mb_test_bit(i << 1, buddy2));
 +                              continue;
 +                      }
 +
 +                      /* both bits in buddy2 must be 0 */
-+                      J_ASSERT(!mb_test_bit(i << 1, buddy2));
-+                      J_ASSERT(!mb_test_bit((i << 1) + 1, buddy2));
++                      J_ASSERT(mb_test_bit(i << 1, buddy2));
++                      J_ASSERT(mb_test_bit((i << 1) + 1, buddy2));
 +
 +                      for (j = 0; j < (1 << order); j++) {
 +                              k = (i * (1 << order)) + j;
-+                              J_ASSERT(mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
++                              J_ASSERT(!mb_test_bit(k, EXT3_MB_BITMAP(e3b)));
 +                      }
 +                      count++;
 +              }
@@ -325,14 +330,14 @@ Index: linux-stage/fs/ext3/mballoc.c
 +
 +      buddy = mb_find_buddy(e3b, 0, &max);
 +      for (i = 0; i < max; i++) {
-+              if (mb_test_bit(i, buddy))
++              if (!mb_test_bit(i, buddy))
 +                      continue;
 +              /* check used bits only */
 +              for (j = 0; j < e3b->bd_blkbits + 1; j++) {
 +                      buddy2 = mb_find_buddy(e3b, j, &max2);
 +                      k = i >> j;
 +                      J_ASSERT(k < max2);
-+                      J_ASSERT(!mb_test_bit(k, buddy2));
++                      J_ASSERT(mb_test_bit(k, buddy2));
 +              }
 +      }
 +}
@@ -363,7 +368,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      bb = EXT3_MB_BUDDY(e3b);
 +      while (order <= e3b->bd_blkbits + 1) {
 +              block = block >> 1;
-+              if (mb_test_bit(block, bb)) {
++              if (!mb_test_bit(block, bb)) {
 +                      /* this block is part of buddy of order 'order' */
 +                      return order;
 +              }
@@ -424,8 +429,8 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              block = first++;
 +              order = 0;
 +
-+              J_ASSERT(!mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
-+              mb_set_bit(block, EXT3_MB_BITMAP(e3b));
++              J_ASSERT(mb_test_bit(block, EXT3_MB_BITMAP(e3b)));
++              mb_clear_bit(block, EXT3_MB_BITMAP(e3b));
 +              e3b->bd_bd->bb_counters[order]++;
 +
 +              /* start of the buddy */
@@ -433,8 +438,8 @@ Index: linux-stage/fs/ext3/mballoc.c
 +
 +              do {
 +                      block &= ~1UL;
-+                      if (!mb_test_bit(block, buddy) ||
-+                                      !mb_test_bit(block + 1, buddy))
++                      if (mb_test_bit(block, buddy) ||
++                                      mb_test_bit(block + 1, buddy))
 +                              break;
 +
 +                      /* both the buddies are free, try to coalesce them */
@@ -444,10 +449,10 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                              break;
 +
 +                      if (order > 0) {
-+                              /* for special purposes, we don't clear
++                              /* for special purposes, we don't set
 +                               * free bits in bitmap */
-+                              mb_clear_bit(block, buddy);
-+                              mb_clear_bit(block + 1, buddy);
++                              mb_set_bit(block, buddy);
++                              mb_set_bit(block + 1, buddy);
 +                      }
 +                      e3b->bd_bd->bb_counters[order]--;
 +                      e3b->bd_bd->bb_counters[order]--;
@@ -456,7 +461,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                      order++;
 +                      e3b->bd_bd->bb_counters[order]++;
 +
-+                      mb_set_bit(block, buddy2);
++                      mb_clear_bit(block, buddy2);
 +                      buddy = buddy2;
 +              } while (1);
 +      }
@@ -476,7 +481,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      buddy = mb_find_buddy(e3b, order, &max);
 +      J_ASSERT(buddy);
 +      J_ASSERT(block < max);
-+      if (!mb_test_bit(block, buddy)) {
++      if (mb_test_bit(block, buddy)) {
 +              ex->fe_len = 0;
 +              ex->fe_start = 0;
 +              ex->fe_group = 0;
@@ -499,7 +504,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                      break;
 +
 +              next = (block + 1) * (1 << order);
-+              if (!mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
++              if (mb_test_bit(next, EXT3_MB_BITMAP(e3b)))
 +                      break;
 +
 +              ord = mb_find_order_for_block(e3b, next);
@@ -533,7 +538,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +                      mlen = 1 << ord;
 +                      buddy = mb_find_buddy(e3b, ord, &max);
 +                      J_ASSERT((start >> ord) < max);
-+                      mb_clear_bit(start >> ord, buddy);
++                      mb_set_bit(start >> ord, buddy);
 +                      e3b->bd_bd->bb_counters[ord]--;
 +                      start += mlen;
 +                      len -= mlen;
@@ -544,20 +549,20 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              /* we have to split large buddy */
 +              J_ASSERT(ord > 0);
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_clear_bit(start >> ord, buddy);
++              mb_set_bit(start >> ord, buddy);
 +              e3b->bd_bd->bb_counters[ord]--;
 +
 +              ord--;
 +              cur = (start >> ord) & ~1U;
 +              buddy = mb_find_buddy(e3b, ord, &max);
-+              mb_set_bit(cur, buddy);
-+              mb_set_bit(cur + 1, buddy);
++              mb_clear_bit(cur, buddy);
++              mb_clear_bit(cur + 1, buddy);
 +              e3b->bd_bd->bb_counters[ord]++;
 +              e3b->bd_bd->bb_counters[ord]++;
 +      }
 +
 +      /* now drop all the bits in bitmap */
-+      mb_clear_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
++      mb_set_bits(EXT3_MB_BITMAP(e3b), ex->fe_start, len0);
 +
 +      mb_check_buddy(e3b);
 +
@@ -733,7 +738,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      i = e3b->bd_bd->bb_first_free;
 +
 +      while (free && ac->ac_status != AC_STATUS_FOUND) {
-+              i = find_next_bit(bitmap, sb->s_blocksize * 8, i);
++              i = ext2_find_next_zero_bit(bitmap, sb->s_blocksize * 8, i);
 +              if (i >= sb->s_blocksize * 8) {
 +                      J_ASSERT(free == 0);
 +                      break;
@@ -951,7 +956,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              /*
 +               * We aren't lucky definitely
 +               */
-+              J_ASSERT(ac.ac_b_ex.fe_len == 0);
 +              DQUOT_FREE_BLOCK(inode, *len);
 +              *errp = -ENOSPC;
 +              block = 0;
@@ -1020,8 +1024,8 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              ext3_error(sb, "ext3_new_block",
 +                          "Allocating block in system zone - "
 +                          "block = %u", block);
-+#if AGGRESSIVE_CHECK
-+      for (i = 0; i < ac.ac_b_len; i++)
++#ifdef AGGRESSIVE_CHECK
++      for (i = 0; i < ac.ac_b_ex.fe_len; i++)
 +              J_ASSERT(!mb_test_bit(ac.ac_b_ex.fe_start + i, bitmap_bh->b_data));
 +#endif
 +      mb_set_bits(bitmap_bh->b_data, ac.ac_b_ex.fe_start, ac.ac_b_ex.fe_len);
@@ -1141,7 +1145,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      
 +      e3b->bd_bd->bb_first_free = grp->mgd_first_free;
 +      e3b->bd_bd->bb_free = grp->mgd_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              e3b->bd_bd->bb_counters[i] = grp->mgd_counters[i];
 +      }
@@ -1197,7 +1201,7 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              goto out;
 +      grp->mgd_first_free = e3b->bd_bd->bb_first_free;
 +      grp->mgd_free = e3b->bd_bd->bb_free;
-+      for (i = 0; i < e3b->bd_blkbits; i++) {
++      for (i = 0; i <= e3b->bd_blkbits + 1; i++) {
 +              J_ASSERT(i < 16);
 +              grp->mgd_counters[i] = e3b->bd_bd->bb_counters[i];
 +      }
@@ -1217,9 +1221,10 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      struct super_block *sb = e3b->bd_sb;
 +      struct buffer_head *bh;
 +      int i, count = 0;
-+      
-+      memset(e3b->bd_bh->b_data, 0, sb->s_blocksize);
-+      memset(e3b->bd_bh2->b_data, 0, sb->s_blocksize);
++
++      mb_debug("generate buddy for group %d\n", e3b->bd_group);
++      memset(e3b->bd_bh->b_data, 0xff, sb->s_blocksize);
++      memset(e3b->bd_bh2->b_data, 0xff, sb->s_blocksize);
 +
 +      bh = read_block_bitmap(sb, e3b->bd_group);
 +      if (bh == NULL)
@@ -1748,6 +1753,19 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      if (err)
 +              goto error_return;
 +
++#ifdef AGGRESSIVE_CHECK
++      {
++              int i;
++              for (i = 0; i < count; i++)
++                      J_ASSERT(mb_test_bit(bit + i, bitmap_bh->b_data));
++      }
++#endif
++      mb_clear_bits(bitmap_bh->b_data, bit, count);
++
++      /* We dirtied the bitmap block */
++      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
++      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
++
 +      if (metadata) {
 +              /* blocks being freed are metadata. these blocks shouldn't
 +               * be used until this transaction is committed */
@@ -1757,21 +1775,18 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              mb_free_blocks(&e3b, bit, count);
 +              ext3_unlock_group(sb, block_group);
 +      }
++
 +      spin_lock(sb_bgl_lock(sbi, block_group));
 +      gdp->bg_free_blocks_count =
 +              cpu_to_le16(le16_to_cpu(gdp->bg_free_blocks_count) + count);
 +      spin_unlock(sb_bgl_lock(sbi, block_group));
++      percpu_counter_mod(&sbi->s_freeblocks_counter, count);
 +      
 +      ext3_mb_dirty_buddy(&e3b);
 +      ext3_mb_release_desc(&e3b);
 +
-+      mb_clear_bits(bitmap_bh->b_data, bit, count);
 +      *freed = count;
 +
-+      /* We dirtied the bitmap block */
-+      BUFFER_TRACE(bitmap_bh, "dirtied bitmap block");
-+      err = ext3_journal_dirty_metadata(handle, bitmap_bh);
-+
 +      /* And the group descriptor block */
 +      BUFFER_TRACE(gd_bh, "dirtied group descriptor block");
 +      ret = ext3_journal_dirty_metadata(handle, gd_bh);
@@ -1833,7 +1848,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +      return ret;
 +}
 +
-+
 +void ext3_free_blocks(handle_t *handle, struct inode * inode,
 +                      unsigned long block, unsigned long count, int metadata)
 +{
@@ -1849,7 +1863,6 @@ Index: linux-stage/fs/ext3/mballoc.c
 +              DQUOT_FREE_BLOCK(inode, freed);
 +      return;
 +}
-+
 Index: linux-stage/fs/ext3/super.c
 ===================================================================
 --- linux-stage.orig/fs/ext3/super.c   2005-02-25 17:27:00.231757312 +0200
@@ -1859,7 +1872,7 @@ Index: linux-stage/fs/ext3/super.c
        int i;
  
 +      ext3_mb_release(sb);
-       ext3_ext_release(sb);
+       ext3_ext_release(sb);
        ext3_xattr_put_super(sb);
        journal_destroy(sbi->s_journal);
 @@ -592,7 +593,7 @@
@@ -1897,16 +1910,14 @@ Index: linux-stage/fs/ext3/super.c
                default:
                        printk (KERN_ERR
                                "EXT3-fs: Unrecognized mount option \"%s\" "
-@@ -1639,7 +1652,8 @@
+@@ -1639,6 +1652,7 @@
                ext3_count_dirs(sb));
  
-       ext3_ext_init(sb);
-- 
+       ext3_ext_init(sb);
 +      ext3_mb_init(sb, needs_recovery);
-+
        return 0;
  
- failed_mount3:
 Index: linux-stage/fs/ext3/Makefile
 ===================================================================
 --- linux-stage.orig/fs/ext3/Makefile  2005-02-25 17:27:00.228757768 +0200
@@ -2122,8 +2133,8 @@ Index: linux-stage/include/linux/ext3_fs.h
  #define EXT3_MOUNT_EXTDEBUG           0x200000/* Extents debug */
 +#define EXT3_MOUNT_MBALLOC            0x400000/* Buddy allocation support */
  
  /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
+ #ifndef _LINUX_EXT2_FS_H
 @@ -725,7 +734,7 @@
  extern unsigned long ext3_bg_num_gdb(struct super_block *sb, int group);
  extern int ext3_new_block (handle_t *, struct inode *, unsigned long, int *);
@@ -2184,7 +2195,7 @@ Index: linux-stage/include/linux/ext3_fs_sb.h
  #endif
  #include <linux/rbtree.h>
  
-+#define EXT3_BB_MAX_BLOCKS    30
++#define EXT3_BB_MAX_BLOCKS    30
 +struct ext3_free_metadata {
 +      unsigned short group;
 +      unsigned short num;
@@ -2222,7 +2233,7 @@ Index: linux-stage/include/linux/ext3_fs_sb.h
 +      spinlock_t s_md_lock;
 +      tid_t s_last_transaction;
 +      int s_mb_factor;
-+ 
++
 +      /* stats for buddy allocator */
 +      spinlock_t s_bal_lock;
 +      unsigned long s_bal_reqs;       /* number of reqs with len > 1 */
diff --git a/lustre/kernel_patches/patches/ext3-o_direct-1.2.4.20-rh.patch b/lustre/kernel_patches/patches/ext3-o_direct-1.2.4.20-rh.patch
deleted file mode 100644 (file)
index 3aff4c5..0000000
+++ /dev/null
@@ -1,197 +0,0 @@
-
-Index: linux-2.4.20-rh/fs/ext3/inode.c
-===================================================================
---- linux-2.4.20-rh.orig/fs/ext3/inode.c       2003-09-04 18:01:41.000000000 +0800
-+++ linux-2.4.20-rh/fs/ext3/inode.c    2003-09-04 18:18:54.000000000 +0800
-@@ -27,6 +27,7 @@
- #include <linux/ext3_jbd.h>
- #include <linux/jbd.h>
- #include <linux/locks.h>
-+#include <linux/iobuf.h>
- #include <linux/smp_lock.h>
- #include <linux/highuid.h>
- #include <linux/quotaops.h>
-@@ -743,9 +744,9 @@
-  * The BKL may not be held on entry here.  Be sure to take it early.
-  */
--static int ext3_get_block_handle(handle_t *handle, struct inode *inode, 
--                               long iblock,
--                               struct buffer_head *bh_result, int create)
-+static int
-+ext3_get_block_handle(handle_t *handle, struct inode *inode, long iblock,
-+              struct buffer_head *bh_result, int create, int extend_disksize)
- {
-       int err = -EIO;
-       int offsets[4];
-@@ -825,15 +826,18 @@
-       if (err)
-               goto cleanup;
--      new_size = inode->i_size;
--      /*
--       * This is not racy against ext3_truncate's modification of i_disksize
--       * because VM/VFS ensures that the file cannot be extended while
--       * truncate is in progress.  It is racy between multiple parallel
--       * instances of get_block, but we have the BKL.
--       */
--      if (new_size > inode->u.ext3_i.i_disksize)
--              inode->u.ext3_i.i_disksize = new_size;
-+      if (extend_disksize) {
-+              /*
-+               * This is not racy against ext3_truncate's modification of
-+               * i_disksize because VM/VFS ensures that the file cannot be
-+               * extended while truncate is in progress.  It is racy between
-+               * multiple parallel instances of get_block, but we have BKL.
-+               */
-+              struct ext3_inode_info *ei = EXT3_I(inode);
-+              new_size = inode->i_size;
-+              if (new_size > ei->i_disksize)
-+                      ei->i_disksize = new_size;
-+      }
-       bh_result->b_state |= (1UL << BH_New);
-       goto got_it;
-@@ -861,7 +865,38 @@
-               handle = ext3_journal_current_handle();
-               J_ASSERT(handle != 0);
-       }
--      ret = ext3_get_block_handle(handle, inode, iblock, bh_result, create);
-+      ret = ext3_get_block_handle(handle, inode, iblock,
-+                              bh_result, create, 1);
-+      return ret;
-+}
-+
-+#define DIO_CREDITS (EXT3_RESERVE_TRANS_BLOCKS + 32)
-+
-+static int
-+ext3_direct_io_get_block(struct inode *inode, long iblock,
-+              struct buffer_head *bh_result, int create)
-+{
-+      handle_t *handle = journal_current_handle();
-+      int ret = 0;
-+
-+      lock_kernel();
-+      if (handle && handle->h_buffer_credits <= EXT3_RESERVE_TRANS_BLOCKS) {
-+              /*
-+               * Getting low on buffer credits...
-+               */
-+              if (!ext3_journal_extend(handle, DIO_CREDITS)) {
-+                      /*
-+                       * Couldn't extend the transaction.  Start a new one
-+                       */
-+                      ret = ext3_journal_restart(handle, DIO_CREDITS);
-+              }
-+      }
-+      if (ret == 0)
-+              ret = ext3_get_block_handle(handle, inode, iblock,
-+                                      bh_result, create, 0);
-+      if (ret == 0)
-+              bh_result->b_size = (1 << inode->i_blkbits);
-+      unlock_kernel();
-       return ret;
- }
-@@ -879,7 +914,7 @@
-       dummy.b_state = 0;
-       dummy.b_blocknr = -1000;
-       buffer_trace_init(&dummy.b_history);
--      *errp = ext3_get_block_handle(handle, inode, block, &dummy, create);
-+      *errp = ext3_get_block_handle(handle, inode, block, &dummy, create, 1);
-       if (!*errp && buffer_mapped(&dummy)) {
-               struct buffer_head *bh;
-               bh = sb_getblk(inode->i_sb, dummy.b_blocknr);
-@@ -1387,6 +1422,67 @@
-       return journal_try_to_free_buffers(journal, page, wait);
- }
-+static int
-+ext3_direct_IO(int rw, struct inode *inode, struct kiobuf *iobuf,
-+              unsigned long blocknr, int blocksize)
-+{
-+      struct ext3_inode_info *ei = EXT3_I(inode);
-+      handle_t *handle = NULL;
-+      int ret;
-+      int orphan = 0;
-+      loff_t offset = (loff_t)blocknr << inode->i_blkbits;    /* ugh */
-+      ssize_t count = iobuf->length;                  /* ditto */
-+
-+      if (rw == WRITE) {
-+              loff_t final_size = offset + count;
-+
-+              lock_kernel();
-+              handle = ext3_journal_start(inode, DIO_CREDITS);
-+              unlock_kernel();
-+              if (IS_ERR(handle)) {
-+                      ret = PTR_ERR(handle);
-+                      goto out;
-+              }
-+              if (final_size > inode->i_size) {
-+                      lock_kernel();
-+                      ret = ext3_orphan_add(handle, inode);
-+                      unlock_kernel();
-+                      if (ret)
-+                              goto out_stop;
-+                      orphan = 1;
-+                      ei->i_disksize = inode->i_size;
-+              }
-+      }
-+
-+      ret = generic_direct_IO(rw, inode, iobuf, blocknr,
-+                              blocksize, ext3_direct_io_get_block);
-+
-+out_stop:
-+      if (handle) {
-+              int err;
-+
-+              lock_kernel();
-+              if (orphan) 
-+                      ext3_orphan_del(handle, inode);
-+              if (orphan && ret > 0) {
-+                      loff_t end = offset + ret;
-+                      if (end > inode->i_size) {
-+                              ei->i_disksize = end;
-+                              inode->i_size = end;
-+                              err = ext3_mark_inode_dirty(handle, inode);
-+                              if (!ret) 
-+                                      ret = err;
-+                      }
-+              }
-+              err = ext3_journal_stop(handle, inode);
-+              if (ret == 0)
-+                      ret = err;
-+              unlock_kernel();
-+      }
-+out:
-+      return ret;
-+
-+}
- struct address_space_operations ext3_aops = {
-       readpage:       ext3_readpage,          /* BKL not held.  Don't need */
-@@ -1397,6 +1493,7 @@
-       bmap:           ext3_bmap,              /* BKL held */
-       flushpage:      ext3_flushpage,         /* BKL not held.  Don't need */
-       releasepage:    ext3_releasepage,       /* BKL not held.  Don't need */
-+      direct_IO:      ext3_direct_IO,         /* BKL not held.  Don't need */
- };
- /*
-@@ -2970,7 +3067,7 @@
-       /* alloc blocks one by one */
-       for (i = 0; i < nblocks; i++) {
-               ret = ext3_get_block_handle(handle, inode, blocks[i],
--                                              &bh_tmp, 1);
-+                                              &bh_tmp, 1, 1);
-               if (ret)
-                       break;
-@@ -3030,7 +3127,7 @@
-                 if (blocks[i] != 0)
-                         continue;
--                rc = ext3_get_block_handle(handle, inode, iblock, &bh, 1);
-+                rc = ext3_get_block_handle(handle, inode, iblock, &bh, 1, 1);
-                 if (rc) {
-                         printk(KERN_INFO "ext3_map_inode_page: error %d "
-                                "allocating block %ld\n", rc, iblock);
diff --git a/lustre/kernel_patches/patches/ext3-orphan_lock-suse.patch b/lustre/kernel_patches/patches/ext3-orphan_lock-suse.patch
deleted file mode 100644 (file)
index c3369e6..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-Index: linux-2.4.21-suse/fs/ext3/namei.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/namei.c     2003-10-30 02:17:22.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/namei.c  2003-10-30 02:20:53.000000000 +0300
-@@ -1747,8 +1747,8 @@
-       struct super_block *sb = inode->i_sb;
-       struct ext3_iloc iloc;
-       int err = 0, rc;
--      
--      lock_super(sb);
-+
-+      down(&EXT3_SB(sb)->s_orphan_lock);
-       if (!list_empty(&EXT3_I(inode)->i_orphan))
-               goto out_unlock;
-@@ -1796,7 +1796,7 @@
-       jbd_debug(4, "orphan inode %ld will point to %d\n",
-                       inode->i_ino, NEXT_ORPHAN(inode));
- out_unlock:
--      unlock_super(sb);
-+      up(&EXT3_SB(sb)->s_orphan_lock);
-       ext3_std_error(inode->i_sb, err);
-       return err;
- }
-@@ -1808,20 +1808,19 @@
- int ext3_orphan_del(handle_t *handle, struct inode *inode)
- {
-       struct list_head *prev;
--      struct ext3_sb_info *sbi;
-+      struct ext3_sb_info *sbi = EXT3_SB(inode->i_sb);
-       unsigned long ino_next;
-       struct ext3_iloc iloc;
-       int err = 0;
--      lock_super(inode->i_sb);
-+      down(&sbi->s_orphan_lock);
-       if (list_empty(&inode->u.ext3_i.i_orphan)) {
--              unlock_super(inode->i_sb);
-+              up(&sbi->s_orphan_lock);
-               return 0;
-       }
-       ino_next = NEXT_ORPHAN(inode);
-       prev = inode->u.ext3_i.i_orphan.prev;
--      sbi = EXT3_SB(inode->i_sb);
-       jbd_debug(4, "remove inode %lu from orphan list\n", inode->i_ino);
-@@ -1870,7 +1869,7 @@
- out_err:
-       ext3_std_error(inode->i_sb, err);
- out:
--      unlock_super(inode->i_sb);
-+      up(&sbi->s_orphan_lock);
-       return err;
- out_brelse:
-Index: linux-2.4.21-suse/fs/ext3/super.c
-===================================================================
---- linux-2.4.21-suse.orig/fs/ext3/super.c     2003-10-30 02:17:22.000000000 +0300
-+++ linux-2.4.21-suse/fs/ext3/super.c  2003-10-30 02:17:22.000000000 +0300
-@@ -1151,6 +1151,7 @@
-        */
-       sb->s_op = &ext3_sops;
-       INIT_LIST_HEAD(&sbi->s_orphan); /* unlinked but open files */
-+      sema_init(&sbi->s_orphan_lock, 1);
-       sb->s_root = 0;
-Index: linux-2.4.21-suse/include/linux/ext3_fs_sb.h
-===================================================================
---- linux-2.4.21-suse.orig/include/linux/ext3_fs_sb.h  2003-10-30 02:17:22.000000000 +0300
-+++ linux-2.4.21-suse/include/linux/ext3_fs_sb.h       2003-10-30 02:17:22.000000000 +0300
-@@ -69,6 +69,7 @@
-       struct inode * s_journal_inode;
-       struct journal_s * s_journal;
-       struct list_head s_orphan;
-+      struct semaphore s_orphan_lock;
-       unsigned long s_commit_interval;
-       struct block_device *journal_bdev;
- #ifdef CONFIG_JBD_DEBUG
diff --git a/lustre/kernel_patches/patches/ext3-pdirops-2.4.20-rh.patch b/lustre/kernel_patches/patches/ext3-pdirops-2.4.20-rh.patch
deleted file mode 100644 (file)
index 2733e7d..0000000
+++ /dev/null
@@ -1,1248 +0,0 @@
- fs/ext3/ialloc.c          |    3 
- fs/ext3/inode.c           |    3 
- fs/ext3/namei.c           |  582 +++++++++++++++++++++++++++++++++++++---------
- fs/ext3/super.c           |   14 +
- include/linux/ext3_fs.h   |    1 
- include/linux/ext3_fs_i.h |    6 
- 6 files changed, 500 insertions(+), 109 deletions(-)
-
-Index: linux-2.4.20/fs/ext3/namei.c
-===================================================================
---- linux-2.4.20.orig/fs/ext3/namei.c  2004-05-27 15:10:40.000000000 -0400
-+++ linux-2.4.20/fs/ext3/namei.c       2004-05-27 15:29:52.000000000 -0400
-@@ -51,6 +51,9 @@
- {
-       struct buffer_head *bh;
-+      /* with parallel dir operations all appends
-+       * have to be serialized -bzzz */
-+      down(&EXT3_I(inode)->i_append_sem);
-       *block = inode->i_size >> inode->i_sb->s_blocksize_bits;
-       if ((bh = ext3_bread(handle, inode, *block, 1, err))) {
-@@ -58,6 +61,8 @@
-               EXT3_I(inode)->i_disksize = inode->i_size;
-               ext3_journal_get_write_access(handle,bh);
-       }
-+      up(&EXT3_I(inode)->i_append_sem);
-+      
-       return bh;
- }
-@@ -134,6 +139,8 @@
-       struct buffer_head *bh;
-       struct dx_entry *entries;
-       struct dx_entry *at;
-+      unsigned long leaf;
-+      unsigned int curidx;
- };
- struct dx_map_entry
-@@ -142,6 +149,30 @@
-       u32 offs;
- };
-+/* FIXME: this should be reworked using bb_spin_lock
-+ * introduced in -mm tree
-+ */
-+#define BH_DXLock     25
-+
-+static inline void dx_lock_bh(struct buffer_head volatile *bh)
-+{
-+#ifdef CONFIG_SMP
-+        while (test_and_set_bit(BH_DXLock, &bh->b_state)) {
-+                while (test_bit(BH_DXLock, &bh->b_state))
-+                        cpu_relax();
-+        }
-+#endif
-+}
-+
-+static inline void dx_unlock_bh(struct buffer_head *bh)
-+{
-+#ifdef CONFIG_SMP
-+        smp_mb__before_clear_bit();
-+        clear_bit(BH_DXLock, &bh->b_state);
-+#endif
-+}
-+
-+
- #ifdef CONFIG_EXT3_INDEX
- static inline unsigned dx_get_block (struct dx_entry *entry);
- static void dx_set_block (struct dx_entry *entry, unsigned value);
-@@ -153,7 +184,7 @@
- static void dx_set_limit (struct dx_entry *entries, unsigned value);
- static unsigned dx_root_limit (struct inode *dir, unsigned infosize);
- static unsigned dx_node_limit (struct inode *dir);
--static struct dx_frame *dx_probe(struct dentry *dentry,
-+static struct dx_frame *dx_probe(struct qstr *name,
-                                struct inode *dir,
-                                struct dx_hash_info *hinfo,
-                                struct dx_frame *frame,
-@@ -165,15 +196,18 @@
- static struct ext3_dir_entry_2 *dx_move_dirents (char *from, char *to,
-               struct dx_map_entry *offsets, int count);
- static struct ext3_dir_entry_2* dx_pack_dirents (char *base, int size);
--static void dx_insert_block (struct dx_frame *frame, u32 hash, u32 block);
-+static void dx_insert_block (struct inode *, struct dx_frame *, u32, u32, u32);
- static int ext3_htree_next_block(struct inode *dir, __u32 hash,
-                                struct dx_frame *frame,
-                                struct dx_frame *frames, int *err,
-                                __u32 *start_hash);
- static struct buffer_head * ext3_dx_find_entry(struct dentry *dentry,
--                     struct ext3_dir_entry_2 **res_dir, int *err);
-+                     struct ext3_dir_entry_2 **res_dir, int *err,
-+                     int rwlock, void **lock);
- static int ext3_dx_add_entry(handle_t *handle, struct dentry *dentry,
-                            struct inode *inode);
-+static inline void *ext3_lock_htree(struct inode *, unsigned long, int);
-+static inline void ext3_unlock_htree(struct inode *, void *);
- /*
-  * Future: use high four bits of block for coalesce-on-delete flags
-@@ -306,6 +340,94 @@
- #endif /* DX_DEBUG */
- /*
-+ * dx_find_position
-+ *
-+ * search position of specified hash in index
-+ *
-+ */
-+
-+struct dx_entry * dx_find_position(struct dx_entry * entries, u32 hash)
-+{
-+      struct dx_entry *p, *q, *m;
-+      int count;
-+
-+      count = dx_get_count(entries);
-+      p = entries + 1;
-+      q = entries + count - 1;
-+      while (p <= q)
-+      {
-+              m = p + (q - p)/2;
-+              if (dx_get_hash(m) > hash)
-+                      q = m - 1;
-+              else
-+                      p = m + 1;
-+      }
-+      return p - 1;
-+}
-+
-+/*
-+ * returns 1 if path is unchanged
-+ */
-+int dx_check_path(struct dx_frame *frame, u32 hash)
-+{
-+      struct dx_entry *p;
-+      int ret = 1;
-+
-+      dx_lock_bh(frame->bh);
-+      p = dx_find_position(frame->entries, hash);
-+      if (frame->leaf != dx_get_block(p))
-+              ret = 0;
-+      dx_unlock_bh(frame->bh);
-+      
-+      return ret;
-+}
-+
-+/*
-+ * 0 - changed
-+ * 1 - hasn't changed
-+ */
-+static int
-+dx_check_full_path(struct dx_frame *frames, struct dx_hash_info *hinfo)
-+{
-+      struct dx_entry *p;
-+      struct dx_frame *frame = frames;
-+      u32 leaf;
-+
-+      /* check first level */
-+      dx_lock_bh(frame->bh);
-+      p = dx_find_position(frame->entries, hinfo->hash);
-+      leaf = dx_get_block(p);
-+      dx_unlock_bh(frame->bh);
-+      
-+      if (leaf != frame->leaf) 
-+              return 0;
-+      
-+      /* is there 2nd level? */
-+      frame++;
-+      if (frame->bh == NULL)
-+              return 1;
-+
-+      /* check second level */
-+      dx_lock_bh(frame->bh);
-+
-+      /* probably 1st level got changed, check it */
-+      if (!dx_check_path(frames, hinfo->hash)) {
-+              /* path changed */
-+              dx_unlock_bh(frame->bh);
-+              return 0;
-+      }
-+
-+      p = dx_find_position(frame->entries, hinfo->hash);
-+      leaf = dx_get_block(p);
-+      dx_unlock_bh(frame->bh);
-+      
-+      if (leaf != frame->leaf)
-+              return 0;
-+
-+      return 1;
-+}
-+
-+/*
-  * Probe for a directory leaf block to search.
-  *
-  * dx_probe can return ERR_BAD_DX_DIR, which means there was a format
-@@ -315,19 +437,20 @@
-  * back to userspace.
-  */
- static struct dx_frame *
--dx_probe(struct dentry *dentry, struct inode *dir,
-+dx_probe(struct qstr *name, struct inode *dir,
-        struct dx_hash_info *hinfo, struct dx_frame *frame_in, int *err)
- {
--      unsigned count, indirect;
--      struct dx_entry *at, *entries, *p, *q, *m;
-+      unsigned indirect;
-+      struct dx_entry *at, *entries;
-       struct dx_root *root;
-       struct buffer_head *bh;
-       struct dx_frame *frame = frame_in;
-       u32 hash;
-+      unsigned int curidx;
-       frame->bh = NULL;
--      if (dentry)
--              dir = dentry->d_parent->d_inode;
-+      frame[1].bh = NULL;
-+
-       if (!(bh = ext3_bread (NULL,dir, 0, 0, err)))
-               goto fail;
-       root = (struct dx_root *) bh->b_data;
-@@ -343,8 +466,8 @@
-       }
-       hinfo->hash_version = root->info.hash_version;
-       hinfo->seed = dir->i_sb->u.ext3_sb.s_hash_seed;
--      if (dentry)
--              ext3fs_dirhash(dentry->d_name.name, dentry->d_name.len, hinfo);
-+      if (name)
-+              ext3fs_dirhash(name->name, name->len, hinfo);
-       hash = hinfo->hash;
-       if (root->info.unused_flags & 1) {
-@@ -356,7 +479,19 @@
-               goto fail;
-       }
-+repeat:
-+      curidx = 0;
-+      entries = (struct dx_entry *) (((char *)&root->info) +
-+                                     root->info.info_length);
-+      assert(dx_get_limit(entries) == dx_root_limit(dir,
-+                                                    root->info.info_length));
-+      dxtrace (printk("Look up %x", hash));
-+      dx_lock_bh(bh);
-+      /* indirect must be initialized under bh lock because
-+       * 2nd level creation procedure may change it and dx_probe()
-+       * will suggest htree is still single-level -bzzz */
-       if ((indirect = root->info.indirect_levels) > 1) {
-+              dx_unlock_bh(bh);
-               ext3_warning(dir->i_sb, __FUNCTION__,
-                            "Unimplemented inode hash depth: %#06x",
-                            root->info.indirect_levels);
-@@ -364,56 +499,46 @@
-               *err = ERR_BAD_DX_DIR;
-               goto fail;
-       }
--
--      entries = (struct dx_entry *) (((char *)&root->info) +
--                                     root->info.info_length);
--      assert(dx_get_limit(entries) == dx_root_limit(dir,
--                                                    root->info.info_length));
--      dxtrace (printk("Look up %x", hash));
-+      
-       while (1)
-       {
--              count = dx_get_count(entries);
--              assert (count && count <= dx_get_limit(entries));
--              p = entries + 1;
--              q = entries + count - 1;
--              while (p <= q)
--              {
--                      m = p + (q - p)/2;
--                      dxtrace(printk("."));
--                      if (dx_get_hash(m) > hash)
--                              q = m - 1;
--                      else
--                              p = m + 1;
--              }
--
--              if (0) // linear search cross check
--              {
--                      unsigned n = count - 1;
--                      at = entries;
--                      while (n--)
--                      {
--                              dxtrace(printk(","));
--                              if (dx_get_hash(++at) > hash)
--                              {
--                                      at--;
--                                      break;
--                              }
--                      }
--                      assert (at == p - 1);
--              }
--
--              at = p - 1;
--              dxtrace(printk(" %x->%u\n", at == entries? 0: dx_get_hash(at), dx_get_block(at)));
-+              at = dx_find_position(entries, hinfo->hash);
-+              dxtrace(printk(" %x->%u\n",
-+                              at == entries? 0: dx_get_hash(at),
-+                              dx_get_block(at)));
-               frame->bh = bh;
-               frame->entries = entries;
-               frame->at = at;
--              if (!indirect--) return frame;
--              if (!(bh = ext3_bread (NULL,dir, dx_get_block(at), 0, err)))
-+              frame->curidx = curidx;
-+              frame->leaf = dx_get_block(at);
-+              if (!indirect--) {
-+                      dx_unlock_bh(bh);
-+                      return frame;
-+              }
-+              
-+              /* step into next htree level */
-+              curidx = dx_get_block(at);
-+              dx_unlock_bh(bh);
-+              if (!(bh = ext3_bread (NULL,dir, frame->leaf, 0, err)))
-                       goto fail2;
-+              
-+              dx_lock_bh(bh);
-+              /* splitting may change root index block and move
-+               * hash we're looking for into another index block
-+               * so, we have to check this situation and repeat
-+               * from begining if path got changed -bzzz */
-+              if (!dx_check_path(frame, hash)) {
-+                      dx_unlock_bh(bh);
-+                      bh = frame->bh;
-+                      indirect++;
-+                      goto repeat;
-+              }
-+              
-               at = entries = ((struct dx_node *) bh->b_data)->entries;
-               assert (dx_get_limit(entries) == dx_node_limit (dir));
-               frame++;
-       }
-+      dx_unlock_bh(bh);
- fail2:
-       while (frame >= frame_in) {
-               brelse(frame->bh);
-@@ -427,8 +552,7 @@
- {
-       if (frames[0].bh == NULL)
-               return;
--
--      if (((struct dx_root *) frames[0].bh->b_data)->info.indirect_levels)
-+      if (frames[1].bh != NULL)
-               brelse(frames[1].bh);
-       brelse(frames[0].bh);
- }
-@@ -470,8 +594,10 @@
-        * nodes need to be read.
-        */
-       while (1) {
--              if (++(p->at) < p->entries + dx_get_count(p->entries))
-+              if (++(p->at) < p->entries + dx_get_count(p->entries)) {
-+                      p->leaf = dx_get_block(p->at);
-                       break;
-+              }
-               if (p == frames)
-                       return 0;
-               num_frames++;
-@@ -497,13 +623,17 @@
-        * block so no check is necessary
-        */
-       while (num_frames--) {
--              if (!(bh = ext3_bread(NULL, dir, dx_get_block(p->at),
--                                    0, err)))
-+              u32 idx;
-+              
-+              idx = p->leaf = dx_get_block(p->at);
-+              if (!(bh = ext3_bread(NULL, dir, idx, 0, err)))
-                       return -1; /* Failure */
-               p++;
-               brelse (p->bh);
-               p->bh = bh;
-               p->at = p->entries = ((struct dx_node *) bh->b_data)->entries;
-+              p->curidx = idx;
-+              p->leaf = dx_get_block(p->at);
-       }
-       return 1;
- }
-@@ -543,7 +673,7 @@
-       dir = dir_file->f_dentry->d_inode;
-       hinfo.hash = start_hash;
-       hinfo.minor_hash = 0;
--      frame = dx_probe(0, dir_file->f_dentry->d_inode, &hinfo, frames, &err);
-+      frame = dx_probe(NULL, dir_file->f_dentry->d_inode, &hinfo, frames, &err);
-       if (!frame)
-               return err;
-@@ -625,7 +755,8 @@
-                       count++;
-               }
-               /* XXX: do we need to check rec_len == 0 case? -Chris */
--              de = (struct ext3_dir_entry_2 *) ((char *) de + le16_to_cpu(de->rec_len));
-+              de = (struct ext3_dir_entry_2 *)((char*)de +
-+                              le16_to_cpu(de->rec_len));
-       }
-       return count;
- }
-@@ -658,7 +789,8 @@
-       } while(more);
- }
--static void dx_insert_block(struct dx_frame *frame, u32 hash, u32 block)
-+static void dx_insert_block(struct inode *dir, struct dx_frame *frame,
-+                      u32 hash, u32 block, u32 idx)
- {
-       struct dx_entry *entries = frame->entries;
-       struct dx_entry *old = frame->at, *new = old + 1;
-@@ -670,6 +802,7 @@
-       dx_set_hash(new, hash);
-       dx_set_block(new, block);
-       dx_set_count(entries, count + 1);
-+      
- }
- #endif
-@@ -752,7 +885,8 @@
-       
- static struct buffer_head * ext3_find_entry (struct dentry *dentry,
--                                      struct ext3_dir_entry_2 ** res_dir)
-+                                      struct ext3_dir_entry_2 ** res_dir,
-+                                      int rwlock, void **lock)
- {
-       struct super_block * sb;
-       struct buffer_head * bh_use[NAMEI_RA_SIZE];
-@@ -768,6 +902,7 @@
-       int namelen;
-       const u8 *name;
-       unsigned blocksize;
-+      int do_not_use_dx = 0;
-       *res_dir = NULL;
-       sb = dir->i_sb;
-@@ -776,9 +911,10 @@
-       name = dentry->d_name.name;
-       if (namelen > EXT3_NAME_LEN)
-               return NULL;
-+repeat:
- #ifdef CONFIG_EXT3_INDEX
-       if (is_dx(dir)) {
--              bh = ext3_dx_find_entry(dentry, res_dir, &err);
-+              bh = ext3_dx_find_entry(dentry, res_dir, &err, rwlock, lock);
-               /*
-                * On success, or if the error was file not found,
-                * return.  Otherwise, fall back to doing a search the
-@@ -787,8 +923,14 @@
-               if (bh || (err != ERR_BAD_DX_DIR))
-                       return bh;
-               dxtrace(printk("ext3_find_entry: dx failed, falling back\n"));
-+              do_not_use_dx = 1;
-       }
- #endif
-+      *lock = ext3_lock_htree(dir, 0, rwlock);
-+      if (is_dx(dir) && !do_not_use_dx) {
-+              ext3_unlock_htree(dir, *lock);
-+              goto repeat;
-+      }
-       nblocks = dir->i_size >> EXT3_BLOCK_SIZE_BITS(sb);
-       start = EXT3_I(dir)->i_dir_start_lookup;
-       if (start >= nblocks)
-@@ -860,12 +1002,17 @@
-       /* Clean up the read-ahead blocks */
-       for (; ra_ptr < ra_max; ra_ptr++)
-               brelse (bh_use[ra_ptr]);
-+      if (!ret) {
-+              ext3_unlock_htree(dir, *lock);
-+              *lock = NULL;
-+      }
-       return ret;
- }
- #ifdef CONFIG_EXT3_INDEX
- static struct buffer_head * ext3_dx_find_entry(struct dentry *dentry,
--                     struct ext3_dir_entry_2 **res_dir, int *err)
-+                     struct ext3_dir_entry_2 **res_dir, int *err,
-+                     int rwlock, void **lock)
- {
-       struct super_block * sb;
-       struct dx_hash_info     hinfo;
-@@ -880,11 +1027,22 @@
-       struct inode *dir = dentry->d_parent->d_inode;
-       
-       sb = dir->i_sb;
--      if (!(frame = dx_probe (dentry, 0, &hinfo, frames, err)))
-+repeat:
-+      if (!(frame = dx_probe (&dentry->d_name, dir, &hinfo, frames, err)))
-               return NULL;
-+      
-+      *lock = ext3_lock_htree(dir, frame->leaf, rwlock);
-+      /* while locking leaf we just found may get splitted
-+       * so, we need another leaf. check this */
-+      if (!dx_check_full_path(frames, &hinfo)) {
-+              ext3_unlock_htree(dir, *lock);
-+              dx_release(frames);
-+              goto repeat;
-+      }
-+
-       hash = hinfo.hash;
-       do {
--              block = dx_get_block(frame->at);
-+              block = frame->leaf;
-               if (!(bh = ext3_bread (NULL,dir, block, 0, err)))
-                       goto errout;
-               de = (struct ext3_dir_entry_2 *) bh->b_data;
-@@ -918,6 +1076,8 @@
-       *err = -ENOENT;
- errout:
-       dxtrace(printk("%s not found\n", name));
-+      ext3_unlock_htree(dir, *lock);
-+      *lock = NULL;
-       dx_release (frames);
-       return NULL;
- }
-@@ -928,6 +1088,7 @@
-       struct inode * inode;
-       struct ext3_dir_entry_2 * de;
-       struct buffer_head * bh;
-+    void *lock = NULL;
-       if (dentry->d_name.len > EXT3_NAME_LEN)
-               return ERR_PTR(-ENAMETOOLONG);
-@@ -935,10 +1096,11 @@
-       if (ext3_check_for_iopen(dir, dentry))
-               return NULL;
--      bh = ext3_find_entry(dentry, &de);
-+      bh = ext3_find_entry(dentry, &de, 0, &lock);
-       inode = NULL;
-       if (bh) {
-               unsigned long ino = le32_to_cpu(de->inode);
-+              ext3_unlock_htree(dir, lock);
-               brelse (bh);
-               inode = iget(dir->i_sb, ino);
-@@ -975,7 +1137,8 @@
-       unsigned rec_len = 0;
-       while (count--) {
--              struct ext3_dir_entry_2 *de = (struct ext3_dir_entry_2 *) (from + map->offs);
-+              struct ext3_dir_entry_2 *de =
-+                      (struct ext3_dir_entry_2 *) (from + map->offs);
-               rec_len = EXT3_DIR_REC_LEN(de->name_len);
-               memcpy (to, de, rec_len);
-               ((struct ext3_dir_entry_2 *) to)->rec_len = rec_len;
-@@ -988,7 +1151,8 @@
- static struct ext3_dir_entry_2* dx_pack_dirents(char *base, int size)
- {
--      struct ext3_dir_entry_2 *next, *to, *prev, *de = (struct ext3_dir_entry_2 *) base;
-+      struct ext3_dir_entry_2 *next, *to, *prev;
-+      struct ext3_dir_entry_2 *de = (struct ext3_dir_entry_2 *) base;
-       unsigned rec_len = 0;
-       prev = to = de;
-@@ -1010,7 +1174,8 @@
- static struct ext3_dir_entry_2 *do_split(handle_t *handle, struct inode *dir,
-                       struct buffer_head **bh,struct dx_frame *frame,
--                      struct dx_hash_info *hinfo, int *error)
-+                      struct dx_hash_info *hinfo, void **target,
-+                      int *error)
- {
-       unsigned blocksize = dir->i_sb->s_blocksize;
-       unsigned count, continued;
-@@ -1057,23 +1222,30 @@
-       hash2 = map[split].hash;
-       continued = hash2 == map[split - 1].hash;
-       dxtrace(printk("Split block %i at %x, %i/%i\n",
--              dx_get_block(frame->at), hash2, split, count-split));
--
-+              frame->leaf, hash2, split, count-split));
-+      
-       /* Fancy dance to stay within two buffers */
-       de2 = dx_move_dirents(data1, data2, map + split, count - split);
-       de = dx_pack_dirents(data1,blocksize);
-       de->rec_len = cpu_to_le16(data1 + blocksize - (char *) de);
-       de2->rec_len = cpu_to_le16(data2 + blocksize - (char *) de2);
--      dxtrace(dx_show_leaf (hinfo, (struct ext3_dir_entry_2 *) data1, blocksize, 1));
--      dxtrace(dx_show_leaf (hinfo, (struct ext3_dir_entry_2 *) data2, blocksize, 1));
-+      dxtrace(dx_show_leaf(hinfo,(struct ext3_dir_entry_2*) data1, blocksize, 1));
-+      dxtrace(dx_show_leaf(hinfo,(struct ext3_dir_entry_2*) data2, blocksize, 1));
-       /* Which block gets the new entry? */
-+      *target = NULL;
-       if (hinfo->hash >= hash2)
-       {
-               swap(*bh, bh2);
-               de = de2;
--      }
--      dx_insert_block (frame, hash2 + continued, newblock);
-+
-+              /* entry will be stored into new block
-+               * we have to lock it before add_dirent_to_buf */
-+              *target = ext3_lock_htree(dir, newblock, 1);
-+      }
-+      dx_lock_bh(frame->bh);
-+      dx_insert_block (dir, frame, hash2 + continued, newblock, frame->curidx);
-+      dx_unlock_bh(frame->bh);
-       err = ext3_journal_dirty_metadata (handle, bh2);
-       if (err)
-               goto journal_error;
-@@ -1147,7 +1319,8 @@
-       nlen = EXT3_DIR_REC_LEN(de->name_len);
-       rlen = le16_to_cpu(de->rec_len);
-       if (de->inode) {
--              struct ext3_dir_entry_2 *de1 = (struct ext3_dir_entry_2 *)((char *)de + nlen);
-+              struct ext3_dir_entry_2 *de1 =
-+                      (struct ext3_dir_entry_2 *)((char *)de + nlen);
-               de1->rec_len = cpu_to_le16(rlen - nlen);
-               de->rec_len = cpu_to_le16(nlen);
-               de = de1;
-@@ -1205,7 +1378,8 @@
-       unsigned        blocksize;
-       struct dx_hash_info hinfo;
-       u32             block;
--              
-+      void            *lock, *new_lock;
-+
-       blocksize =  dir->i_sb->s_blocksize;
-       dxtrace(printk("Creating index\n"));
-       retval = ext3_journal_get_write_access(handle, bh);
-@@ -1216,7 +1390,6 @@
-       }
-       root = (struct dx_root *) bh->b_data;
-               
--      EXT3_I(dir)->i_flags |= EXT3_INDEX_FL;
-       bh2 = ext3_append (handle, dir, &block, &retval);
-       if (!(bh2)) {
-               brelse(bh);
-@@ -1224,6 +1397,8 @@
-       }
-       data1 = bh2->b_data;
-+      lock = ext3_lock_htree(dir, block, 1);
-+
-       /* The 0th block becomes the root, move the dirents out */
-       de = (struct ext3_dir_entry_2 *) &root->dotdot;
-       de = (struct ext3_dir_entry_2 *) ((char *)de + de->rec_len);
-@@ -1253,13 +1428,25 @@
-       frame->entries = entries;
-       frame->at = entries;
-       frame->bh = bh;
-+      frame->curidx = 0;
-+      frame->leaf = 0;
-+      frame[1].bh = NULL;
-       bh = bh2;
--      de = do_split(handle,dir, &bh, frame, &hinfo, &retval);
-+      de = do_split(handle,dir, &bh, frame, &hinfo, &new_lock, &retval);
-       dx_release (frames);
-       if (!(de))
--              return retval;
-+              goto cleanup;
-+
-+      retval = add_dirent_to_buf(handle, dentry, inode, de, bh);
-+cleanup:
-+      if (new_lock)
-+              ext3_unlock_htree(dir, new_lock);
-+      /* we mark directory indexed in order to
-+       * avoid races while htree being created -bzzz */
-+      EXT3_I(dir)->i_flags |= EXT3_INDEX_FL;
-+      ext3_unlock_htree(dir, lock);
--      return add_dirent_to_buf(handle, dentry, inode, de, bh);
-+      return retval;
- }
- #endif
-@@ -1288,11 +1475,13 @@
-       unsigned blocksize;
-       unsigned nlen, rlen;
-       u32 block, blocks;
-+      void *lock;
-       sb = dir->i_sb;
-       blocksize = sb->s_blocksize;
-       if (!dentry->d_name.len)
-               return -EINVAL;
-+repeat:
- #ifdef CONFIG_EXT3_INDEX
-       if (is_dx(dir)) {
-               retval = ext3_dx_add_entry(handle, dentry, inode);
-@@ -1303,36 +1492,53 @@
-               ext3_mark_inode_dirty(handle, dir);
-       }
- #endif
-+      lock = ext3_lock_htree(dir, 0, 1);
-+      if (is_dx(dir)) {
-+              /* we got lock for block 0
-+               * probably previous holder of the lock
-+               * created htree -bzzz */
-+              ext3_unlock_htree(dir, lock);
-+              goto repeat;
-+      }
-+      
-       blocks = dir->i_size >> sb->s_blocksize_bits;
-       for (block = 0, offset = 0; block < blocks; block++) {
-               bh = ext3_bread(handle, dir, block, 0, &retval);
--              if(!bh)
-+              if(!bh) {
-+                      ext3_unlock_htree(dir, lock);
-                       return retval;
-+              }
-               retval = add_dirent_to_buf(handle, dentry, inode, 0, bh);
--              if (retval != -ENOSPC)
-+              if (retval != -ENOSPC) {
-+                      ext3_unlock_htree(dir, lock);
-                       return retval;
-+              }
- #ifdef CONFIG_EXT3_INDEX
-               if (blocks == 1 && !dx_fallback &&
--                  EXT3_HAS_COMPAT_FEATURE(sb, EXT3_FEATURE_COMPAT_DIR_INDEX))
--                      return make_indexed_dir(handle, dentry, inode, bh);
-+                  EXT3_HAS_COMPAT_FEATURE(sb, EXT3_FEATURE_COMPAT_DIR_INDEX)) {
-+                      retval = make_indexed_dir(handle, dentry, inode, bh);
-+                      ext3_unlock_htree(dir, lock);
-+                      return retval;
-+              }
- #endif
-               brelse(bh);
-       }
-       bh = ext3_append(handle, dir, &block, &retval);
--      if (!bh)
-+      if (!bh) {
-+              ext3_unlock_htree(dir, lock);
-               return retval;
-+      }
-       de = (struct ext3_dir_entry_2 *) bh->b_data;
-       de->inode = 0;
-       de->rec_len = cpu_to_le16(rlen = blocksize);
-       nlen = 0;
--      return add_dirent_to_buf(handle, dentry, inode, de, bh);
-+      retval = add_dirent_to_buf(handle, dentry, inode, de, bh);
-+      ext3_unlock_htree(dir, lock);
-+      return retval;
- }
- #ifdef CONFIG_EXT3_INDEX
--/*
-- * Returns 0 for success, or a negative error value
-- */
- static int ext3_dx_add_entry(handle_t *handle, struct dentry *dentry,
-                            struct inode *inode)
- {
-@@ -1344,15 +1550,28 @@
-       struct super_block * sb = dir->i_sb;
-       struct ext3_dir_entry_2 *de;
-       int err;
--
--      frame = dx_probe(dentry, 0, &hinfo, frames, &err);
-+      int curidx;
-+      void *idx_lock, *leaf_lock, *newleaf_lock;
-+      
-+repeat:
-+      frame = dx_probe(&dentry->d_name, dir, &hinfo, frames, &err);
-       if (!frame)
-               return err;
--      entries = frame->entries;
--      at = frame->at;
--      if (!(bh = ext3_bread(handle,dir, dx_get_block(frame->at), 0, &err)))
-+      /* we're going to chage leaf, so lock it first */
-+      leaf_lock = ext3_lock_htree(dir, frame->leaf, 1);
-+
-+      /* while locking leaf we just found may get splitted
-+       * so we need to check this */
-+      if (!dx_check_full_path(frames, &hinfo)) {
-+              ext3_unlock_htree(dir, leaf_lock);
-+              dx_release(frames);
-+              goto repeat;
-+      }
-+      if (!(bh = ext3_bread(handle,dir, frame->leaf, 0, &err))) {
-+              printk("can't ext3_bread(%d) = %d\n", (int) frame->leaf, err);
-               goto cleanup;
-+      }
-       BUFFER_TRACE(bh, "get_write_access");
-       err = ext3_journal_get_write_access(handle, bh);
-@@ -1365,6 +1584,35 @@
-               goto cleanup;
-       }
-+      /* our leaf has no enough space. hence, we have to
-+       * split it. so lock index for this leaf first */
-+      curidx = frame->curidx;
-+      idx_lock = ext3_lock_htree(dir, curidx, 1);
-+
-+      /* now check did path get changed? */
-+      dx_release(frames);
-+
-+      frame = dx_probe(&dentry->d_name, dentry->d_parent->d_inode,
-+                      &hinfo, frames, &err);
-+      if (!frame) {
-+              /* FIXME: error handling here */
-+              brelse(bh);
-+              ext3_unlock_htree(dir, idx_lock);
-+              return err;
-+      }
-+      
-+      if (frame->curidx != curidx) {
-+              /* path has been changed. we have to drop old lock
-+               * and repeat */
-+              brelse(bh);
-+              ext3_unlock_htree(dir, idx_lock);
-+              ext3_unlock_htree(dir, leaf_lock);
-+              dx_release(frames);
-+              goto repeat;
-+      }
-+      entries = frame->entries;
-+      at = frame->at;
-+
-       /* Block full, should compress but for now just split */
-       dxtrace(printk("using %u of %u node entries\n",
-                      dx_get_count(entries), dx_get_limit(entries)));
-@@ -1376,7 +1624,8 @@
-               struct dx_entry *entries2;
-               struct dx_node *node2;
-               struct buffer_head *bh2;
--
-+              void *nb_lock;
-+              
-               if (levels && (dx_get_count(frames->entries) ==
-                              dx_get_limit(frames->entries))) {
-                       ext3_warning(sb, __FUNCTION__,
-@@ -1387,6 +1636,7 @@
-               bh2 = ext3_append (handle, dir, &newblock, &err);
-               if (!(bh2))
-                       goto cleanup;
-+              nb_lock = ext3_lock_htree(dir, newblock, 1);
-               node2 = (struct dx_node *)(bh2->b_data);
-               entries2 = node2->entries;
-               node2->fake.rec_len = cpu_to_le16(sb->s_blocksize);
-@@ -1398,27 +1648,73 @@
-               if (levels) {
-                       unsigned icount1 = icount/2, icount2 = icount - icount1;
-                       unsigned hash2 = dx_get_hash(entries + icount1);
-+                      void *ri_lock;
-+
-+                      /* we have to protect root htree index against
-+                       * another dx_add_entry() which would want to
-+                       * split it too -bzzz */
-+                      ri_lock = ext3_lock_htree(dir, 0, 1);
-+
-+                      /* as root index block blocked we must repeat
-+                       * searching for current position of our 2nd index -bzzz */
-+                      dx_lock_bh(frame->bh);
-+                      frames->at = dx_find_position(frames->entries, hinfo.hash);
-+                      dx_unlock_bh(frame->bh);
-+                      
-                       dxtrace(printk("Split index %i/%i\n", icount1, icount2));
--                              
--                      BUFFER_TRACE(frame->bh, "get_write_access"); /* index root */
-+      
-+                      BUFFER_TRACE(frame->bh, "get_write_access");
-                       err = ext3_journal_get_write_access(handle,
-                                                            frames[0].bh);
-                       if (err)
-                               goto journal_error;
--                              
-+                      
-+                      /* copy index into new one */
-                       memcpy ((char *) entries2, (char *) (entries + icount1),
-                               icount2 * sizeof(struct dx_entry));
--                      dx_set_count (entries, icount1);
-                       dx_set_count (entries2, icount2);
-                       dx_set_limit (entries2, dx_node_limit(dir));
-                       /* Which index block gets the new entry? */
-                       if (at - entries >= icount1) {
-+                              /* unlock index we won't use */
-+                              ext3_unlock_htree(dir, idx_lock);
-+                              idx_lock = nb_lock;
-                               frame->at = at = at - entries - icount1 + entries2;
--                              frame->entries = entries = entries2;
-+                              frame->entries = entries2;
-+                              frame->curidx = curidx = newblock;
-                               swap(frame->bh, bh2);
-+                      } else {
-+                              /* we'll use old index,so new one may be freed */
-+                              ext3_unlock_htree(dir, nb_lock);
-                       }
--                      dx_insert_block (frames + 0, hash2, newblock);
-+              
-+                      /* NOTE: very subtle piece of code
-+                       * competing dx_probe() may find 2nd level index in root
-+                       * index, then we insert new index here and set new count
-+                       * in that 2nd level index. so, dx_probe() may see 2nd
-+                       * level index w/o hash it looks for. the solution is
-+                       * to check root index after we locked just founded 2nd
-+                       * level index -bzzz */
-+                      dx_lock_bh(frames[0].bh);
-+                      dx_insert_block (dir, frames + 0, hash2, newblock, 0);
-+                      dx_unlock_bh(frames[0].bh);
-+                      
-+                      /* now old and new 2nd level index blocks contain
-+                       * all pointers, so dx_probe() may find it in the both.
-+                       * it's OK -bzzz */
-+                      
-+                      dx_lock_bh(frame->bh);
-+                      dx_set_count(entries, icount1);
-+                      dx_unlock_bh(frame->bh);
-+
-+                      /* now old 2nd level index block points to first half
-+                       * of leafs. it's importand that dx_probe() must
-+                       * check root index block for changes under
-+                       * dx_lock_bh(frame->bh) -bzzz */
-+
-+                      ext3_unlock_htree(dir, ri_lock);
-+              
-                       dxtrace(dx_show_index ("node", frames[1].entries));
-                       dxtrace(dx_show_index ("node",
-                              ((struct dx_node *) bh2->b_data)->entries));
-@@ -1427,38 +1723,61 @@
-                               goto journal_error;
-                       brelse (bh2);
-               } else {
-+                      unsigned long leaf = frame->leaf;
-+
-                       dxtrace(printk("Creating second level index...\n"));
-                       memcpy((char *) entries2, (char *) entries,
-                              icount * sizeof(struct dx_entry));
-                       dx_set_limit(entries2, dx_node_limit(dir));
-                       /* Set up root */
-+                      dx_lock_bh(frames[0].bh);
-                       dx_set_count(entries, 1);
-                       dx_set_block(entries + 0, newblock);
-                       ((struct dx_root *) frames[0].bh->b_data)->info.indirect_levels = 1;
-+                      dx_unlock_bh(frames[0].bh);
-                       /* Add new access path frame */
-                       frame = frames + 1;
-                       frame->at = at = at - entries + entries2;
-                       frame->entries = entries = entries2;
-                       frame->bh = bh2;
-+                      frame->curidx = newblock;
-+                      frame->leaf = leaf;
-                       err = ext3_journal_get_write_access(handle,
-                                                            frame->bh);
-                       if (err)
-                               goto journal_error;
-+
-+                      /* first level index was root. it's already initialized */
-+                      /* we my unlock it now */
-+                      ext3_unlock_htree(dir, idx_lock);
-+
-+                      /* current index is just created 2nd level index */
-+                      curidx = newblock;
-+                      idx_lock = nb_lock;
-               }
-               ext3_journal_dirty_metadata(handle, frames[0].bh);
-       }
--      de = do_split(handle, dir, &bh, frame, &hinfo, &err);
-+      de = do_split(handle, dir, &bh, frame, &hinfo, &newleaf_lock, &err);
-       if (!de)
-               goto cleanup;
-+
-+      /* index splitted */
-+      ext3_unlock_htree(dir, idx_lock);
-+      
-       err = add_dirent_to_buf(handle, dentry, inode, de, bh);
-+
-+      if (newleaf_lock)
-+              ext3_unlock_htree(dir, newleaf_lock);
-+      
-       bh = 0;
-       goto cleanup;
-       
- journal_error:
-       ext3_std_error(dir->i_sb, err);
- cleanup:
-+      ext3_unlock_htree(dir, leaf_lock);
-       if (bh)
-               brelse(bh);
-       dx_release(frames);
-@@ -1902,6 +2221,7 @@
-       struct buffer_head * bh;
-       struct ext3_dir_entry_2 * de;
-       handle_t *handle;
-+      void *lock;
-       handle = ext3_journal_start(dir, EXT3_DELETE_TRANS_BLOCKS);
-       if (IS_ERR(handle)) {
-@@ -1909,7 +2229,7 @@
-       }
-       retval = -ENOENT;
--      bh = ext3_find_entry (dentry, &de);
-+      bh = ext3_find_entry (dentry, &de, 1, &lock);
-       if (!bh)
-               goto end_rmdir;
-@@ -1920,14 +2240,19 @@
-       DQUOT_INIT(inode);
-       retval = -EIO;
--      if (le32_to_cpu(de->inode) != inode->i_ino)
-+      if (le32_to_cpu(de->inode) != inode->i_ino) {
-+              ext3_unlock_htree(dir, lock);
-               goto end_rmdir;
-+      }
-       retval = -ENOTEMPTY;
--      if (!empty_dir (inode))
-+      if (!empty_dir (inode)) {
-+              ext3_unlock_htree(dir, lock);
-               goto end_rmdir;
-+      }
-       retval = ext3_delete_entry(handle, dir, de, bh);
-+      ext3_unlock_htree(dir, lock);
-       if (retval)
-               goto end_rmdir;
-       if (inode->i_nlink != 2)
-@@ -1956,6 +2281,7 @@
-       struct buffer_head * bh;
-       struct ext3_dir_entry_2 * de;
-       handle_t *handle;
-+      void *lock;
-       handle = ext3_journal_start(dir, EXT3_DELETE_TRANS_BLOCKS);
-       if (IS_ERR(handle)) {
-@@ -1966,7 +2292,7 @@
-               handle->h_sync = 1;
-       retval = -ENOENT;
--      bh = ext3_find_entry (dentry, &de);
-+      bh = ext3_find_entry (dentry, &de, 1, &lock);
-       if (!bh)
-               goto end_unlink;
-@@ -1974,8 +2300,10 @@
-       DQUOT_INIT(inode);
-       retval = -EIO;
--      if (le32_to_cpu(de->inode) != inode->i_ino)
-+      if (le32_to_cpu(de->inode) != inode->i_ino) {
-+              ext3_unlock_htree(dir, lock);
-               goto end_unlink;
-+      }
-       
-       if (!inode->i_nlink) {
-               ext3_warning (inode->i_sb, "ext3_unlink",
-@@ -1984,6 +2312,7 @@
-               inode->i_nlink = 1;
-       }
-       retval = ext3_delete_entry(handle, dir, de, bh);
-+      ext3_unlock_htree(dir, lock);
-       if (retval)
-               goto end_unlink;
-       dir->i_ctime = dir->i_mtime = CURRENT_TIME;
-@@ -2121,6 +2450,7 @@
-       struct buffer_head * old_bh, * new_bh, * dir_bh;
-       struct ext3_dir_entry_2 * old_de, * new_de;
-       int retval;
-+      void *lock1 = NULL, *lock2 = NULL, *lock3 = NULL;
-       old_bh = new_bh = dir_bh = NULL;
-@@ -2133,7 +2463,10 @@
-       if (IS_SYNC(old_dir) || IS_SYNC(new_dir))
-               handle->h_sync = 1;
--      old_bh = ext3_find_entry (old_dentry, &old_de);
-+      if (old_dentry->d_parent == new_dentry->d_parent)
-+              down(&EXT3_I(old_dentry->d_parent->d_inode)->i_rename_sem);
-+
-+      old_bh = ext3_find_entry (old_dentry, &old_de, 1, &lock1 /* FIXME */);
-       /*
-        *  Check for inode number is _not_ due to possible IO errors.
-        *  We might rmdir the source, keep it as pwd of some process
-@@ -2146,7 +2479,7 @@
-               goto end_rename;
-       new_inode = new_dentry->d_inode;
--      new_bh = ext3_find_entry (new_dentry, &new_de);
-+      new_bh = ext3_find_entry (new_dentry, &new_de, 1, &lock2 /* FIXME */);
-       if (new_bh) {
-               if (!new_inode) {
-                       brelse (new_bh);
-@@ -2213,7 +2546,7 @@
-               struct buffer_head *old_bh2;
-               struct ext3_dir_entry_2 *old_de2;
--              old_bh2 = ext3_find_entry(old_dentry, &old_de2);
-+              old_bh2 = ext3_find_entry(old_dentry, &old_de2, 1, &lock3 /* FIXME */);
-               if (old_bh2) {
-                       retval = ext3_delete_entry(handle, old_dir,
-                                                  old_de2, old_bh2);
-@@ -2256,6 +2589,14 @@
-       retval = 0;
- end_rename:
-+      if (lock1)
-+              ext3_unlock_htree(old_dentry->d_parent->d_inode, lock1);
-+      if (lock2)
-+              ext3_unlock_htree(new_dentry->d_parent->d_inode, lock2);
-+      if (lock3)
-+              ext3_unlock_htree(old_dentry->d_parent->d_inode, lock3);
-+      if (old_dentry->d_parent == new_dentry->d_parent)
-+              up(&EXT3_I(old_dentry->d_parent->d_inode)->i_rename_sem);
-       brelse (dir_bh);
-       brelse (old_bh);
-       brelse (new_bh);
-@@ -2264,6 +2605,29 @@
- }
- /*
-+ * this locking primitives are used to protect parts
-+ * of dir's htree. protection unit is block: leaf or index
-+ */
-+static inline void *ext3_lock_htree(struct inode *dir,
-+                                      unsigned long value, int rwlock)
-+{
-+      void *lock;
-+      
-+      if (!test_opt(dir->i_sb, PDIROPS))
-+              return NULL;
-+      lock = dynlock_lock(&EXT3_I(dir)->i_htree_lock, value, 1, GFP_KERNEL);
-+      return lock;
-+}
-+
-+static inline void ext3_unlock_htree(struct inode *dir,
-+                                      void *lock)
-+{
-+      if (!test_opt(dir->i_sb, PDIROPS) || !lock)
-+              return;
-+      dynlock_unlock(&EXT3_I(dir)->i_htree_lock, lock);
-+}
-+
-+/*
-  * directories can handle most operations...
-  */
- struct inode_operations ext3_dir_inode_operations = {
-Index: linux-2.4.20/fs/ext3/super.c
-===================================================================
---- linux-2.4.20.orig/fs/ext3/super.c  2004-05-27 15:10:41.000000000 -0400
-+++ linux-2.4.20/fs/ext3/super.c       2004-05-27 15:10:45.000000000 -0400
-@@ -796,6 +796,8 @@
-                               return 0;
-                       }
-               }
-+              else if (!strcmp (this_char, "pdirops"))
-+                      set_opt (sbi->s_mount_opt, PDIROPS);
-               else if (!strcmp (this_char, "grpid") ||
-                        !strcmp (this_char, "bsdgroups"))
-                       set_opt (*mount_options, GRPID);
-@@ -822,6 +824,9 @@
-                       if (want_numeric(value, "sb", sb_block))
-                               return 0;
-               }
-+              else if (!strcmp (this_char, "pdirops")) {
-+                      set_opt (sbi->s_mount_opt, PDIROPS);
-+              }
- #ifdef CONFIG_JBD_DEBUG
-               else if (!strcmp (this_char, "ro-after")) {
-                       unsigned long v;
-@@ -985,6 +990,10 @@
-               ext3_check_inodes_bitmap (sb);
-       }
- #endif
-+#ifdef S_PDIROPS
-+      if (test_opt (sb, PDIROPS))
-+              sb->s_flags |= S_PDIROPS;
-+#endif
-       setup_ro_after(sb);
-       return res;
- }
-@@ -1484,6 +1493,11 @@
-               test_opt(sb,DATA_FLAGS) == EXT3_MOUNT_ORDERED_DATA ? "ordered":
-               "writeback");
-+      if (test_opt(sb, PDIROPS)) {
-+              printk (KERN_INFO "EXT3-fs: mounted filesystem with parallel dirops\n");
-+              sb->s_flags |= S_PDIROPS;
-+      }
-+              
-       return sb;
- failed_mount3:
-Index: linux-2.4.20/fs/ext3/inode.c
-===================================================================
---- linux-2.4.20.orig/fs/ext3/inode.c  2004-05-27 15:10:41.000000000 -0400
-+++ linux-2.4.20/fs/ext3/inode.c       2004-05-27 15:10:45.000000000 -0400
-@@ -2435,6 +2435,9 @@
-       } else if (S_ISDIR(inode->i_mode)) {
-               inode->i_op = &ext3_dir_inode_operations;
-               inode->i_fop = &ext3_dir_operations;
-+              dynlock_init(&EXT3_I(inode)->i_htree_lock);
-+              sema_init(&EXT3_I(inode)->i_rename_sem, 1);
-+              sema_init(&EXT3_I(inode)->i_append_sem, 1);
-       } else if (S_ISLNK(inode->i_mode)) {
-               if (ext3_inode_is_fast_symlink(inode))
-                       inode->i_op = &ext3_fast_symlink_inode_operations;
-Index: linux-2.4.20/fs/ext3/ialloc.c
-===================================================================
---- linux-2.4.20.orig/fs/ext3/ialloc.c 2004-05-27 15:10:39.000000000 -0400
-+++ linux-2.4.20/fs/ext3/ialloc.c      2004-05-27 15:10:45.000000000 -0400
-@@ -601,6 +601,9 @@
-               return ERR_PTR(-EDQUOT);
-       }
-       ext3_debug ("allocating inode %lu\n", inode->i_ino);
-+      dynlock_init(&EXT3_I(inode)->i_htree_lock);
-+      sema_init(&EXT3_I(inode)->i_rename_sem, 1);
-+      sema_init(&EXT3_I(inode)->i_append_sem, 1);
-       return inode;
- fail:
-Index: linux-2.4.20/include/linux/ext3_fs.h
-===================================================================
---- linux-2.4.20.orig/include/linux/ext3_fs.h  2004-05-27 15:10:40.000000000 -0400
-+++ linux-2.4.20/include/linux/ext3_fs.h       2004-05-27 15:10:45.000000000 -0400
-@@ -306,6 +306,7 @@
- /*
-  * Mount flags
-  */
-+#define EXT3_MOUNT_PDIROPS            0x800000/* Parallel dir operations */
- #define EXT3_MOUNT_CHECK              0x0001  /* Do mount-time checks */
- #define EXT3_MOUNT_GRPID              0x0004  /* Create files with directory's group */
- #define EXT3_MOUNT_DEBUG              0x0008  /* Some debugging messages */
-Index: linux-2.4.20/include/linux/ext3_fs_i.h
-===================================================================
---- linux-2.4.20.orig/include/linux/ext3_fs_i.h        2001-11-22 14:46:19.000000000 -0500
-+++ linux-2.4.20/include/linux/ext3_fs_i.h     2004-05-27 15:10:45.000000000 -0400
-@@ -17,6 +17,7 @@
- #define _LINUX_EXT3_FS_I
- #include <linux/rwsem.h>
-+#include <linux/dynlocks.h>
- /*
-  * second extended file system inode data in memory
-@@ -73,6 +74,11 @@
-        * by other means, so we have truncate_sem.
-        */
-       struct rw_semaphore truncate_sem;
-+
-+      /* following fields for parallel directory operations -bzzz */
-+      struct dynlock i_htree_lock;
-+      struct semaphore i_append_sem;
-+      struct semaphore i_rename_sem;
- };
- #endif        /* _LINUX_EXT3_FS_I */
diff --git a/lustre/kernel_patches/patches/ext3_delete_thread_2.4.20_chaos.patch b/lustre/kernel_patches/patches/ext3_delete_thread_2.4.20_chaos.patch
deleted file mode 100644 (file)
index 414d60d..0000000
+++ /dev/null
@@ -1,500 +0,0 @@
- fs/ext3/file.c             |    4 
- fs/ext3/inode.c            |  116 ++++++++++++++++++++++
- fs/ext3/super.c            |  230 +++++++++++++++++++++++++++++++++++++++++++++
- include/linux/ext3_fs.h    |    5 
- include/linux/ext3_fs_sb.h |   10 +
- 5 files changed, 365 insertions(+)
-
-Index: linux-2.4.20-rh-20.9/fs/ext3/super.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/super.c  2004-01-12 19:27:46.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/super.c       2004-01-13 17:20:31.000000000 +0300
-@@ -400,6 +400,221 @@
-       }
- }
-+#ifdef EXT3_DELETE_THREAD
-+/*
-+ * Delete inodes in a loop until there are no more to be deleted.
-+ * Normally, we run in the background doing the deletes and sleeping again,
-+ * and clients just add new inodes to be deleted onto the end of the list.
-+ * If someone is concerned about free space (e.g. block allocation or similar)
-+ * then they can sleep on s_delete_waiter_queue and be woken up when space
-+ * has been freed.
-+ */
-+int ext3_delete_thread(void *data)
-+{
-+      struct super_block *sb = data;
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      struct task_struct *tsk = current;
-+
-+      /* Almost like daemonize, but not quite */
-+      exit_mm(current);
-+      tsk->session = 1;
-+      tsk->pgrp = 1;
-+      tsk->tty = NULL;
-+      exit_files(current);
-+      reparent_to_init();
-+
-+      sprintf(tsk->comm, "kdelext3-%s", kdevname(sb->s_dev));
-+      sigfillset(&tsk->blocked);
-+
-+      /*tsk->flags |= PF_KERNTHREAD;*/
-+
-+      INIT_LIST_HEAD(&sbi->s_delete_list);
-+      wake_up(&sbi->s_delete_waiter_queue);
-+      ext3_debug("delete thread on %s started\n", kdevname(sb->s_dev));
-+
-+      /* main loop */
-+      for (;;) {
-+              wait_event_interruptible(sbi->s_delete_thread_queue,
-+                                       !list_empty(&sbi->s_delete_list) ||
-+                                       !test_opt(sb, ASYNCDEL));
-+              ext3_debug("%s woken up: %lu inodes, %lu blocks\n",
-+                         tsk->comm,sbi->s_delete_inodes,sbi->s_delete_blocks);
-+
-+              spin_lock(&sbi->s_delete_lock);
-+              if (list_empty(&sbi->s_delete_list)) {
-+                      clear_opt(sbi->s_mount_opt, ASYNCDEL);
-+                      memset(&sbi->s_delete_list, 0,
-+                             sizeof(sbi->s_delete_list));
-+                      spin_unlock(&sbi->s_delete_lock);
-+                      ext3_debug("delete thread on %s exiting\n",
-+                                 kdevname(sb->s_dev));
-+                      wake_up(&sbi->s_delete_waiter_queue);
-+                      break;
-+              }
-+
-+              while (!list_empty(&sbi->s_delete_list)) {
-+                      struct inode *inode=list_entry(sbi->s_delete_list.next,
-+                                                     struct inode, i_dentry);
-+                      unsigned long blocks = inode->i_blocks >>
-+                                                      (inode->i_blkbits - 9);
-+
-+                      list_del_init(&inode->i_dentry);
-+                      spin_unlock(&sbi->s_delete_lock);
-+                      ext3_debug("%s delete ino %lu blk %lu\n",
-+                                 tsk->comm, inode->i_ino, blocks);
-+
-+                      iput(inode);
-+
-+                      spin_lock(&sbi->s_delete_lock);
-+                      sbi->s_delete_blocks -= blocks;
-+                      sbi->s_delete_inodes--;
-+              }
-+              if (sbi->s_delete_blocks != 0 || sbi->s_delete_inodes != 0) {
-+                      ext3_warning(sb, __FUNCTION__,
-+                                   "%lu blocks, %lu inodes on list?\n",
-+                                   sbi->s_delete_blocks,sbi->s_delete_inodes);
-+                      sbi->s_delete_blocks = 0;
-+                      sbi->s_delete_inodes = 0;
-+              }
-+              spin_unlock(&sbi->s_delete_lock);
-+              wake_up(&sbi->s_delete_waiter_queue);
-+      }
-+
-+      return 0;
-+}
-+
-+static void ext3_start_delete_thread(struct super_block *sb)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(sb);
-+      int rc;
-+
-+      spin_lock_init(&sbi->s_delete_lock);
-+      init_waitqueue_head(&sbi->s_delete_thread_queue);
-+      init_waitqueue_head(&sbi->s_delete_waiter_queue);
-+
-+      if (!test_opt(sb, ASYNCDEL))
-+              return;
-+
-+      rc = kernel_thread(ext3_delete_thread, sb, CLONE_VM | CLONE_FILES);
-+      if (rc < 0)
-+              printk(KERN_ERR "EXT3-fs: cannot start delete thread: rc %d\n",
-+                     rc);
-+      else
-+              wait_event(sbi->s_delete_waiter_queue, sbi->s_delete_list.next);
-+}
-+
-+static void ext3_stop_delete_thread(struct ext3_sb_info *sbi)
-+{
-+      if (sbi->s_delete_list.next == 0)       /* thread never started */
-+              return;
-+
-+      clear_opt(sbi->s_mount_opt, ASYNCDEL);
-+      wake_up(&sbi->s_delete_thread_queue);
-+      wait_event(sbi->s_delete_waiter_queue,
-+                      sbi->s_delete_list.next == 0 && sbi->s_delete_inodes == 0);
-+}
-+
-+/* Instead of playing games with the inode flags, destruction, etc we just
-+ * create a new inode locally and put it on a list for the truncate thread.
-+ * We need large parts of the inode struct in order to complete the
-+ * truncate and unlink, so we may as well just have a real inode to do it.
-+ *
-+ * If we have any problem deferring the delete, just delete it right away.
-+ * If we defer it, we also mark how many blocks it would free, so that we
-+ * can keep the statfs data correct, and we know if we should sleep on the
-+ * delete thread when we run out of space.
-+ */
-+static void ext3_delete_inode_thread(struct inode *old_inode)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(old_inode->i_sb);
-+      struct ext3_inode_info *nei, *oei = EXT3_I(old_inode);
-+      struct inode *new_inode;
-+      unsigned long blocks = old_inode->i_blocks >> (old_inode->i_blkbits-9);
-+
-+      if (is_bad_inode(old_inode)) {
-+              clear_inode(old_inode);
-+              return;
-+      }
-+
-+      if (!test_opt(old_inode->i_sb, ASYNCDEL) || !sbi->s_delete_list.next)
-+              goto out_delete;
-+
-+      /* We may want to delete the inode immediately and not defer it */
-+      if (IS_SYNC(old_inode) || blocks <= EXT3_NDIR_BLOCKS)
-+              goto out_delete;
-+
-+      /* We can't use the delete thread as-is during real orphan recovery,
-+       * as we add to the orphan list here, causing ext3_orphan_cleanup()
-+       * to loop endlessly.  It would be nice to do so, but needs work.
-+       */
-+      if (oei->i_state & EXT3_STATE_DELETE ||
-+          sbi->s_mount_state & EXT3_ORPHAN_FS) {
-+              ext3_debug("doing deferred inode %lu delete (%lu blocks)\n",
-+                         old_inode->i_ino, blocks);
-+              goto out_delete;
-+      }
-+
-+      /* We can iget this inode again here, because our caller has unhashed
-+       * old_inode, so new_inode will be in a different inode struct.
-+       *
-+       * We need to ensure that the i_orphan pointers in the other inodes
-+       * point at the new inode copy instead of the old one so the orphan
-+       * list doesn't get corrupted when the old orphan inode is freed.
-+       */
-+      down(&sbi->s_orphan_lock);
-+
-+      sbi->s_mount_state |= EXT3_ORPHAN_FS;
-+      new_inode = iget(old_inode->i_sb, old_inode->i_ino);
-+      sbi->s_mount_state &= ~EXT3_ORPHAN_FS;
-+      if (is_bad_inode(new_inode)) {
-+              printk(KERN_WARNING "read bad inode %lu\n", old_inode->i_ino);
-+              iput(new_inode);
-+              new_inode = NULL;
-+      }
-+      if (!new_inode) {
-+              up(&sbi->s_orphan_lock);
-+              ext3_debug("delete inode %lu directly (bad read)\n",
-+                         old_inode->i_ino);
-+              goto out_delete;
-+      }
-+      J_ASSERT(new_inode != old_inode);
-+
-+      J_ASSERT(!list_empty(&oei->i_orphan));
-+
-+      nei = EXT3_I(new_inode);
-+      /* Ugh.  We need to insert new_inode into the same spot on the list
-+       * as old_inode was, to ensure the in-memory orphan list is still
-+       * in the same order as the on-disk orphan list (badness otherwise).
-+       */
-+      nei->i_orphan = oei->i_orphan;
-+      nei->i_orphan.next->prev = &nei->i_orphan;
-+      nei->i_orphan.prev->next = &nei->i_orphan;
-+      nei->i_state |= EXT3_STATE_DELETE;
-+      up(&sbi->s_orphan_lock);
-+
-+      clear_inode(old_inode);
-+
-+      spin_lock(&sbi->s_delete_lock);
-+      J_ASSERT(list_empty(&new_inode->i_dentry));
-+      list_add_tail(&new_inode->i_dentry, &sbi->s_delete_list);
-+      sbi->s_delete_blocks += blocks;
-+      sbi->s_delete_inodes++;
-+      spin_unlock(&sbi->s_delete_lock);
-+
-+      ext3_debug("delete inode %lu (%lu blocks) by thread\n",
-+                 new_inode->i_ino, blocks);
-+
-+      wake_up(&sbi->s_delete_thread_queue);
-+      return;
-+
-+out_delete:
-+      ext3_delete_inode(old_inode);
-+}
-+#else
-+#define ext3_start_delete_thread(sbi) do {} while(0)
-+#define ext3_stop_delete_thread(sbi) do {} while(0)
-+#endif /* EXT3_DELETE_THREAD */
-+
- void ext3_put_super (struct super_block * sb)
- {
-       struct ext3_sb_info *sbi = EXT3_SB(sb);
-@@ -407,6 +622,7 @@
-       kdev_t j_dev = sbi->s_journal->j_dev;
-       int i;
-+      J_ASSERT(sbi->s_delete_inodes == 0);
-       ext3_xattr_put_super(sb);
-       journal_destroy(sbi->s_journal);
-       if (!(sb->s_flags & MS_RDONLY)) {
-@@ -455,7 +671,11 @@
-       write_inode:    ext3_write_inode,       /* BKL not held.  Don't need */
-       dirty_inode:    ext3_dirty_inode,       /* BKL not held.  We take it */
-       put_inode:      ext3_put_inode,         /* BKL not held.  Don't need */
-+#ifdef EXT3_DELETE_THREAD
-+      delete_inode:   ext3_delete_inode_thread,/* BKL not held. We take it */
-+#else
-       delete_inode:   ext3_delete_inode,      /* BKL not held.  We take it */
-+#endif
-       put_super:      ext3_put_super,         /* BKL held */
-       write_super:    ext3_write_super,       /* BKL held */
-       sync_fs:        ext3_sync_fs,
-@@ -524,6 +744,13 @@
-                       clear_opt (*mount_options, XATTR_USER);
-               else
- #endif
-+#ifdef EXT3_DELETE_THREAD
-+              if (!strcmp(this_char, "asyncdel"))
-+                      set_opt(*mount_options, ASYNCDEL);
-+              else if (!strcmp(this_char, "noasyncdel"))
-+                      clear_opt(*mount_options, ASYNCDEL);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -1223,6 +1450,7 @@
-       }
-       ext3_setup_super (sb, es, sb->s_flags & MS_RDONLY);
-+      ext3_start_delete_thread(sb);
-       /*
-        * akpm: core read_super() calls in here with the superblock locked.
-        * That deadlocks, because orphan cleanup needs to lock the superblock
-@@ -1614,7 +1842,12 @@
- static int ext3_sync_fs(struct super_block *sb)
- {
-       tid_t target;
--      
-+
-+      if (atomic_read(&sb->s_active) == 0) {
-+              /* fs is being umounted: time to stop delete thread */
-+              ext3_stop_delete_thread(EXT3_SB(sb));
-+      }
-+
-       sb->s_dirt = 0;
-       target = log_start_commit(EXT3_SB(sb)->s_journal, NULL);
-       log_wait_commit(EXT3_SB(sb)->s_journal, target);
-@@ -1678,6 +1911,9 @@
-       if (!parse_options(data, &tmp, sbi, &tmp, 1))
-               return -EINVAL;
-+      if (!test_opt(sb, ASYNCDEL) || (*flags & MS_RDONLY))
-+              ext3_stop_delete_thread(sbi);
-+
-       if (sbi->s_mount_opt & EXT3_MOUNT_ABORT)
-               ext3_abort(sb, __FUNCTION__, "Abort forced by user");
-Index: linux-2.4.20-rh-20.9/fs/ext3/inode.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/inode.c  2004-01-12 19:27:46.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/inode.c       2004-01-13 17:15:48.000000000 +0300
-@@ -2017,6 +2017,122 @@
-       ext3_journal_stop(handle, inode);
- }
-+#ifdef EXT3_DELETE_THREAD
-+/* Move blocks from to-be-truncated inode over to a new inode, and delete
-+ * that one from the delete thread instead.  This avoids a lot of latency
-+ * when truncating large files.
-+ *
-+ * If we have any problem deferring the truncate, just truncate it right away.
-+ * If we defer it, we also mark how many blocks it would free, so that we
-+ * can keep the statfs data correct, and we know if we should sleep on the
-+ * delete thread when we run out of space.
-+ *
-+ * During normal filesystem usage, we are always called here with a
-+ * transaction already started.  The only time ext3_truncate is called
-+ * without a started transaction is from ext3_orphan_cleanup(), and we
-+ * currently just do a direct truncate in that case.
-+ */
-+void ext3_truncate_thread(struct inode *old_inode)
-+{
-+      struct ext3_sb_info *sbi = EXT3_SB(old_inode->i_sb);
-+      struct ext3_inode_info *nei, *oei = EXT3_I(old_inode);
-+      struct inode *new_inode;
-+      handle_t *handle;
-+      unsigned long blocks = old_inode->i_blocks >> (old_inode->i_blkbits-9);
-+
-+      if (!test_opt(old_inode->i_sb, ASYNCDEL) || !sbi->s_delete_list.next)
-+              goto out_truncate;
-+
-+      /* XXX This is a temporary limitation for code simplicity.
-+       *     We could truncate to arbitrary sizes at some later time.
-+       */
-+      if (old_inode->i_size != 0)
-+              goto out_truncate;
-+
-+      /* We may want to truncate the inode immediately and not defer it */
-+      if (IS_SYNC(old_inode) || blocks <= EXT3_NDIR_BLOCKS ||
-+          old_inode->i_size > oei->i_disksize)
-+              goto out_truncate;
-+
-+      /* We can't use the delete thread as-is during real orphan recovery,
-+       * as we add to the orphan list here, causing ext3_orphan_cleanup()
-+       * to loop endlessly.  It would be nice to do so, but needs work.
-+       */
-+      if (oei->i_state & EXT3_STATE_DELETE ||
-+          sbi->s_mount_state & EXT3_ORPHAN_FS) {
-+              ext3_debug("doing deferred inode %lu delete (%lu blocks)\n",
-+                         old_inode->i_ino, blocks);
-+              goto out_truncate;
-+      }
-+
-+      ext3_discard_prealloc(old_inode);
-+
-+      /* old_inode   = 1
-+       * new_inode   = sb + GDT + ibitmap
-+       * orphan list = 1 inode/superblock for add, 2 inodes for del
-+       * quota files = 2 * EXT3_SINGLEDATA_TRANS_BLOCKS
-+       */
-+      handle = ext3_journal_start(old_inode, 7);
-+      if (IS_ERR(handle))
-+              goto out_truncate;
-+
-+      new_inode = ext3_new_inode(handle, old_inode, old_inode->i_mode);
-+      if (IS_ERR(new_inode)) {
-+              ext3_debug("truncate inode %lu directly (no new inodes)\n",
-+                         old_inode->i_ino);
-+              goto out_journal;
-+      }
-+
-+      if (ext3_orphan_add(handle, new_inode) < 0)
-+              goto out_journal;
-+
-+      if (ext3_orphan_del(handle, old_inode) < 0) {
-+              ext3_orphan_del(handle, new_inode);
-+              iput(new_inode);
-+              goto out_journal;
-+      }
-+
-+      nei = EXT3_I(new_inode);
-+
-+      down_write(&oei->truncate_sem);
-+      new_inode->i_size = old_inode->i_size;
-+      new_inode->i_blocks = old_inode->i_blocks;
-+      new_inode->i_uid = old_inode->i_uid;
-+      new_inode->i_gid = old_inode->i_gid;
-+      new_inode->i_nlink = 0;
-+
-+      /* FIXME when we do arbitrary truncates */
-+      old_inode->i_blocks = oei->i_file_acl ? old_inode->i_blksize / 512 : 0;
-+
-+      memcpy(nei->i_data, oei->i_data, sizeof(nei->i_data));
-+      memset(oei->i_data, 0, sizeof(oei->i_data));
-+
-+      nei->i_disksize = oei->i_disksize;
-+      nei->i_state |= EXT3_STATE_DELETE;
-+      up_write(&oei->truncate_sem);
-+
-+      ext3_journal_stop(handle, old_inode);
-+
-+      spin_lock(&sbi->s_delete_lock);
-+      J_ASSERT(list_empty(&new_inode->i_dentry));
-+      list_add_tail(&new_inode->i_dentry, &sbi->s_delete_list);
-+      sbi->s_delete_blocks += blocks;
-+      sbi->s_delete_inodes++;
-+      spin_unlock(&sbi->s_delete_lock);
-+
-+      ext3_debug("delete inode %lu (%lu blocks) by thread\n",
-+                 new_inode->i_ino, blocks);
-+
-+      wake_up(&sbi->s_delete_thread_queue);
-+      return;
-+
-+out_journal:
-+      ext3_journal_stop(handle, old_inode);
-+out_truncate:
-+      ext3_truncate(old_inode);
-+}
-+#endif /* EXT3_DELETE_THREAD */
-+
- /* 
-  * ext3_get_inode_loc returns with an extra refcount against the
-  * inode's underlying buffer_head on success. 
-Index: linux-2.4.20-rh-20.9/fs/ext3/file.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/fs/ext3/file.c   2004-01-12 19:27:46.000000000 +0300
-+++ linux-2.4.20-rh-20.9/fs/ext3/file.c        2004-01-13 17:15:48.000000000 +0300
-@@ -125,7 +125,11 @@
- };
- struct inode_operations ext3_file_inode_operations = {
-+#ifdef EXT3_DELETE_THREAD
-+      truncate:       ext3_truncate_thread,   /* BKL held */
-+#else
-       truncate:       ext3_truncate,          /* BKL held */
-+#endif
-       setattr:        ext3_setattr,           /* BKL held */
-       setxattr:       ext3_setxattr,          /* BKL held */
-       getxattr:       ext3_getxattr,          /* BKL held */
-Index: linux-2.4.20-rh-20.9/include/linux/ext3_fs.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/linux/ext3_fs.h  2004-01-12 19:27:46.000000000 +0300
-+++ linux-2.4.20-rh-20.9/include/linux/ext3_fs.h       2004-01-13 17:15:48.000000000 +0300
-@@ -193,6 +193,7 @@
-  */
- #define EXT3_STATE_JDATA              0x00000001 /* journaled data exists */
- #define EXT3_STATE_NEW                        0x00000002 /* inode is newly created */
-+#define EXT3_STATE_DELETE             0x00000010 /* deferred delete inode */
- /*
-  * ioctl commands
-@@ -320,6 +321,7 @@
- #define EXT3_MOUNT_UPDATE_JOURNAL     0x1000  /* Update the journal format */
- #define EXT3_MOUNT_NO_UID32           0x2000  /* Disable 32-bit UIDs */
- #define EXT3_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
-+#define EXT3_MOUNT_ASYNCDEL           0x20000 /* Delayed deletion */
- /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
- #ifndef _LINUX_EXT2_FS_H
-@@ -695,6 +697,9 @@
- extern void ext3_dirty_inode(struct inode *);
- extern int ext3_change_inode_journal_flag(struct inode *, int);
- extern void ext3_truncate (struct inode *);
-+#ifdef EXT3_DELETE_THREAD
-+extern void ext3_truncate_thread(struct inode *inode);
-+#endif
- extern void ext3_set_inode_flags(struct inode *);
- /* ioctl.c */
-Index: linux-2.4.20-rh-20.9/include/linux/ext3_fs_sb.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/linux/ext3_fs_sb.h       2004-01-12 19:27:46.000000000 +0300
-+++ linux-2.4.20-rh-20.9/include/linux/ext3_fs_sb.h    2004-01-13 17:15:48.000000000 +0300
-@@ -29,6 +29,8 @@
- #define EXT3_MAX_GROUP_LOADED 32
-+#define EXT3_DELETE_THREAD
-+
- /*
-  * third extended-fs super-block data in memory
-  */
-@@ -76,6 +78,14 @@
-       struct timer_list turn_ro_timer;        /* For turning read-only (crash simulation) */
-       wait_queue_head_t ro_wait_queue;        /* For people waiting for the fs to go read-only */
- #endif
-+#ifdef EXT3_DELETE_THREAD
-+      spinlock_t s_delete_lock;
-+      struct list_head s_delete_list;
-+      unsigned long s_delete_blocks;
-+      unsigned long s_delete_inodes;
-+      wait_queue_head_t s_delete_thread_queue;
-+      wait_queue_head_t s_delete_waiter_queue;
-+#endif
- };
- #endif        /* _LINUX_EXT3_FS_SB */
diff --git a/lustre/kernel_patches/patches/ext3_orphan_lock-2.4.20-rh.patch b/lustre/kernel_patches/patches/ext3_orphan_lock-2.4.20-rh.patch
deleted file mode 100644 (file)
index d029650..0000000
+++ /dev/null
@@ -1,82 +0,0 @@
- fs/ext3/namei.c            |   15 +++++++--------
- fs/ext3/super.c            |    1 +
- include/linux/ext3_fs_sb.h |    1 +
- 3 files changed, 9 insertions(+), 8 deletions(-)
-
---- linux-rh-2.4.20-8/fs/ext3/namei.c~ext3_orphan_lock-2.4.20-rh       2003-05-05 19:49:15.000000000 +0800
-+++ linux-rh-2.4.20-8-root/fs/ext3/namei.c     2003-05-05 20:01:28.000000000 +0800
-@@ -1747,8 +1747,8 @@ int ext3_orphan_add(handle_t *handle, st
-       struct super_block *sb = inode->i_sb;
-       struct ext3_iloc iloc;
-       int err = 0, rc;
--      
--      lock_super(sb);
-+
-+      down(&EXT3_SB(sb)->s_orphan_lock);
-       if (!list_empty(&EXT3_I(inode)->i_orphan))
-               goto out_unlock;
-@@ -1796,7 +1796,7 @@ int ext3_orphan_add(handle_t *handle, st
-       jbd_debug(4, "orphan inode %ld will point to %d\n",
-                       inode->i_ino, NEXT_ORPHAN(inode));
- out_unlock:
--      unlock_super(sb);
-+      up(&EXT3_SB(sb)->s_orphan_lock);
-       ext3_std_error(inode->i_sb, err);
-       return err;
- }
-@@ -1809,20 +1809,19 @@ int ext3_orphan_del(handle_t *handle, st
- {
-       struct list_head *prev;
-       struct ext3_inode_info *ei = EXT3_I(inode);
--      struct ext3_sb_info *sbi;
-+      struct ext3_sb_info *sbi = EXT3_SB(inode->i_sb);
-       unsigned long ino_next;
-       struct ext3_iloc iloc;
-       int err = 0;
--      lock_super(inode->i_sb);
-+      down(&sbi->s_orphan_lock);
-       if (list_empty(&ei->i_orphan)) {
--              unlock_super(inode->i_sb);
-+              up(&sbi->s_orphan_lock);
-               return 0;
-       }
-       ino_next = NEXT_ORPHAN(inode);
-       prev = ei->i_orphan.prev;
--      sbi = EXT3_SB(inode->i_sb);
-       jbd_debug(4, "remove inode %lu from orphan list\n", inode->i_ino);
-@@ -1871,7 +1870,7 @@ int ext3_orphan_del(handle_t *handle, st
- out_err:
-       ext3_std_error(inode->i_sb, err);
- out:
--      unlock_super(inode->i_sb);
-+      up(&sbi->s_orphan_lock);
-       return err;
- out_brelse:
---- linux-rh-2.4.20-8/fs/ext3/super.c~ext3_orphan_lock-2.4.20-rh       2003-05-05 19:49:15.000000000 +0800
-+++ linux-rh-2.4.20-8-root/fs/ext3/super.c     2003-05-05 19:54:09.000000000 +0800
-@@ -1151,6 +1151,7 @@ struct super_block * ext3_read_super (st
-        */
-       sb->s_op = &ext3_sops;
-       INIT_LIST_HEAD(&sbi->s_orphan); /* unlinked but open files */
-+      sema_init(&sbi->s_orphan_lock, 1);
-       sb->s_root = 0;
---- linux-rh-2.4.20-8/include/linux/ext3_fs_sb.h~ext3_orphan_lock-2.4.20-rh    2003-05-05 19:49:07.000000000 +0800
-+++ linux-rh-2.4.20-8-root/include/linux/ext3_fs_sb.h  2003-05-05 19:54:09.000000000 +0800
-@@ -69,6 +69,7 @@ struct ext3_sb_info {
-       struct inode * s_journal_inode;
-       struct journal_s * s_journal;
-       struct list_head s_orphan;
-+      struct semaphore s_orphan_lock;
-       unsigned long s_commit_interval;
-       struct block_device *journal_bdev;
- #ifdef CONFIG_JBD_DEBUG
-
-_
diff --git a/lustre/kernel_patches/patches/extN-wantedi-2.4.22-rh.patch b/lustre/kernel_patches/patches/extN-wantedi-2.4.22-rh.patch
deleted file mode 100644 (file)
index 5ec4dab..0000000
+++ /dev/null
@@ -1,217 +0,0 @@
- fs/ext3/ialloc.c        |   41 +++++++++++++++++++++++++++++++++++++++--
- fs/ext3/inode.c         |    2 +-
- fs/ext3/ioctl.c         |   25 +++++++++++++++++++++++++
- fs/ext3/namei.c         |   21 +++++++++++++++++----
- include/linux/dcache.h  |    5 +++++
- include/linux/ext3_fs.h |    5 ++++-
- 6 files changed, 91 insertions(+), 8 deletions(-)
-
---- linux-2.4.22-ac1/fs/ext3/ialloc.c~extN-wantedi-2.4.22-rh   2003-09-26 00:57:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/ialloc.c   2003-09-26 01:00:17.000000000 +0400
-@@ -524,7 +524,8 @@ static int find_group_other(struct super
-  * group to find a free inode.
-  */
- struct inode * ext3_new_inode (handle_t *handle,
--                              const struct inode * dir, int mode)
-+                              const struct inode * dir, int mode,
-+                              unsigned long goal)
- {
-       struct super_block * sb;
-       struct buffer_head * bh;
-@@ -549,7 +550,41 @@ struct inode * ext3_new_inode (handle_t 
-       init_rwsem(&inode->u.ext3_i.truncate_sem);
-       lock_super (sb);
--      es = sb->u.ext3_sb.s_es;
-+      es = EXT3_SB(sb)->s_es;
-+
-+      if (goal) {
-+              group = (goal - 1) / EXT3_INODES_PER_GROUP(sb);
-+              ino = (goal - 1) % EXT3_INODES_PER_GROUP(sb);
-+              gdp = ext3_get_group_desc(sb, group, &bh2);
-+
-+              bitmap_nr = load_inode_bitmap (sb, group);
-+              if (bitmap_nr < 0) {
-+                      err = bitmap_nr;
-+                      goto fail;
-+              }
-+
-+              bh = EXT3_SB(sb)->s_inode_bitmap[bitmap_nr];
-+
-+              BUFFER_TRACE(bh, "get_write_access");
-+              err = ext3_journal_get_write_access(handle, bh);
-+              if (err) goto fail;
-+
-+              if (ext3_set_bit(ino, bh->b_data)) {
-+                      printk(KERN_ERR "goal inode %lu unavailable\n", goal);
-+                      /* Oh well, we tried. */
-+                      goto repeat;
-+              }
-+
-+              BUFFER_TRACE(bh, "call ext3_journal_dirty_metadata");
-+              err = ext3_journal_dirty_metadata(handle, bh);
-+              if (err) goto fail;
-+
-+              /* We've shortcircuited the allocation system successfully,
-+               * now finish filling in the inode.
-+               */
-+              goto have_bit_and_group;
-+      }
-+
- repeat:
-       if (S_ISDIR(mode)) {
-               if (test_opt (sb, OLDALLOC))
-@@ -606,6 +641,8 @@ repeat:
-               }
-               goto repeat;
-       }
-+
-+have_bit_and_group:
-       ino += group * EXT3_INODES_PER_GROUP(sb) + 1;
-       if (ino < EXT3_FIRST_INO(sb) || ino > le32_to_cpu(es->s_inodes_count)) {
-               ext3_error (sb, "ext3_new_inode",
---- linux-2.4.22-ac1/fs/ext3/inode.c~extN-wantedi-2.4.22-rh    2003-09-26 00:57:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/inode.c    2003-09-26 00:57:29.000000000 +0400
-@@ -2614,7 +2614,7 @@ void ext3_truncate_thread(struct inode *
-       if (IS_ERR(handle))
-               goto out_truncate;
--      new_inode = ext3_new_inode(handle, old_inode, old_inode->i_mode);
-+      new_inode = ext3_new_inode(handle, old_inode, old_inode->i_mode, 0);
-       if (IS_ERR(new_inode)) {
-               ext3_debug("truncate inode %lu directly (no new inodes)\n",
-                          old_inode->i_ino);
---- linux-2.4.22-ac1/fs/ext3/ioctl.c~extN-wantedi-2.4.22-rh    2003-09-25 14:16:23.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/ioctl.c    2003-09-26 00:57:29.000000000 +0400
-@@ -23,6 +23,31 @@ int ext3_ioctl (struct inode * inode, st
-       ext3_debug ("cmd = %u, arg = %lu\n", cmd, arg);
-       switch (cmd) {
-+      case EXT3_IOC_CREATE_INUM: {
-+              char name[32];
-+              struct dentry *dchild, *dparent;
-+              int rc = 0;
-+
-+              dparent = list_entry(inode->i_dentry.next, struct dentry,
-+                                   d_alias);
-+              snprintf(name, sizeof name, "%lu", arg);
-+              dchild = lookup_one_len(name, dparent, strlen(name));
-+              if (dchild->d_inode) {
-+                      printk(KERN_ERR "%*s/%lu already exists (ino %lu)\n",
-+                             dparent->d_name.len, dparent->d_name.name, arg,
-+                             dchild->d_inode->i_ino);
-+                      rc = -EEXIST;
-+              } else {
-+                      dchild->d_fsdata = (void *)arg;
-+                      rc = vfs_create(inode, dchild, 0644);
-+                      if (rc)
-+                              printk(KERN_ERR "vfs_create: %d\n", rc);
-+                      else if (dchild->d_inode->i_ino != arg)
-+                              rc = -EEXIST;
-+              }
-+              dput(dchild);
-+              return rc;
-+      }
-       case EXT3_IOC_GETFLAGS:
-               flags = inode->u.ext3_i.i_flags & EXT3_FL_USER_VISIBLE;
-               return put_user(flags, (int *) arg);
---- linux-2.4.22-ac1/fs/ext3/namei.c~extN-wantedi-2.4.22-rh    2003-09-26 00:57:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/namei.c    2003-09-26 00:57:29.000000000 +0400
-@@ -1534,6 +1534,19 @@ static int ext3_add_nondir(handle_t *han
-       return err;
- }
-+static struct inode * ext3_new_inode_wantedi(handle_t *handle, struct inode *dir,
-+                                              int mode, struct dentry *dentry)
-+{
-+      unsigned long inum = 0;
-+
-+      if (dentry->d_fsdata != NULL) {
-+              struct dentry_params *param =
-+                      (struct dentry_params *) dentry->d_fsdata;
-+              inum = param->p_inum;
-+      }
-+      return ext3_new_inode(handle, dir, mode, inum);
-+}
-+
- /*
-  * By the time this is called, we already have created
-  * the directory cache entry for the new file, but it
-@@ -1557,7 +1570,7 @@ static int ext3_create (struct inode * d
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
--      inode = ext3_new_inode (handle, dir, mode);
-+      inode = ext3_new_inode_wantedi (handle, dir, mode, dentry);
-       err = PTR_ERR(inode);
-       if (!IS_ERR(inode)) {
-               inode->i_op = &ext3_file_inode_operations;
-@@ -1585,7 +1598,7 @@ static int ext3_mknod (struct inode * di
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
--      inode = ext3_new_inode (handle, dir, mode);
-+      inode = ext3_new_inode_wantedi (handle, dir, mode, dentry);
-       err = PTR_ERR(inode);
-       if (!IS_ERR(inode)) {
-               init_special_inode(inode, mode, rdev);
-@@ -1615,7 +1628,7 @@ static int ext3_mkdir(struct inode * dir
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
--      inode = ext3_new_inode (handle, dir, S_IFDIR | mode);
-+      inode = ext3_new_inode_wantedi (handle, dir, S_IFDIR | mode, dentry);
-       err = PTR_ERR(inode);
-       if (IS_ERR(inode))
-               goto out_stop;
-@@ -2010,7 +2023,7 @@ static int ext3_symlink (struct inode * 
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
--      inode = ext3_new_inode (handle, dir, S_IFLNK|S_IRWXUGO);
-+      inode = ext3_new_inode_wantedi (handle, dir, S_IFLNK|S_IRWXUGO, dentry);
-       err = PTR_ERR(inode);
-       if (IS_ERR(inode))
-               goto out_stop;
---- linux-2.4.22-ac1/include/linux/dcache.h~extN-wantedi-2.4.22-rh     2003-09-26 00:57:27.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/dcache.h     2003-09-26 00:57:29.000000000 +0400
-@@ -63,6 +63,11 @@ static inline void intent_init(struct lo
- #define IS_ROOT(x) ((x) == (x)->d_parent)
-+struct dentry_params {
-+      unsigned long   p_inum;
-+      void            *p_ptr;
-+};
-+
- /*
-  * "quick string" -- eases parameter passing, but more importantly
-  * saves "metadata" about the string (ie length and the hash).
---- linux-2.4.22-ac1/include/linux/ext3_fs.h~extN-wantedi-2.4.22-rh    2003-09-26 00:57:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/ext3_fs.h    2003-09-26 00:57:29.000000000 +0400
-@@ -203,6 +203,7 @@ struct ext3_group_desc
- #define       EXT3_IOC_SETFLAGS               _IOW('f', 2, long)
- #define       EXT3_IOC_GETVERSION             _IOR('f', 3, long)
- #define       EXT3_IOC_SETVERSION             _IOW('f', 4, long)
-+/* EXT3_IOC_CREATE_INUM at bottom of file (visible to kernel and user). */
- #define       EXT3_IOC_GETVERSION_OLD         _IOR('v', 1, long)
- #define       EXT3_IOC_SETVERSION_OLD         _IOW('v', 2, long)
- #ifdef CONFIG_JBD_DEBUG
-@@ -676,7 +677,8 @@ extern int ext3fs_dirhash(const char *na
-                         dx_hash_info *hinfo);
- /* ialloc.c */
--extern struct inode * ext3_new_inode (handle_t *, const struct inode *, int);
-+extern struct inode * ext3_new_inode (handle_t *, const struct inode *, int,
-+                                    unsigned long);
- extern void ext3_free_inode (handle_t *, struct inode *);
- extern struct inode * ext3_orphan_get (struct super_block *, unsigned long);
- extern unsigned long ext3_count_free_inodes (struct super_block *);
-@@ -769,4 +771,5 @@ extern struct inode_operations ext3_fast
- #endif        /* __KERNEL__ */
-+#define EXT3_IOC_CREATE_INUM                  _IOW('f', 5, long)
- #endif        /* _LINUX_EXT3_FS_H */
-
-_
diff --git a/lustre/kernel_patches/patches/gpl_header-chaos-2.4.20.patch b/lustre/kernel_patches/patches/gpl_header-chaos-2.4.20.patch
deleted file mode 100644 (file)
index 95213ba..0000000
+++ /dev/null
@@ -1,11 +0,0 @@
---- kernel-2.4.20-6chaos_18_7/include/linux/module.h~gpl-header        Wed Jul 16 03:54:37 2003
-+++ kernel-2.4.20-6chaos_18_7/include/linux/module.h   Wed Jul 16 03:55:45 2003
-@@ -288,7 +288,7 @@
- "license=" license
- #define GPL_HEADER() \
--static const char cpyright="This software may be freely redistributed under the terms of the GNU General Public License.";
-+static const char cpyright[]="This software may be freely redistributed under the terms of the GNU General Public License.";
- /* Define the module variable, and usage macros.  */
- extern struct module __this_module;
diff --git a/lustre/kernel_patches/patches/iod-rmap-exports-2.4.20.patch b/lustre/kernel_patches/patches/iod-rmap-exports-2.4.20.patch
deleted file mode 100644 (file)
index 3fdf3fd..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
- fs/Makefile     |    4 +++-
- fs/inode.c      |    4 +++-
- mm/Makefile     |    2 +-
- mm/page_alloc.c |    1 +
- mm/vmscan.c     |    3 +++
- 5 files changed, 11 insertions(+), 3 deletions(-)
-
---- linux-rh-2.4.20-6/fs/inode.c~iod-rmap-exports      Tue Apr  1 01:01:56 2003
-+++ linux-rh-2.4.20-6-braam/fs/inode.c Tue Apr  1 01:01:56 2003
-@@ -5,6 +5,7 @@
-  */
- #include <linux/config.h>
-+#include <linux/module.h>
- #include <linux/fs.h>
- #include <linux/string.h>
- #include <linux/mm.h>
-@@ -66,7 +67,8 @@ static LIST_HEAD(anon_hash_chain); /* fo
-  * NOTE! You also have to own the lock if you change
-  * the i_state of an inode while it is in use..
-  */
--static spinlock_t inode_lock = SPIN_LOCK_UNLOCKED;
-+spinlock_t inode_lock = SPIN_LOCK_UNLOCKED;
-+EXPORT_SYMBOL(inode_lock);
- /*
-  * Statistics gathering..
---- linux-rh-2.4.20-6/fs/Makefile~iod-rmap-exports     Tue Apr  1 01:01:56 2003
-+++ linux-rh-2.4.20-6-braam/fs/Makefile        Tue Apr  1 01:02:34 2003
-@@ -1,3 +1,5 @@
-+
-+
- #
- # Makefile for the Linux filesystems.
- #
-@@ -7,7 +9,7 @@
- O_TARGET := fs.o
--export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o
-+export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o inode.o
- mod-subdirs :=        nls
- obj-y :=      open.o read_write.o devices.o file_table.o buffer.o \
---- linux-rh-2.4.20-6/mm/vmscan.c~iod-rmap-exports     Tue Apr  1 01:01:56 2003
-+++ linux-rh-2.4.20-6-braam/mm/vmscan.c        Tue Apr  1 01:01:56 2003
-@@ -15,6 +15,8 @@
-  *  O(1) rmap vm, Arjan van de ven <arjanv@redhat.com>
-  */
-+#include <linux/config.h>
-+#include <linux/module.h>
- #include <linux/slab.h>
- #include <linux/kernel_stat.h>
- #include <linux/swap.h>
-@@ -1061,6 +1063,7 @@ void wakeup_kswapd(unsigned int gfp_mask
-       set_current_state(TASK_RUNNING);
-       remove_wait_queue(&kswapd_done, &wait);
- }
-+EXPORT_SYMBOL(wakeup_kswapd);
- static void wakeup_memwaiters(void)
- {
---- linux-rh-2.4.20-6/mm/Makefile~iod-rmap-exports     Tue Apr  1 01:01:56 2003
-+++ linux-rh-2.4.20-6-braam/mm/Makefile        Tue Apr  1 01:01:56 2003
-@@ -9,7 +9,7 @@
- O_TARGET := mm.o
--export-objs := shmem.o filemap.o memory.o page_alloc.o mempool.o
-+export-objs := shmem.o filemap.o memory.o page_alloc.o mempool.o vmscan.o
- obj-y  := memory.o mmap.o filemap.o mprotect.o mlock.o mremap.o \
-           vmalloc.o slab.o bootmem.o swap.o vmscan.o page_io.o \
---- linux-rh-2.4.20-6/mm/page_alloc.c~iod-rmap-exports Tue Apr  1 01:01:56 2003
-+++ linux-rh-2.4.20-6-braam/mm/page_alloc.c    Tue Apr  1 01:01:56 2003
-@@ -27,6 +27,7 @@
- int nr_swap_pages;
- pg_data_t *pgdat_list;
-+EXPORT_SYMBOL(pgdat_list);
- /*
-  *
-
-_
diff --git a/lustre/kernel_patches/patches/iod-stock-24-exports.patch b/lustre/kernel_patches/patches/iod-stock-24-exports.patch
deleted file mode 100644 (file)
index 2070377..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
- fs/Makefile     |    2 +-
- fs/inode.c      |    4 +++-
- mm/page_alloc.c |    1 +
- 3 files changed, 5 insertions(+), 2 deletions(-)
-
---- linux-2.4.20/fs/inode.c~iod-stock-24-exports       Wed Apr  2 23:21:20 2003
-+++ linux-2.4.20-braam/fs/inode.c      Wed Apr  2 23:21:20 2003
-@@ -5,6 +5,7 @@
-  */
- #include <linux/config.h>
-+#include <linux/module.h>
- #include <linux/fs.h>
- #include <linux/string.h>
- #include <linux/mm.h>
-@@ -66,7 +67,8 @@ static LIST_HEAD(anon_hash_chain); /* fo
-  * NOTE! You also have to own the lock if you change
-  * the i_state of an inode while it is in use..
-  */
--static spinlock_t inode_lock = SPIN_LOCK_UNLOCKED;
-+spinlock_t inode_lock = SPIN_LOCK_UNLOCKED;
-+EXPORT_SYMBOL(inode_lock);
- /*
-  * Statistics gathering..
---- linux-2.4.20/fs/Makefile~iod-stock-24-exports      Wed Apr  2 23:21:20 2003
-+++ linux-2.4.20-braam/fs/Makefile     Wed Apr  2 23:21:53 2003
-@@ -7,7 +7,7 @@
- O_TARGET := fs.o
--export-objs :=        filesystems.o open.o dcache.o buffer.o
-+export-objs :=        filesystems.o open.o dcache.o buffer.o inode.o
- mod-subdirs :=        nls
- obj-y :=      open.o read_write.o devices.o file_table.o buffer.o \
---- linux-2.4.20/mm/page_alloc.c~iod-stock-24-exports  Wed Apr  2 23:21:20 2003
-+++ linux-2.4.20-braam/mm/page_alloc.c Wed Apr  2 23:21:20 2003
-@@ -28,6 +28,7 @@ int nr_inactive_pages;
- LIST_HEAD(inactive_list);
- LIST_HEAD(active_list);
- pg_data_t *pgdat_list;
-+EXPORT_SYMBOL(pgdat_list);
- /*
-  *
-
-_
diff --git a/lustre/kernel_patches/patches/iod-stock-exports-2.4.22-rh.patch b/lustre/kernel_patches/patches/iod-stock-exports-2.4.22-rh.patch
deleted file mode 100644 (file)
index 8d8790e..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
- fs/Makefile     |    2 +-
- fs/inode.c      |    4 +++-
- mm/page_alloc.c |    1 +
- 3 files changed, 5 insertions(+), 2 deletions(-)
-
---- linux-2.4.22-ac1/fs/inode.c~iod-stock-exports-2.4.22-rh    2003-09-25 14:45:32.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/inode.c 2003-09-25 14:49:41.000000000 +0400
-@@ -5,6 +5,7 @@
-  */
- #include <linux/config.h>
-+#include <linux/module.h>
- #include <linux/fs.h>
- #include <linux/string.h>
- #include <linux/mm.h>
-@@ -68,7 +69,8 @@ static LIST_HEAD(anon_hash_chain); /* fo
-  * NOTE! You also have to own the lock if you change
-  * the i_state of an inode while it is in use..
-  */
--static spinlock_t inode_lock = SPIN_LOCK_UNLOCKED;
-+spinlock_t inode_lock = SPIN_LOCK_UNLOCKED;
-+EXPORT_SYMBOL(inode_lock);
- /*
-  * Statistics gathering..
---- linux-2.4.22-ac1/fs/Makefile~iod-stock-exports-2.4.22-rh   2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/Makefile        2003-09-25 14:50:00.000000000 +0400
-@@ -7,7 +7,7 @@
- O_TARGET := fs.o
--export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o
-+export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o inode.o
- mod-subdirs :=        nls xfs
- obj-y :=      open.o read_write.o devices.o file_table.o buffer.o \
---- linux-2.4.22-ac1/mm/page_alloc.c~iod-stock-exports-2.4.22-rh       2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/mm/page_alloc.c    2003-09-25 14:49:41.000000000 +0400
-@@ -28,6 +28,7 @@ int nr_inactive_pages;
- LIST_HEAD(inactive_list);
- LIST_HEAD(active_list);
- pg_data_t *pgdat_list;
-+EXPORT_SYMBOL(pgdat_list);
- /*
-  *
-
-_
diff --git a/lustre/kernel_patches/patches/kernel_text_address-2.4.21-suse-171.patch b/lustre/kernel_patches/patches/kernel_text_address-2.4.21-suse-171.patch
deleted file mode 100644 (file)
index 4088b4f..0000000
+++ /dev/null
@@ -1,116 +0,0 @@
-Index: linux-2.4.21-241/arch/um/kernel/Makefile
-===================================================================
---- linux-2.4.21-241.orig/arch/um/kernel/Makefile      2004-10-03 17:30:07.000000000 -0400
-+++ linux-2.4.21-241/arch/um/kernel/Makefile   2004-10-04 02:51:20.000000000 -0400
-@@ -37,7 +37,8 @@
- export-objs-$(CONFIG_GPROF) += gprof_syms.o
- export-objs-$(CONFIG_GCOV) += gmon_syms.o
--export-objs = ksyms.o process_kern.o signal_kern.o user_syms.o $(export-objs-y)
-+export-objs = ksyms.o process_kern.o signal_kern.o user_syms.o sysrq.o \
-+      $(export-objs-y)
- CFLAGS_user_syms.o = -D__AUTOCONF_INCLUDED__ $(DMODULES-y) $(DMODVERSIONS-y) \
-       -I/usr/include -I../include
-Index: linux-2.4.21-241/arch/um/kernel/sysrq.c
-===================================================================
---- linux-2.4.21-241.orig/arch/um/kernel/sysrq.c       2004-10-03 17:30:07.000000000 -0400
-+++ linux-2.4.21-241/arch/um/kernel/sysrq.c    2004-10-04 02:51:20.000000000 -0400
-@@ -86,6 +86,37 @@
-       show_trace((unsigned long *)esp);
- }
-+#ifdef CONFIG_MODULES
-+extern struct module *module_list;
-+extern struct module kernel_module;
-+#endif
-+
-+int is_kernel_text_address(unsigned long addr)
-+{
-+      int retval = 0;
-+#ifdef CONFIG_MODULES
-+      struct module *mod;
-+#endif
-+      if (addr >= (unsigned long) &_stext &&
-+          addr <= (unsigned long) &_etext)
-+              return 1;
-+
-+#ifdef CONFIG_MODULES
-+      for (mod = module_list; mod != &kernel_module; mod = mod->next) {
-+              /* mod_bound tests for addr being inside the vmalloc'ed
-+               * module area. Of course it'd be better to test only
-+               * for the .text subset... */
-+              if (mod_bound(addr, 0, mod)) {
-+                      retval = 1;
-+                      break;
-+              }
-+      }
-+#endif
-+      return retval;
-+}
-+
-+EXPORT_SYMBOL(is_kernel_text_address);
-+
- /*
-  * Overrides for Emacs so that we follow Linus's tabbing style.
-  * Emacs will notice this stuff at the end of the file and automatically
-Index: linux-2.4.21-241/arch/i386/kernel/Makefile
-===================================================================
---- linux-2.4.21-241.orig/arch/i386/kernel/Makefile    2004-10-03 17:31:39.000000000 -0400
-+++ linux-2.4.21-241/arch/i386/kernel/Makefile 2004-10-04 02:52:04.000000000 -0400
-@@ -20,7 +20,8 @@
- O_TARGET := kernel.o
--export-objs     := mca.o mtrr.o msr.o cpuid.o microcode.o i386_ksyms.o time.o dr_alloc.o
-+export-objs     := mca.o mtrr.o msr.o cpuid.o microcode.o i386_ksyms.o time.o \
-+      traps.o dr_alloc.o
- ifdef CONFIG_X86_SPEEDSTEP_ICH
- export-objs   += speedstep-lib.o
-Index: linux-2.4.21-241/arch/i386/kernel/traps.c
-===================================================================
---- linux-2.4.21-241.orig/arch/i386/kernel/traps.c     2004-10-04 02:48:05.000000000 -0400
-+++ linux-2.4.21-241/arch/i386/kernel/traps.c  2004-10-04 02:51:20.000000000 -0400
-@@ -1339,3 +1339,41 @@
-       cobalt_init();
- #endif
- }
-+
-+#ifdef CONFIG_MODULES
-+extern struct module *module_list;
-+extern struct module kernel_module;
-+#endif
-+                                                                                
-+int is_kernel_text_address(unsigned long addr)
-+{
-+       int retval = 0;
-+#ifdef CONFIG_MODULES
-+       struct module *mod;
-+#endif
-+       if (addr >= (unsigned long) &_stext &&
-+           addr <= (unsigned long) &_etext);
-+               return 1;
-+                                                                                
-+#ifdef CONFIG_MODULES
-+       for (mod = module_list; mod != &kernel_module; mod = mod->next) {
-+               /* mod_bound tests for addr being inside the vmalloc'ed
-+                * module area. Of course it'd be better to test only
-+                * for the .text subset... */
-+               if (mod_bound(addr, 0, mod)) {
-+                       retval = 1;
-+                       break;
-+               }
-+       }
-+#endif
-+                                                                                
-+       return retval;
-+}
-+
-+int lookup_symbol(unsigned long address, char *buf, int buflen)
-+{
-+      return -ENOSYS;
-+}
-+
-+EXPORT_SYMBOL_GPL(is_kernel_text_address);
-+EXPORT_SYMBOL_GPL(lookup_symbol);
diff --git a/lustre/kernel_patches/patches/linux-2.4.20-xattr-0.8.54-chaos.patch b/lustre/kernel_patches/patches/linux-2.4.20-xattr-0.8.54-chaos.patch
deleted file mode 100644 (file)
index cbf51ea..0000000
+++ /dev/null
@@ -1,5531 +0,0 @@
- Documentation/Configure.help  |   66 ++
- arch/alpha/defconfig          |    7 
- arch/alpha/kernel/entry.S     |   12 
- arch/arm/defconfig            |    7 
- arch/arm/kernel/calls.S       |   24 
- arch/i386/defconfig           |    7 
- arch/ia64/defconfig           |    7 
- arch/m68k/defconfig           |    7 
- arch/mips/defconfig           |    7 
- arch/mips64/defconfig         |    7 
- arch/ppc/defconfig            |   14 
- arch/ppc64/kernel/misc.S      |    2 
- arch/s390/defconfig           |    7 
- arch/s390/kernel/entry.S      |   24 
- arch/s390x/defconfig          |    7 
- arch/s390x/kernel/entry.S     |   24 
- arch/s390x/kernel/wrapper32.S |   92 +++
- arch/sparc/defconfig          |    7 
- arch/sparc/kernel/systbls.S   |   10 
- arch/sparc64/defconfig        |    7 
- arch/sparc64/kernel/systbls.S |   20 
- fs/Config.in                  |   14 
- fs/Makefile                   |    3 
- fs/ext2/Makefile              |    4 
- fs/ext2/file.c                |    5 
- fs/ext2/ialloc.c              |    2 
- fs/ext2/inode.c               |   34 -
- fs/ext2/namei.c               |   14 
- fs/ext2/super.c               |   29 
- fs/ext2/symlink.c             |   14 
- fs/ext2/xattr.c               | 1212 +++++++++++++++++++++++++++++++++++++++++
- fs/ext2/xattr_user.c          |  103 +++
- fs/ext3/Makefile              |   10 
- fs/ext3/ext3-exports.c        |   13 
- fs/ext3/file.c                |    5 
- fs/ext3/ialloc.c              |    2 
- fs/ext3/inode.c               |   35 -
- fs/ext3/namei.c               |   21 
- fs/ext3/super.c               |   36 +
- fs/ext3/symlink.c             |   14 
- fs/ext3/xattr.c               | 1225 ++++++++++++++++++++++++++++++++++++++++++
- fs/ext3/xattr_user.c          |  111 +++
- fs/jfs/jfs_xattr.h            |    6 
- fs/jfs/xattr.c                |    6 
- fs/mbcache.c                  |  648 ++++++++++++++++++++++
- include/asm-arm/unistd.h      |    2 
- include/asm-ppc64/unistd.h    |    2 
- include/asm-s390/unistd.h     |   15 
- include/asm-s390x/unistd.h    |   15 
- include/asm-sparc/unistd.h    |   24 
- include/asm-sparc64/unistd.h  |   24 
- include/linux/cache_def.h     |   15 
- include/linux/errno.h         |    4 
- include/linux/ext2_fs.h       |   31 -
- include/linux/ext2_xattr.h    |  157 +++++
- include/linux/ext3_fs.h       |   31 -
- include/linux/ext3_jbd.h      |    8 
- include/linux/ext3_xattr.h    |  157 +++++
- include/linux/fs.h            |    2 
- include/linux/mbcache.h       |   69 ++
- kernel/ksyms.c                |    4 
- mm/vmscan.c                   |   36 +
- 62 files changed, 4344 insertions(+), 183 deletions(-)
-
---- kernel-2.4.20-6chaos_18_7/Documentation/Configure.help~linux-2.4.20-xattr-0.8.54-chaos     2003-06-23 10:39:21.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/Documentation/Configure.help       2003-07-12 15:34:44.000000000 -0600
-@@ -15253,6 +15253,39 @@ CONFIG_EXT2_FS
-   be compiled as a module, and so this could be dangerous.  Most
-   everyone wants to say Y here.
-+Ext2 extended attributes
-+CONFIG_EXT2_FS_XATTR
-+  Extended attributes are name:value pairs associated with inodes by
-+  the kernel or by users (see the attr(5) manual page, or visit
-+  <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext2 extended attribute block sharing
-+CONFIG_EXT2_FS_XATTR_SHARING
-+  This options enables code for sharing identical extended attribute
-+  blocks among multiple inodes.
-+
-+  Usually, say Y.
-+
-+Ext2 extended user attributes
-+CONFIG_EXT2_FS_XATTR_USER
-+  This option enables extended user attributes on ext2. Processes can
-+  associate extended user attributes with inodes to store additional
-+  information such as the character encoding of files, etc. (see the
-+  attr(5) manual page, or visit <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext2 trusted extended attributes
-+CONFIG_EXT2_FS_XATTR_TRUSTED
-+  This option enables extended attributes on ext2 that are accessible
-+  (and visible) only to users capable of CAP_SYS_ADMIN. Usually this
-+  is only the super user. Trusted extended attributes are meant for
-+  implementing system/security services.
-+
-+  If unsure, say N.
-+
- Ext3 journalling file system support (EXPERIMENTAL)
- CONFIG_EXT3_FS
-   This is the journalling version of the Second extended file system
-@@ -15285,6 +15318,39 @@ CONFIG_EXT3_FS
-   of your root partition (the one containing the directory /) cannot
-   be compiled as a module, and so this may be dangerous.
-+Ext3 extended attributes
-+CONFIG_EXT3_FS_XATTR
-+  Extended attributes are name:value pairs associated with inodes by
-+  the kernel or by users (see the attr(5) manual page, or visit
-+  <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext3 extended attribute block sharing
-+CONFIG_EXT3_FS_XATTR_SHARING
-+  This options enables code for sharing identical extended attribute
-+  blocks among multiple inodes.
-+
-+  Usually, say Y.
-+
-+Ext3 extended user attributes
-+CONFIG_EXT3_FS_XATTR_USER
-+  This option enables extended user attributes on ext3. Processes can
-+  associate extended user attributes with inodes to store additional
-+  information such as the character encoding of files, etc. (see the
-+  attr(5) manual page, or visit <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext3 trusted extended attributes
-+CONFIG_EXT3_FS_XATTR_TRUSTED
-+  This option enables extended attributes on ext3 that are accessible
-+  (and visible) only to users capable of CAP_SYS_ADMIN. Usually this
-+  is only the super user. Trusted extended attributes are meant for
-+  implementing system/security services.
-+
-+  If unsure, say N.
-+
- Journal Block Device support (JBD for ext3) (EXPERIMENTAL)
- CONFIG_JBD
-   This is a generic journalling layer for block devices.  It is
---- kernel-2.4.20-6chaos_18_7/arch/alpha/defconfig~linux-2.4.20-xattr-0.8.54-chaos     2002-05-07 15:53:54.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/alpha/defconfig       2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_ALPHA=y
- # CONFIG_UID16 is not set
- # CONFIG_RWSEM_GENERIC_SPINLOCK is not set
---- kernel-2.4.20-6chaos_18_7/arch/alpha/kernel/entry.S~linux-2.4.20-xattr-0.8.54-chaos        2003-05-15 21:11:53.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/alpha/kernel/entry.S  2003-07-12 15:34:44.000000000 -0600
-@@ -1162,6 +1162,18 @@ sys_call_table:
-       .quad sys_readahead
-       .quad sys_ni_syscall                    /* 380, sys_security */
-       .quad sys_tkill
-+      .quad sys_setxattr
-+      .quad sys_lsetxattr
-+      .quad sys_fsetxattr
-+      .quad sys_getxattr                      /* 385 */
-+      .quad sys_lgetxattr
-+      .quad sys_fgetxattr
-+      .quad sys_listxattr
-+      .quad sys_llistxattr
-+      .quad sys_flistxattr                    /* 390 */
-+      .quad sys_removexattr
-+      .quad sys_lremovexattr
-+      .quad sys_fremovexattr
- /* Remember to update everything, kids.  */
- .ifne (. - sys_call_table) - (NR_SYSCALLS * 8)
---- kernel-2.4.20-6chaos_18_7/arch/arm/defconfig~linux-2.4.20-xattr-0.8.54-chaos       2002-05-07 15:53:56.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/arm/defconfig 2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_ARM=y
- # CONFIG_EISA is not set
- # CONFIG_SBUS is not set
---- kernel-2.4.20-6chaos_18_7/arch/arm/kernel/calls.S~linux-2.4.20-xattr-0.8.54-chaos  2002-09-25 11:09:16.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/arm/kernel/calls.S    2003-07-12 15:34:44.000000000 -0600
-@@ -240,18 +240,18 @@ __syscall_start:
-               .long   SYMBOL_NAME(sys_ni_syscall) /* Security */
-               .long   SYMBOL_NAME(sys_gettid)
- /* 225 */     .long   SYMBOL_NAME(sys_readahead)
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_setxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_lsetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_fsetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_getxattr */
--/* 230 */     .long   SYMBOL_NAME(sys_ni_syscall) /* sys_lgetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_fgetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_listxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_llistxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_flistxattr */
--/* 235 */     .long   SYMBOL_NAME(sys_ni_syscall) /* sys_removexattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_lremovexattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_fremovexattr */
-+              .long   SYMBOL_NAME(sys_setxattr)
-+              .long   SYMBOL_NAME(sys_lsetxattr)
-+              .long   SYMBOL_NAME(sys_fsetxattr)
-+              .long   SYMBOL_NAME(sys_getxattr)
-+/* 230 */     .long   SYMBOL_NAME(sys_lgetxattr)
-+              .long   SYMBOL_NAME(sys_fgetxattr)
-+              .long   SYMBOL_NAME(sys_listxattr)
-+              .long   SYMBOL_NAME(sys_llistxattr)
-+              .long   SYMBOL_NAME(sys_flistxattr)
-+/* 235 */     .long   SYMBOL_NAME(sys_removexattr)
-+              .long   SYMBOL_NAME(sys_lremovexattr)
-+              .long   SYMBOL_NAME(sys_fremovexattr)
-               .long   SYMBOL_NAME(sys_tkill)
-               /*
-                * Please check 2.5 _before_ adding calls here,
---- kernel-2.4.20-6chaos_18_7/arch/i386/defconfig~linux-2.4.20-xattr-0.8.54-chaos      2003-05-15 21:12:00.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/i386/defconfig        2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_X86=y
- CONFIG_ISA=y
- # CONFIG_SBUS is not set
---- kernel-2.4.20-6chaos_18_7/arch/ia64/defconfig~linux-2.4.20-xattr-0.8.54-chaos      2003-05-15 21:12:04.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/ia64/defconfig        2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- #
- # Code maturity level options
---- kernel-2.4.20-6chaos_18_7/arch/m68k/defconfig~linux-2.4.20-xattr-0.8.54-chaos      2002-05-07 15:53:55.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/m68k/defconfig        2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_UID16=y
- #
---- kernel-2.4.20-6chaos_18_7/arch/mips/defconfig~linux-2.4.20-xattr-0.8.54-chaos      2003-02-14 15:58:06.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/mips/defconfig        2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_MIPS=y
- CONFIG_MIPS32=y
- # CONFIG_MIPS64 is not set
---- kernel-2.4.20-6chaos_18_7/arch/mips64/defconfig~linux-2.4.20-xattr-0.8.54-chaos    2003-02-14 15:58:11.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/mips64/defconfig      2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_MIPS=y
- # CONFIG_MIPS32 is not set
- CONFIG_MIPS64=y
---- kernel-2.4.20-6chaos_18_7/arch/ppc/defconfig~linux-2.4.20-xattr-0.8.54-chaos       2003-05-15 21:12:20.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/ppc/defconfig 2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_UID16 is not set
- # CONFIG_RWSEM_GENERIC_SPINLOCK is not set
- CONFIG_RWSEM_XCHGADD_ALGORITHM=y
---- kernel-2.4.20-6chaos_18_7/arch/ppc64/kernel/misc.S~linux-2.4.20-xattr-0.8.54-chaos 2003-02-14 15:58:20.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/ppc64/kernel/misc.S   2003-07-12 15:34:44.000000000 -0600
-@@ -731,6 +731,7 @@ _GLOBAL(sys_call_table32)
-       .llong .sys_gettid              /* 207 */
- #if 0 /* Reserved syscalls */
-       .llong .sys_tkill               /* 208 */
-+#endif
-       .llong .sys_setxattr
-       .llong .sys_lsetxattr   /* 210 */
-       .llong .sys_fsetxattr
-@@ -743,6 +744,7 @@ _GLOBAL(sys_call_table32)
-       .llong .sys_removexattr
-       .llong .sys_lremovexattr
-       .llong .sys_fremovexattr        /* 220 */
-+#if 0 /* Reserved syscalls */
-       .llong .sys_futex
- #endif
-       .llong .sys_perfmonctl   /* Put this here for now ... */
---- kernel-2.4.20-6chaos_18_7/arch/s390/defconfig~linux-2.4.20-xattr-0.8.54-chaos      2003-02-14 15:58:20.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/s390/defconfig        2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_ISA is not set
- # CONFIG_EISA is not set
- # CONFIG_MCA is not set
---- kernel-2.4.20-6chaos_18_7/arch/s390/kernel/entry.S~linux-2.4.20-xattr-0.8.54-chaos 2003-02-14 15:58:20.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/s390/kernel/entry.S   2003-07-12 15:34:44.000000000 -0600
-@@ -558,18 +558,18 @@ sys_call_table:
-         .long  sys_fcntl64 
-       .long  sys_ni_syscall
-       .long  sys_ni_syscall
--      .long  sys_ni_syscall            /* 224 - reserved for setxattr  */
--      .long  sys_ni_syscall            /* 225 - reserved for lsetxattr */
--      .long  sys_ni_syscall            /* 226 - reserved for fsetxattr */
--      .long  sys_ni_syscall            /* 227 - reserved for getxattr  */
--      .long  sys_ni_syscall            /* 228 - reserved for lgetxattr */
--      .long  sys_ni_syscall            /* 229 - reserved for fgetxattr */
--      .long  sys_ni_syscall            /* 230 - reserved for listxattr */
--      .long  sys_ni_syscall            /* 231 - reserved for llistxattr */
--      .long  sys_ni_syscall            /* 232 - reserved for flistxattr */
--      .long  sys_ni_syscall            /* 233 - reserved for removexattr */
--      .long  sys_ni_syscall            /* 234 - reserved for lremovexattr */
--      .long  sys_ni_syscall            /* 235 - reserved for fremovexattr */
-+      .long  sys_setxattr
-+      .long  sys_lsetxattr            /* 225 */
-+      .long  sys_fsetxattr
-+      .long  sys_getxattr
-+      .long  sys_lgetxattr
-+      .long  sys_fgetxattr
-+      .long  sys_listxattr            /* 230 */
-+      .long  sys_llistxattr
-+      .long  sys_flistxattr
-+      .long  sys_removexattr
-+      .long  sys_lremovexattr
-+      .long  sys_fremovexattr         /* 235 */
-       .long  sys_gettid
-       .long  sys_tkill
-       .rept  255-237
---- kernel-2.4.20-6chaos_18_7/arch/s390x/defconfig~linux-2.4.20-xattr-0.8.54-chaos     2003-02-14 15:58:21.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/s390x/defconfig       2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_ISA is not set
- # CONFIG_EISA is not set
- # CONFIG_MCA is not set
---- kernel-2.4.20-6chaos_18_7/arch/s390x/kernel/entry.S~linux-2.4.20-xattr-0.8.54-chaos        2003-02-14 15:58:21.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/s390x/kernel/entry.S  2003-07-12 15:34:44.000000000 -0600
-@@ -591,18 +591,18 @@ sys_call_table:
-       .long  SYSCALL(sys_ni_syscall,sys32_fcntl64_wrapper)
-       .long  SYSCALL(sys_ni_syscall,sys_ni_syscall)
-       .long  SYSCALL(sys_ni_syscall,sys_ni_syscall)
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 224 - reserved for setxattr  */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 225 - reserved for lsetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 226 - reserved for fsetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 227 - reserved for getxattr  */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 228 - reserved for lgetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 229 - reserved for fgetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 230 - reserved for listxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 231 - reserved for llistxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 232 - reserved for flistxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 233 - reserved for removexattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 234 - reserved for lremovexattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 235 - reserved for fremovexattr */
-+      .long  SYSCALL(sys_setxattr,sys32_setxattr_wrapper)
-+      .long  SYSCALL(sys_lsetxattr,sys32_lsetxattr_wrapper)   /* 225 */
-+      .long  SYSCALL(sys_fsetxattr,sys32_fsetxattr_wrapper)
-+      .long  SYSCALL(sys_getxattr,sys32_getxattr_wrapper)
-+      .long  SYSCALL(sys_lgetxattr,sys32_lgetxattr_wrapper)
-+      .long  SYSCALL(sys_fgetxattr,sys32_fgetxattr_wrapper)
-+      .long  SYSCALL(sys_listxattr,sys32_listxattr_wrapper)   /* 230 */
-+      .long  SYSCALL(sys_llistxattr,sys32_llistxattr_wrapper)
-+      .long  SYSCALL(sys_flistxattr,sys32_flistxattr_wrapper)
-+      .long  SYSCALL(sys_removexattr,sys32_removexattr_wrapper)
-+      .long  SYSCALL(sys_lremovexattr,sys32_lremovexattr_wrapper)
-+      .long  SYSCALL(sys_fremovexattr,sys32_fremovexattr_wrapper)/* 235 */
-       .long  SYSCALL(sys_gettid,sys_gettid)
-       .long  SYSCALL(sys_tkill,sys_tkill)
-       .rept  255-237
---- kernel-2.4.20-6chaos_18_7/arch/s390x/kernel/wrapper32.S~linux-2.4.20-xattr-0.8.54-chaos    2002-05-07 15:53:59.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/s390x/kernel/wrapper32.S      2003-07-12 15:34:44.000000000 -0600
-@@ -1091,3 +1091,95 @@ sys32_fstat64_wrapper:
-       llgtr   %r3,%r3                 # struct stat64 *
-       llgfr   %r4,%r4                 # long
-       jg      sys32_fstat64           # branch to system call
-+
-+      .globl  sys32_setxattr_wrapper
-+sys32_setxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_setxattr
-+
-+      .globl  sys32_lsetxattr_wrapper
-+sys32_lsetxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_lsetxattr
-+
-+      .globl  sys32_fsetxattr_wrapper
-+sys32_fsetxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_fsetxattr
-+
-+      .globl  sys32_getxattr_wrapper
-+sys32_getxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_getxattr
-+
-+      .globl  sys32_lgetxattr_wrapper
-+sys32_lgetxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_lgetxattr
-+
-+      .globl  sys32_fgetxattr_wrapper
-+sys32_fgetxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_fgetxattr
-+
-+      .globl  sys32_listxattr_wrapper
-+sys32_listxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_listxattr
-+
-+      .globl  sys32_llistxattr_wrapper
-+sys32_llistxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_llistxattr
-+
-+      .globl  sys32_flistxattr_wrapper
-+sys32_flistxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_flistxattr
-+
-+      .globl  sys32_removexattr_wrapper
-+sys32_removexattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_removexattr
-+
-+      .globl  sys32_lremovexattr_wrapper
-+sys32_lremovexattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_lremovexattr
-+
-+      .globl  sys32_fremovexattr_wrapper
-+sys32_fremovexattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_fremovexattr
-+
-+
---- kernel-2.4.20-6chaos_18_7/arch/sparc/defconfig~linux-2.4.20-xattr-0.8.54-chaos     2002-09-25 11:10:50.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/sparc/defconfig       2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_UID16=y
- CONFIG_HIGHMEM=y
---- kernel-2.4.20-6chaos_18_7/arch/sparc/kernel/systbls.S~linux-2.4.20-xattr-0.8.54-chaos      2002-09-25 11:10:52.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/sparc/kernel/systbls.S        2003-07-12 15:34:44.000000000 -0600
-@@ -51,11 +51,11 @@ sys_call_table:
- /*150*/       .long sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_poll, sys_getdents64
- /*155*/       .long sys_fcntl64, sys_nis_syscall, sys_statfs, sys_fstatfs, sys_oldumount
- /*160*/       .long sys_nis_syscall, sys_nis_syscall, sys_getdomainname, sys_setdomainname, sys_nis_syscall
--/*165*/       .long sys_quotactl, sys_nis_syscall, sys_mount, sys_ustat, sys_nis_syscall
--/*170*/       .long sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_getdents
--/*175*/       .long sys_setsid, sys_fchdir, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall
--/*180*/       .long sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_sigpending, sys_query_module
--/*185*/       .long sys_setpgid, sys_nis_syscall, sys_tkill, sys_nis_syscall, sys_newuname
-+/*165*/       .long sys_quotactl, sys_nis_syscall, sys_mount, sys_ustat, sys_setxattr
-+/*170*/       .long sys_lsetxattr, sys_fsetxattr, sys_getxattr, sys_lgetxattr, sys_getdents
-+/*175*/       .long sys_setsid, sys_fchdir, sys_fgetxattr, sys_listxattr, sys_llistxattr
-+/*180*/       .long sys_flistxattr, sys_removexattr, sys_lremovexattr, sys_sigpending, sys_query_module
-+/*185*/       .long sys_setpgid, sys_fremovexattr, sys_tkill, sys_nis_syscall, sys_newuname
- /*190*/       .long sys_init_module, sys_personality, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall
- /*195*/       .long sys_nis_syscall, sys_nis_syscall, sys_getppid, sparc_sigaction, sys_sgetmask
- /*200*/       .long sys_ssetmask, sys_sigsuspend, sys_newlstat, sys_uselib, old_readdir
---- kernel-2.4.20-6chaos_18_7/arch/sparc64/defconfig~linux-2.4.20-xattr-0.8.54-chaos   2003-05-15 21:12:29.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/sparc64/defconfig     2003-07-12 15:34:44.000000000 -0600
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- #
- # Code maturity level options
---- kernel-2.4.20-6chaos_18_7/arch/sparc64/kernel/systbls.S~linux-2.4.20-xattr-0.8.54-chaos    2002-09-25 11:10:55.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/arch/sparc64/kernel/systbls.S      2003-07-12 15:34:44.000000000 -0600
-@@ -52,11 +52,11 @@ sys_call_table32:
- /*150*/       .word sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_poll, sys_getdents64
-       .word sys32_fcntl64, sys_nis_syscall, sys32_statfs, sys32_fstatfs, sys_oldumount
- /*160*/       .word sys_nis_syscall, sys_nis_syscall, sys_getdomainname, sys_setdomainname, sys_nis_syscall
--      .word sys32_quotactl, sys_nis_syscall, sys32_mount, sys_ustat, sys_nis_syscall
--/*170*/       .word sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys32_getdents
--      .word sys_setsid, sys_fchdir, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall
--/*180*/       .word sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys32_sigpending, sys32_query_module
--      .word sys_setpgid, sys_nis_syscall, sys_tkill, sys_nis_syscall, sparc64_newuname
-+      .word sys32_quotactl, sys_nis_syscall, sys32_mount, sys_ustat, sys_setxattr
-+/*170*/       .word sys_lsetxattr, sys_fsetxattr, sys_getxattr, sys_lgetxattr, sys32_getdents
-+      .word sys_setsid, sys_fchdir, sys_fgetxattr, sys_listxattr, sys_llistxattr
-+/*180*/       .word sys_flistxattr, sys_removexattr, sys_lremovexattr, sys32_sigpending, sys32_query_module
-+      .word sys_setpgid, sys_fremovexattr, sys_tkill, sys_nis_syscall, sparc64_newuname
- /*190*/       .word sys32_init_module, sparc64_personality, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall
-       .word sys_nis_syscall, sys_nis_syscall, sys_getppid, sys32_sigaction, sys_sgetmask
- /*200*/       .word sys_ssetmask, sys_sigsuspend, sys32_newlstat, sys_uselib, old32_readdir
-@@ -111,11 +111,11 @@ sys_call_table:
- /*150*/       .word sys_getsockname, sys_nis_syscall, sys_nis_syscall, sys_poll, sys_getdents64
-       .word sys_nis_syscall, sys_nis_syscall, sys_statfs, sys_fstatfs, sys_oldumount
- /*160*/       .word sys_nis_syscall, sys_nis_syscall, sys_getdomainname, sys_setdomainname, sys_utrap_install
--      .word sys_quotactl, sys_nis_syscall, sys_mount, sys_ustat, sys_nis_syscall
--/*170*/       .word sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_getdents
--      .word sys_setsid, sys_fchdir, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall
--/*180*/       .word sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall, sys_query_module
--      .word sys_setpgid, sys_nis_syscall, sys_tkill, sys_nis_syscall, sparc64_newuname
-+      .word sys_quotactl, sys_nis_syscall, sys_mount, sys_ustat, sys_setxattr
-+/*170*/       .word sys_lsetxattr, sys_fsetxattr, sys_getxattr, sys_lgetxattr, sys_getdents
-+      .word sys_setsid, sys_fchdir, sys_fgetxattr, sys_listxattr, sys_llistxattr
-+/*180*/       .word sys_flistxattr, sys_removexattr, sys_lremovexattr, sys_nis_syscall, sys_query_module
-+      .word sys_setpgid, sys_fremovexattr, sys_tkill, sys_nis_syscall, sparc64_newuname
- /*190*/       .word sys_init_module, sparc64_personality, sys_nis_syscall, sys_nis_syscall, sys_nis_syscall
-       .word sys_nis_syscall, sys_nis_syscall, sys_getppid, sys_nis_syscall, sys_sgetmask
- /*200*/       .word sys_ssetmask, sys_nis_syscall, sys_newlstat, sys_uselib, sys_nis_syscall
---- kernel-2.4.20-6chaos_18_7/fs/Config.in~linux-2.4.20-xattr-0.8.54-chaos     2003-05-15 21:14:24.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/Config.in       2003-07-12 15:34:44.000000000 -0600
-@@ -34,6 +34,11 @@ dep_mbool '  Debug Befs' CONFIG_BEFS_DEB
- dep_tristate 'BFS file system support (EXPERIMENTAL)' CONFIG_BFS_FS $CONFIG_EXPERIMENTAL
- tristate 'Ext3 journalling file system support' CONFIG_EXT3_FS
-+dep_mbool '  Ext3 extended attributes' CONFIG_EXT3_FS_XATTR $CONFIG_EXT3_FS
-+dep_bool '    Ext3 extended attribute block sharing' \
-+    CONFIG_EXT3_FS_XATTR_SHARING $CONFIG_EXT3_FS_XATTR
-+dep_bool '    Ext3 extended user attributes' \
-+    CONFIG_EXT3_FS_XATTR_USER $CONFIG_EXT3_FS_XATTR
- # CONFIG_JBD could be its own option (even modular), but until there are
- # other users than ext3, we will simply make it be the same as CONFIG_EXT3_FS
- # dep_tristate '  Journal Block Device support (JBD for ext3)' CONFIG_JBD $CONFIG_EXT3_FS
-@@ -93,6 +98,11 @@ dep_mbool '  QNX4FS write support (DANGE
- tristate 'ROM file system support' CONFIG_ROMFS_FS
- tristate 'Second extended fs support' CONFIG_EXT2_FS
-+dep_mbool '  Ext2 extended attributes' CONFIG_EXT2_FS_XATTR $CONFIG_EXT2_FS
-+dep_bool '    Ext2 extended attribute block sharing' \
-+    CONFIG_EXT2_FS_XATTR_SHARING $CONFIG_EXT2_FS_XATTR
-+dep_bool '    Ext2 extended user attributes' \
-+    CONFIG_EXT2_FS_XATTR_USER $CONFIG_EXT2_FS_XATTR
- tristate 'System V/Xenix/V7/Coherent file system support' CONFIG_SYSV_FS
-@@ -164,6 +174,10 @@ else
-    define_tristate CONFIG_ZISOFS_FS n
- fi
-+# Meta block cache for Extended Attributes (ext2/ext3)
-+#tristate 'Meta block cache' CONFIG_FS_MBCACHE
-+define_tristate CONFIG_FS_MBCACHE y
-+
- mainmenu_option next_comment
- comment 'Partition Types'
- source fs/partitions/Config.in
---- kernel-2.4.20-6chaos_18_7/fs/Makefile~linux-2.4.20-xattr-0.8.54-chaos      2003-07-12 15:33:34.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/Makefile        2003-07-12 15:34:44.000000000 -0600
-@@ -84,6 +84,9 @@ obj-y                                += binfmt_script.o
- obj-$(CONFIG_BINFMT_ELF)      += binfmt_elf.o
-+export-objs += mbcache.o
-+obj-$(CONFIG_FS_MBCACHE)      += mbcache.o
-+
- # persistent filesystems
- obj-y += $(join $(subdir-y),$(subdir-y:%=/%.o))
---- kernel-2.4.20-6chaos_18_7/fs/ext2/Makefile~linux-2.4.20-xattr-0.8.54-chaos 2002-05-07 15:53:46.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/Makefile   2003-07-12 15:34:44.000000000 -0600
-@@ -13,4 +13,8 @@ obj-y    := balloc.o bitmap.o dir.o file
-               ioctl.o namei.o super.o symlink.o
- obj-m    := $(O_TARGET)
-+export-objs += xattr.o
-+obj-$(CONFIG_EXT2_FS_XATTR) += xattr.o
-+obj-$(CONFIG_EXT2_FS_XATTR_USER) += xattr_user.o
-+
- include $(TOPDIR)/Rules.make
---- kernel-2.4.20-6chaos_18_7/fs/ext2/file.c~linux-2.4.20-xattr-0.8.54-chaos   2002-05-07 15:53:46.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/file.c     2003-07-12 15:34:44.000000000 -0600
-@@ -20,6 +20,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/sched.h>
- /*
-@@ -51,4 +52,8 @@ struct file_operations ext2_file_operati
- struct inode_operations ext2_file_inode_operations = {
-       truncate:       ext2_truncate,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- kernel-2.4.20-6chaos_18_7/fs/ext2/ialloc.c~linux-2.4.20-xattr-0.8.54-chaos 2003-02-14 15:59:09.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/ialloc.c   2003-07-12 15:34:44.000000000 -0600
-@@ -15,6 +15,7 @@
- #include <linux/config.h>
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/locks.h>
- #include <linux/quotaops.h>
-@@ -167,6 +168,7 @@ void ext2_free_inode (struct inode * ino
-        */
-       if (!is_bad_inode(inode)) {
-               /* Quota is already initialized in iput() */
-+              ext2_xattr_delete_inode(inode);
-               DQUOT_FREE_INODE(inode);
-               DQUOT_DROP(inode);
-       }
---- kernel-2.4.20-6chaos_18_7/fs/ext2/inode.c~linux-2.4.20-xattr-0.8.54-chaos  2003-02-14 15:59:09.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/inode.c    2003-07-12 15:34:44.000000000 -0600
-@@ -39,6 +39,18 @@ MODULE_LICENSE("GPL");
- static int ext2_update_inode(struct inode * inode, int do_sync);
- /*
-+ * Test whether an inode is a fast symlink.
-+ */
-+static inline int ext2_inode_is_fast_symlink(struct inode *inode)
-+{
-+      int ea_blocks = inode->u.ext2_i.i_file_acl ?
-+              (inode->i_sb->s_blocksize >> 9) : 0;
-+
-+      return (S_ISLNK(inode->i_mode) &&
-+              inode->i_blocks - ea_blocks == 0);
-+}
-+
-+/*
-  * Called at each iput()
-  */
- void ext2_put_inode (struct inode * inode)
-@@ -53,9 +65,7 @@ void ext2_delete_inode (struct inode * i
- {
-       lock_kernel();
--      if (is_bad_inode(inode) ||
--          inode->i_ino == EXT2_ACL_IDX_INO ||
--          inode->i_ino == EXT2_ACL_DATA_INO)
-+      if (is_bad_inode(inode))
-               goto no_delete;
-       inode->u.ext2_i.i_dtime = CURRENT_TIME;
-       mark_inode_dirty(inode);
-@@ -801,6 +811,8 @@ void ext2_truncate (struct inode * inode
-       if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
-           S_ISLNK(inode->i_mode)))
-               return;
-+      if (ext2_inode_is_fast_symlink(inode))
-+              return;
-       if (IS_APPEND(inode) || IS_IMMUTABLE(inode))
-               return;
-@@ -888,8 +900,7 @@ void ext2_read_inode (struct inode * ino
-       unsigned long offset;
-       struct ext2_group_desc * gdp;
--      if ((inode->i_ino != EXT2_ROOT_INO && inode->i_ino != EXT2_ACL_IDX_INO &&
--           inode->i_ino != EXT2_ACL_DATA_INO &&
-+      if ((inode->i_ino != EXT2_ROOT_INO &&
-            inode->i_ino < EXT2_FIRST_INO(inode->i_sb)) ||
-           inode->i_ino > le32_to_cpu(inode->i_sb->u.ext2_sb.s_es->s_inodes_count)) {
-               ext2_error (inode->i_sb, "ext2_read_inode",
-@@ -974,10 +985,7 @@ void ext2_read_inode (struct inode * ino
-       for (block = 0; block < EXT2_N_BLOCKS; block++)
-               inode->u.ext2_i.i_data[block] = raw_inode->i_block[block];
--      if (inode->i_ino == EXT2_ACL_IDX_INO ||
--          inode->i_ino == EXT2_ACL_DATA_INO)
--              /* Nothing to do */ ;
--      else if (S_ISREG(inode->i_mode)) {
-+      if (S_ISREG(inode->i_mode)) {
-               inode->i_op = &ext2_file_inode_operations;
-               inode->i_fop = &ext2_file_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-@@ -986,15 +994,17 @@ void ext2_read_inode (struct inode * ino
-               inode->i_fop = &ext2_dir_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-       } else if (S_ISLNK(inode->i_mode)) {
--              if (!inode->i_blocks)
-+              if (ext2_inode_is_fast_symlink(inode))
-                       inode->i_op = &ext2_fast_symlink_inode_operations;
-               else {
--                      inode->i_op = &page_symlink_inode_operations;
-+                      inode->i_op = &ext2_symlink_inode_operations;
-                       inode->i_mapping->a_ops = &ext2_aops;
-               }
--      } else 
-+      } else {
-+              inode->i_op = &ext2_special_inode_operations;
-               init_special_inode(inode, inode->i_mode,
-                                  le32_to_cpu(raw_inode->i_block[0]));
-+      }
-       brelse (bh);
-       inode->i_attr_flags = 0;
-       if (inode->u.ext2_i.i_flags & EXT2_SYNC_FL) {
---- kernel-2.4.20-6chaos_18_7/fs/ext2/namei.c~linux-2.4.20-xattr-0.8.54-chaos  2002-05-07 15:53:46.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/namei.c    2003-07-12 15:34:44.000000000 -0600
-@@ -31,6 +31,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/pagemap.h>
- /*
-@@ -136,7 +137,7 @@ static int ext2_symlink (struct inode * 
-       if (l > sizeof (inode->u.ext2_i.i_data)) {
-               /* slow symlink */
--              inode->i_op = &page_symlink_inode_operations;
-+              inode->i_op = &ext2_symlink_inode_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-               err = block_symlink(inode, symname, l);
-               if (err)
-@@ -345,4 +346,15 @@ struct inode_operations ext2_dir_inode_o
-       rmdir:          ext2_rmdir,
-       mknod:          ext2_mknod,
-       rename:         ext2_rename,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
-+};
-+
-+struct inode_operations ext2_special_inode_operations = {
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- kernel-2.4.20-6chaos_18_7/fs/ext2/super.c~linux-2.4.20-xattr-0.8.54-chaos  2003-02-14 15:59:09.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/super.c    2003-07-12 15:34:44.000000000 -0600
-@@ -21,6 +21,7 @@
- #include <linux/string.h>
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/slab.h>
- #include <linux/init.h>
- #include <linux/locks.h>
-@@ -125,6 +126,7 @@ void ext2_put_super (struct super_block 
-       int db_count;
-       int i;
-+      ext2_xattr_put_super(sb);
-       if (!(sb->s_flags & MS_RDONLY)) {
-               struct ext2_super_block *es = EXT2_SB(sb)->s_es;
-@@ -175,6 +177,13 @@ static int parse_options (char * options
-            this_char = strtok (NULL, ",")) {
-               if ((value = strchr (this_char, '=')) != NULL)
-                       *value++ = 0;
-+#ifdef CONFIG_EXT2_FS_XATTR_USER
-+              if (!strcmp (this_char, "user_xattr"))
-+                      set_opt (*mount_options, XATTR_USER);
-+              else if (!strcmp (this_char, "nouser_xattr"))
-+                      clear_opt (*mount_options, XATTR_USER);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -424,6 +433,9 @@ struct super_block * ext2_read_super (st
-           blocksize = BLOCK_SIZE;
-       sb->u.ext2_sb.s_mount_opt = 0;
-+#ifdef CONFIG_EXT2_FS_XATTR_USER
-+      /* set_opt (sb->u.ext2_sb.s_mount_opt, XATTR_USER); */
-+#endif
-       if (!parse_options ((char *) data, &sb_block, &resuid, &resgid,
-           &sb->u.ext2_sb.s_mount_opt)) {
-               return NULL;
-@@ -813,12 +825,27 @@ static DECLARE_FSTYPE_DEV(ext2_fs_type, 
- static int __init init_ext2_fs(void)
- {
--        return register_filesystem(&ext2_fs_type);
-+      int error = init_ext2_xattr();
-+      if (error)
-+              return error;
-+      error = init_ext2_xattr_user();
-+      if (error)
-+              goto fail;
-+      error = register_filesystem(&ext2_fs_type);
-+      if (!error)
-+              return 0;
-+
-+      exit_ext2_xattr_user();
-+fail:
-+      exit_ext2_xattr();
-+      return error;
- }
- static void __exit exit_ext2_fs(void)
- {
-       unregister_filesystem(&ext2_fs_type);
-+      exit_ext2_xattr_user();
-+      exit_ext2_xattr();
- }
- EXPORT_NO_SYMBOLS;
---- kernel-2.4.20-6chaos_18_7/fs/ext2/symlink.c~linux-2.4.20-xattr-0.8.54-chaos        2002-05-07 15:53:46.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/symlink.c  2003-07-12 15:34:44.000000000 -0600
-@@ -19,6 +19,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- static int ext2_readlink(struct dentry *dentry, char *buffer, int buflen)
- {
-@@ -32,7 +33,20 @@ static int ext2_follow_link(struct dentr
-       return vfs_follow_link(nd, s);
- }
-+struct inode_operations ext2_symlink_inode_operations = {
-+      readlink:       page_readlink,
-+      follow_link:    page_follow_link,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
-+};
-+
- struct inode_operations ext2_fast_symlink_inode_operations = {
-       readlink:       ext2_readlink,
-       follow_link:    ext2_follow_link,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/xattr.c    2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,1212 @@
-+/*
-+ * linux/fs/ext2/xattr.c
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ *
-+ * Fix by Harrison Xing <harrison@mountainviewdata.com>.
-+ * Extended attributes for symlinks and special files added per
-+ *  suggestion of Luka Renko <luka.renko@hermes.si>.
-+ */
-+
-+/*
-+ * Extended attributes are stored on disk blocks allocated outside of
-+ * any inode. The i_file_acl field is then made to point to this allocated
-+ * block. If all extended attributes of an inode are identical, these
-+ * inodes may share the same extended attribute block. Such situations
-+ * are automatically detected by keeping a cache of recent attribute block
-+ * numbers and hashes over the block's contents in memory.
-+ *
-+ *
-+ * Extended attribute block layout:
-+ *
-+ *   +------------------+
-+ *   | header           |
-+ *   | entry 1          | |
-+ *   | entry 2          | | growing downwards
-+ *   | entry 3          | v
-+ *   | four null bytes  |
-+ *   | . . .            |
-+ *   | value 1          | ^
-+ *   | value 3          | | growing upwards
-+ *   | value 2          | |
-+ *   +------------------+
-+ *
-+ * The block header is followed by multiple entry descriptors. These entry
-+ * descriptors are variable in size, and alligned to EXT2_XATTR_PAD
-+ * byte boundaries. The entry descriptors are sorted by attribute name,
-+ * so that two extended attribute blocks can be compared efficiently.
-+ *
-+ * Attribute values are aligned to the end of the block, stored in
-+ * no specific order. They are also padded to EXT2_XATTR_PAD byte
-+ * boundaries. No additional gaps are left between them.
-+ *
-+ * Locking strategy
-+ * ----------------
-+ * The VFS already holds the BKL and the inode->i_sem semaphore when any of
-+ * the xattr inode operations are called, so we are guaranteed that only one
-+ * processes accesses extended attributes of an inode at any time.
-+ *
-+ * For writing we also grab the ext2_xattr_sem semaphore. This ensures that
-+ * only a single process is modifying an extended attribute block, even
-+ * if the block is shared among inodes.
-+ *
-+ * Note for porting to 2.5
-+ * -----------------------
-+ * The BKL will no longer be held in the xattr inode operations.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/locks.h>
-+#include <linux/slab.h>
-+#include <linux/fs.h>
-+#include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
-+#include <linux/mbcache.h>
-+#include <linux/quotaops.h>
-+#include <asm/semaphore.h>
-+#include <linux/compatmac.h>
-+
-+/* These symbols may be needed by a module. */
-+EXPORT_SYMBOL(ext2_xattr_register);
-+EXPORT_SYMBOL(ext2_xattr_unregister);
-+EXPORT_SYMBOL(ext2_xattr_get);
-+EXPORT_SYMBOL(ext2_xattr_list);
-+EXPORT_SYMBOL(ext2_xattr_set);
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+# define mark_buffer_dirty(bh) mark_buffer_dirty(bh, 1)
-+#endif
-+
-+#define HDR(bh) ((struct ext2_xattr_header *)((bh)->b_data))
-+#define ENTRY(ptr) ((struct ext2_xattr_entry *)(ptr))
-+#define FIRST_ENTRY(bh) ENTRY(HDR(bh)+1)
-+#define IS_LAST_ENTRY(entry) (*(__u32 *)(entry) == 0)
-+
-+#ifdef EXT2_XATTR_DEBUG
-+# define ea_idebug(inode, f...) do { \
-+              printk(KERN_DEBUG "inode %s:%ld: ", \
-+                      kdevname(inode->i_dev), inode->i_ino); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+# define ea_bdebug(bh, f...) do { \
-+              printk(KERN_DEBUG "block %s:%ld: ", \
-+                      kdevname(bh->b_dev), bh->b_blocknr); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+#else
-+# define ea_idebug(f...)
-+# define ea_bdebug(f...)
-+#endif
-+
-+static int ext2_xattr_set2(struct inode *, struct buffer_head *,
-+                         struct ext2_xattr_header *);
-+
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+
-+static int ext2_xattr_cache_insert(struct buffer_head *);
-+static struct buffer_head *ext2_xattr_cache_find(struct inode *,
-+                                               struct ext2_xattr_header *);
-+static void ext2_xattr_cache_remove(struct buffer_head *);
-+static void ext2_xattr_rehash(struct ext2_xattr_header *,
-+                            struct ext2_xattr_entry *);
-+
-+static struct mb_cache *ext2_xattr_cache;
-+
-+#else
-+# define ext2_xattr_cache_insert(bh) 0
-+# define ext2_xattr_cache_find(inode, header) NULL
-+# define ext2_xattr_cache_remove(bh) while(0) {}
-+# define ext2_xattr_rehash(header, entry) while(0) {}
-+#endif
-+
-+/*
-+ * If a file system does not share extended attributes among inodes,
-+ * we should not need the ext2_xattr_sem semaphore. However, the
-+ * filesystem may still contain shared blocks, so we always take
-+ * the lock.
-+ */
-+
-+DECLARE_MUTEX(ext2_xattr_sem);
-+
-+static inline int
-+ext2_xattr_new_block(struct inode *inode, int * errp, int force)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      int goal = le32_to_cpu(EXT2_SB(sb)->s_es->s_first_data_block) +
-+              EXT2_I(inode)->i_block_group * EXT2_BLOCKS_PER_GROUP(sb);
-+
-+      /* How can we enforce the allocation? */
-+      int block = ext2_new_block(inode, goal, 0, 0, errp);
-+#ifdef OLD_QUOTAS
-+      if (!*errp)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#endif
-+      return block;
-+}
-+
-+static inline int
-+ext2_xattr_quota_alloc(struct inode *inode, int force)
-+{
-+      /* How can we enforce the allocation? */
-+#ifdef OLD_QUOTAS
-+      int error = DQUOT_ALLOC_BLOCK(inode->i_sb, inode, 1);
-+      if (!error)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#else
-+      int error = DQUOT_ALLOC_BLOCK(inode, 1);
-+#endif
-+      return error;
-+}
-+
-+#ifdef OLD_QUOTAS
-+
-+static inline void
-+ext2_xattr_quota_free(struct inode *inode)
-+{
-+      DQUOT_FREE_BLOCK(inode->i_sb, inode, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+static inline void
-+ext2_xattr_free_block(struct inode * inode, unsigned long block)
-+{
-+      ext2_free_blocks(inode, block, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+#else
-+# define ext2_xattr_quota_free(inode) \
-+      DQUOT_FREE_BLOCK(inode, 1)
-+# define ext2_xattr_free_block(inode, block) \
-+      ext2_free_blocks(inode, block, 1)
-+#endif
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,18)
-+
-+static inline struct buffer_head *
-+sb_bread(struct super_block *sb, int block)
-+{
-+      return bread(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+static inline struct buffer_head *
-+sb_getblk(struct super_block *sb, int block)
-+{
-+      return getblk(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+#endif
-+
-+struct ext2_xattr_handler *ext2_xattr_handlers[EXT2_XATTR_INDEX_MAX];
-+rwlock_t ext2_handler_lock = RW_LOCK_UNLOCKED;
-+
-+int
-+ext2_xattr_register(int name_index, struct ext2_xattr_handler *handler)
-+{
-+      int error = -EINVAL;
-+
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              write_lock(&ext2_handler_lock);
-+              if (!ext2_xattr_handlers[name_index-1]) {
-+                      ext2_xattr_handlers[name_index-1] = handler;
-+                      error = 0;
-+              }
-+              write_unlock(&ext2_handler_lock);
-+      }
-+      return error;
-+}
-+
-+void
-+ext2_xattr_unregister(int name_index, struct ext2_xattr_handler *handler)
-+{
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              write_lock(&ext2_handler_lock);
-+              ext2_xattr_handlers[name_index-1] = NULL;
-+              write_unlock(&ext2_handler_lock);
-+      }
-+}
-+
-+static inline const char *
-+strcmp_prefix(const char *a, const char *a_prefix)
-+{
-+      while (*a_prefix && *a == *a_prefix) {
-+              a++;
-+              a_prefix++;
-+      }
-+      return *a_prefix ? NULL : a;
-+}
-+
-+/*
-+ * Decode the extended attribute name, and translate it into
-+ * the name_index and name suffix.
-+ */
-+static struct ext2_xattr_handler *
-+ext2_xattr_resolve_name(const char **name)
-+{
-+      struct ext2_xattr_handler *handler = NULL;
-+      int i;
-+
-+      if (!*name)
-+              return NULL;
-+      read_lock(&ext2_handler_lock);
-+      for (i=0; i<EXT2_XATTR_INDEX_MAX; i++) {
-+              if (ext2_xattr_handlers[i]) {
-+                      const char *n = strcmp_prefix(*name,
-+                              ext2_xattr_handlers[i]->prefix);
-+                      if (n) {
-+                              handler = ext2_xattr_handlers[i];
-+                              *name = n;
-+                              break;
-+                      }
-+              }
-+      }
-+      read_unlock(&ext2_handler_lock);
-+      return handler;
-+}
-+
-+static inline struct ext2_xattr_handler *
-+ext2_xattr_handler(int name_index)
-+{
-+      struct ext2_xattr_handler *handler = NULL;
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              read_lock(&ext2_handler_lock);
-+              handler = ext2_xattr_handlers[name_index-1];
-+              read_unlock(&ext2_handler_lock);
-+      }
-+      return handler;
-+}
-+
-+/*
-+ * Inode operation getxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext2_getxattr(struct dentry *dentry, const char *name,
-+            void *buffer, size_t size)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->get(inode, name, buffer, size);
-+}
-+
-+/*
-+ * Inode operation listxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext2_listxattr(struct dentry *dentry, char *buffer, size_t size)
-+{
-+      return ext2_xattr_list(dentry->d_inode, buffer, size);
-+}
-+
-+/*
-+ * Inode operation setxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext2_setxattr(struct dentry *dentry, const char *name,
-+            const void *value, size_t size, int flags)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      if (size == 0)
-+              value = "";  /* empty EA, do not remove */
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, value, size, flags);
-+}
-+
-+/*
-+ * Inode operation removexattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext2_removexattr(struct dentry *dentry, const char *name)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, NULL, 0, XATTR_REPLACE);
-+}
-+
-+/*
-+ * ext2_xattr_get()
-+ *
-+ * Copy an extended attribute into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext2_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_entry *entry;
-+      unsigned int block, size;
-+      char *end;
-+      int name_len, error;
-+
-+      ea_idebug(inode, "name=%d.%s, buffer=%p, buffer_size=%ld",
-+                name_index, name, buffer, (long)buffer_size);
-+
-+      if (name == NULL)
-+              return -EINVAL;
-+      if (!EXT2_I(inode)->i_file_acl)
-+              return -ENOATTR;
-+      block = EXT2_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext2_error(inode->i_sb, "ext2_xattr_get",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* find named attribute */
-+      name_len = strlen(name);
-+
-+      error = -ERANGE;
-+      if (name_len > 255)
-+              goto cleanup;
-+      entry = FIRST_ENTRY(bh);
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              if (name_index == entry->e_name_index &&
-+                  name_len == entry->e_name_len &&
-+                  memcmp(name, entry->e_name, name_len) == 0)
-+                      goto found;
-+              entry = next;
-+      }
-+      /* Check the remaining name entries */
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              entry = next;
-+      }
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      error = -ENOATTR;
-+      goto cleanup;
-+found:
-+      /* check the buffer size */
-+      if (entry->e_value_block != 0)
-+              goto bad_block;
-+      size = le32_to_cpu(entry->e_value_size);
-+      if (size > inode->i_sb->s_blocksize ||
-+          le16_to_cpu(entry->e_value_offs) + size > inode->i_sb->s_blocksize)
-+              goto bad_block;
-+
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (buffer) {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+              /* return value of attribute */
-+              memcpy(buffer, bh->b_data + le16_to_cpu(entry->e_value_offs),
-+                      size);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_list()
-+ *
-+ * Copy a list of attribute names into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext2_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_entry *entry;
-+      unsigned int block, size = 0;
-+      char *buf, *end;
-+      int error;
-+
-+      ea_idebug(inode, "buffer=%p, buffer_size=%ld",
-+                buffer, (long)buffer_size);
-+
-+      if (!EXT2_I(inode)->i_file_acl)
-+              return 0;
-+      block = EXT2_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext2_error(inode->i_sb, "ext2_xattr_list",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* compute the size required for the list of attribute names */
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT2_XATTR_NEXT(entry)) {
-+              struct ext2_xattr_handler *handler;
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+
-+              handler = ext2_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      size += handler->list(NULL, inode, entry->e_name,
-+                                            entry->e_name_len);
-+      }
-+
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (!buffer) {
-+              error = size;
-+              goto cleanup;
-+      } else {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+      }
-+
-+      /* list the attribute names */
-+      buf = buffer;
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT2_XATTR_NEXT(entry)) {
-+              struct ext2_xattr_handler *handler;
-+              
-+              handler = ext2_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      buf += handler->list(buf, inode, entry->e_name,
-+                                           entry->e_name_len);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * If the EXT2_FEATURE_COMPAT_EXT_ATTR feature of this file system is
-+ * not set, set it.
-+ */
-+static void ext2_xattr_update_super_block(struct super_block *sb)
-+{
-+      if (EXT2_HAS_COMPAT_FEATURE(sb, EXT2_FEATURE_COMPAT_EXT_ATTR))
-+              return;
-+
-+      lock_super(sb);
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+      EXT2_SB(sb)->s_feature_compat |= EXT2_FEATURE_COMPAT_EXT_ATTR;
-+#endif
-+      EXT2_SB(sb)->s_es->s_feature_compat |=
-+              cpu_to_le32(EXT2_FEATURE_COMPAT_EXT_ATTR);
-+      sb->s_dirt = 1;
-+      mark_buffer_dirty(EXT2_SB(sb)->s_sbh);
-+      unlock_super(sb);
-+}
-+
-+/*
-+ * ext2_xattr_set()
-+ *
-+ * Create, replace or remove an extended attribute for this inode. Buffer
-+ * is NULL to remove an existing extended attribute, and non-NULL to
-+ * either replace an existing extended attribute, or create a new extended
-+ * attribute. The flags XATTR_REPLACE and XATTR_CREATE
-+ * specify that an extended attribute must exist and must not exist
-+ * previous to the call, respectively.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+int
-+ext2_xattr_set(struct inode *inode, int name_index, const char *name,
-+             const void *value, size_t value_len, int flags)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_header *header = NULL;
-+      struct ext2_xattr_entry *here, *last;
-+      unsigned int name_len;
-+      int block = EXT2_I(inode)->i_file_acl;
-+      int min_offs = sb->s_blocksize, not_found = 1, free, error;
-+      char *end;
-+      
-+      /*
-+       * header -- Points either into bh, or to a temporarily
-+       *           allocated buffer.
-+       * here -- The named entry found, or the place for inserting, within
-+       *         the block pointed to by header.
-+       * last -- Points right after the last named entry within the block
-+       *         pointed to by header.
-+       * min_offs -- The offset of the first value (values are aligned
-+       *             towards the end of the block).
-+       * end -- Points right after the block pointed to by header.
-+       */
-+      
-+      ea_idebug(inode, "name=%d.%s, value=%p, value_len=%ld",
-+                name_index, name, value, (long)value_len);
-+
-+      if (IS_RDONLY(inode))
-+              return -EROFS;
-+      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-+              return -EPERM;
-+      if (value == NULL)
-+              value_len = 0;
-+      if (name == NULL)
-+              return -EINVAL;
-+      name_len = strlen(name);
-+      if (name_len > 255 || value_len > sb->s_blocksize)
-+              return -ERANGE;
-+      down(&ext2_xattr_sem);
-+
-+      if (block) {
-+              /* The inode already has an extended attribute block. */
-+
-+              bh = sb_bread(sb, block);
-+              error = -EIO;
-+              if (!bh)
-+                      goto cleanup;
-+              ea_bdebug(bh, "b_count=%d, refcount=%d",
-+                      atomic_read(&(bh->b_count)),
-+                      le32_to_cpu(HDR(bh)->h_refcount));
-+              header = HDR(bh);
-+              end = bh->b_data + bh->b_size;
-+              if (header->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+                  header->h_blocks != cpu_to_le32(1)) {
-+bad_block:            ext2_error(sb, "ext2_xattr_set",
-+                              "inode %ld: bad block %d", inode->i_ino, block);
-+                      error = -EIO;
-+                      goto cleanup;
-+              }
-+              /* Find the named attribute. */
-+              here = FIRST_ENTRY(bh);
-+              while (!IS_LAST_ENTRY(here)) {
-+                      struct ext2_xattr_entry *next = EXT2_XATTR_NEXT(here);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!here->e_value_block && here->e_value_size) {
-+                              int offs = le16_to_cpu(here->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      not_found = name_index - here->e_name_index;
-+                      if (!not_found)
-+                              not_found = name_len - here->e_name_len;
-+                      if (!not_found)
-+                              not_found = memcmp(name, here->e_name,name_len);
-+                      if (not_found <= 0)
-+                              break;
-+                      here = next;
-+              }
-+              last = here;
-+              /* We still need to compute min_offs and last. */
-+              while (!IS_LAST_ENTRY(last)) {
-+                      struct ext2_xattr_entry *next = EXT2_XATTR_NEXT(last);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!last->e_value_block && last->e_value_size) {
-+                              int offs = le16_to_cpu(last->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      last = next;
-+              }
-+
-+              /* Check whether we have enough space left. */
-+              free = min_offs - ((char*)last - (char*)header) - sizeof(__u32);
-+      } else {
-+              /* We will use a new extended attribute block. */
-+              free = sb->s_blocksize -
-+                      sizeof(struct ext2_xattr_header) - sizeof(__u32);
-+              here = last = NULL;  /* avoid gcc uninitialized warning. */
-+      }
-+
-+      if (not_found) {
-+              /* Request to remove a nonexistent attribute? */
-+              error = -ENOATTR;
-+              if (flags & XATTR_REPLACE)
-+                      goto cleanup;
-+              error = 0;
-+              if (value == NULL)
-+                      goto cleanup;
-+              else
-+                      free -= EXT2_XATTR_LEN(name_len);
-+      } else {
-+              /* Request to create an existing attribute? */
-+              error = -EEXIST;
-+              if (flags & XATTR_CREATE)
-+                      goto cleanup;
-+              if (!here->e_value_block && here->e_value_size) {
-+                      unsigned int size = le32_to_cpu(here->e_value_size);
-+
-+                      if (le16_to_cpu(here->e_value_offs) + size > 
-+                          sb->s_blocksize || size > sb->s_blocksize)
-+                              goto bad_block;
-+                      free += EXT2_XATTR_SIZE(size);
-+              }
-+      }
-+      free -= EXT2_XATTR_SIZE(value_len);
-+      error = -ENOSPC;
-+      if (free < 0)
-+              goto cleanup;
-+
-+      /* Here we know that we can set the new attribute. */
-+
-+      if (header) {
-+              if (header->h_refcount == cpu_to_le32(1)) {
-+                      ea_bdebug(bh, "modifying in-place");
-+                      ext2_xattr_cache_remove(bh);
-+              } else {
-+                      int offset;
-+
-+                      ea_bdebug(bh, "cloning");
-+                      header = kmalloc(bh->b_size, GFP_KERNEL);
-+                      error = -ENOMEM;
-+                      if (header == NULL)
-+                              goto cleanup;
-+                      memcpy(header, HDR(bh), bh->b_size);
-+                      header->h_refcount = cpu_to_le32(1);
-+                      offset = (char *)header - bh->b_data;
-+                      here = ENTRY((char *)here + offset);
-+                      last = ENTRY((char *)last + offset);
-+              }
-+      } else {
-+              /* Allocate a buffer where we construct the new block. */
-+              header = kmalloc(sb->s_blocksize, GFP_KERNEL);
-+              error = -ENOMEM;
-+              if (header == NULL)
-+                      goto cleanup;
-+              memset(header, 0, sb->s_blocksize);
-+              end = (char *)header + sb->s_blocksize;
-+              header->h_magic = cpu_to_le32(EXT2_XATTR_MAGIC);
-+              header->h_blocks = header->h_refcount = cpu_to_le32(1);
-+              last = here = ENTRY(header+1);
-+      }
-+
-+      if (not_found) {
-+              /* Insert the new name. */
-+              int size = EXT2_XATTR_LEN(name_len);
-+              int rest = (char *)last - (char *)here;
-+              memmove((char *)here + size, here, rest);
-+              memset(here, 0, size);
-+              here->e_name_index = name_index;
-+              here->e_name_len = name_len;
-+              memcpy(here->e_name, name, name_len);
-+      } else {
-+              /* Remove the old value. */
-+              if (!here->e_value_block && here->e_value_size) {
-+                      char *first_val = (char *)header + min_offs;
-+                      int offs = le16_to_cpu(here->e_value_offs);
-+                      char *val = (char *)header + offs;
-+                      size_t size = EXT2_XATTR_SIZE(
-+                              le32_to_cpu(here->e_value_size));
-+                      memmove(first_val + size, first_val, val - first_val);
-+                      memset(first_val, 0, size);
-+                      here->e_value_offs = 0;
-+                      min_offs += size;
-+
-+                      /* Adjust all value offsets. */
-+                      last = ENTRY(header+1);
-+                      while (!IS_LAST_ENTRY(last)) {
-+                              int o = le16_to_cpu(last->e_value_offs);
-+                              if (!last->e_value_block && o < offs)
-+                                      last->e_value_offs =
-+                                              cpu_to_le16(o + size);
-+                              last = EXT2_XATTR_NEXT(last);
-+                      }
-+              }
-+              if (value == NULL) {
-+                      /* Remove this attribute. */
-+                      if (EXT2_XATTR_NEXT(ENTRY(header+1)) == last) {
-+                              /* This block is now empty. */
-+                              error = ext2_xattr_set2(inode, bh, NULL);
-+                              goto cleanup;
-+                      } else {
-+                              /* Remove the old name. */
-+                              int size = EXT2_XATTR_LEN(name_len);
-+                              last = ENTRY((char *)last - size);
-+                              memmove(here, (char*)here + size,
-+                                      (char*)last - (char*)here);
-+                              memset(last, 0, size);
-+                      }
-+              }
-+      }
-+
-+      if (value != NULL) {
-+              /* Insert the new value. */
-+              here->e_value_size = cpu_to_le32(value_len);
-+              if (value_len) {
-+                      size_t size = EXT2_XATTR_SIZE(value_len);
-+                      char *val = (char *)header + min_offs - size;
-+                      here->e_value_offs =
-+                              cpu_to_le16((char *)val - (char *)header);
-+                      memset(val + size - EXT2_XATTR_PAD, 0,
-+                             EXT2_XATTR_PAD); /* Clear the pad bytes. */
-+                      memcpy(val, value, value_len);
-+              }
-+      }
-+      ext2_xattr_rehash(header, here);
-+
-+      error = ext2_xattr_set2(inode, bh, header);
-+
-+cleanup:
-+      brelse(bh);
-+      if (!(bh && header == HDR(bh)))
-+              kfree(header);
-+      up(&ext2_xattr_sem);
-+
-+      return error;
-+}
-+
-+/*
-+ * Second half of ext2_xattr_set(): Update the file system.
-+ */
-+static int
-+ext2_xattr_set2(struct inode *inode, struct buffer_head *old_bh,
-+              struct ext2_xattr_header *header)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *new_bh = NULL;
-+      int error;
-+
-+      if (header) {
-+              new_bh = ext2_xattr_cache_find(inode, header);
-+              if (new_bh) {
-+                      /*
-+                       * We found an identical block in the cache.
-+                       * The old block will be released after updating
-+                       * the inode.
-+                       */
-+                      ea_bdebug(old_bh, "reusing block %ld",
-+                              new_bh->b_blocknr);
-+                      
-+                      error = -EDQUOT;
-+                      if (ext2_xattr_quota_alloc(inode, 1))
-+                              goto cleanup;
-+                      
-+                      HDR(new_bh)->h_refcount = cpu_to_le32(
-+                              le32_to_cpu(HDR(new_bh)->h_refcount) + 1);
-+                      ea_bdebug(new_bh, "refcount now=%d",
-+                              le32_to_cpu(HDR(new_bh)->h_refcount));
-+              } else if (old_bh && header == HDR(old_bh)) {
-+                      /* Keep this block. */
-+                      new_bh = old_bh;
-+                      (void)ext2_xattr_cache_insert(new_bh);
-+              } else {
-+                      /* We need to allocate a new block */
-+                      int force = EXT2_I(inode)->i_file_acl != 0;
-+                      int block = ext2_xattr_new_block(inode, &error, force);
-+                      if (error)
-+                              goto cleanup;
-+                      ea_idebug(inode, "creating block %d", block);
-+
-+                      new_bh = sb_getblk(sb, block);
-+                      if (!new_bh) {
-+                              ext2_xattr_free_block(inode, block);
-+                              error = -EIO;
-+                              goto cleanup;
-+                      }
-+                      lock_buffer(new_bh);
-+                      memcpy(new_bh->b_data, header, new_bh->b_size);
-+                      mark_buffer_uptodate(new_bh, 1);
-+                      unlock_buffer(new_bh);
-+                      (void)ext2_xattr_cache_insert(new_bh);
-+                      
-+                      ext2_xattr_update_super_block(sb);
-+              }
-+              mark_buffer_dirty(new_bh);
-+              if (IS_SYNC(inode)) {
-+                      ll_rw_block(WRITE, 1, &new_bh);
-+                      wait_on_buffer(new_bh); 
-+                      error = -EIO;
-+                      if (buffer_req(new_bh) && !buffer_uptodate(new_bh))
-+                              goto cleanup;
-+              }
-+      }
-+
-+      /* Update the inode. */
-+      EXT2_I(inode)->i_file_acl = new_bh ? new_bh->b_blocknr : 0;
-+      inode->i_ctime = CURRENT_TIME;
-+      if (IS_SYNC(inode)) {
-+              error = ext2_sync_inode (inode);
-+              if (error)
-+                      goto cleanup;
-+      } else
-+              mark_inode_dirty(inode);
-+
-+      error = 0;
-+      if (old_bh && old_bh != new_bh) {
-+              /*
-+               * If there was an old block, and we are not still using it,
-+               * we now release the old block.
-+              */
-+              unsigned int refcount = le32_to_cpu(HDR(old_bh)->h_refcount);
-+
-+              if (refcount == 1) {
-+                      /* Free the old block. */
-+                      ea_bdebug(old_bh, "freeing");
-+                      ext2_xattr_free_block(inode, old_bh->b_blocknr);
-+                      mark_buffer_clean(old_bh);
-+              } else {
-+                      /* Decrement the refcount only. */
-+                      refcount--;
-+                      HDR(old_bh)->h_refcount = cpu_to_le32(refcount);
-+                      ext2_xattr_quota_free(inode);
-+                      mark_buffer_dirty(old_bh);
-+                      ea_bdebug(old_bh, "refcount now=%d", refcount);
-+              }
-+      }
-+
-+cleanup:
-+      if (old_bh != new_bh)
-+              brelse(new_bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_delete_inode()
-+ *
-+ * Free extended attribute resources associated with this inode. This
-+ * is called immediately before an inode is freed.
-+ */
-+void
-+ext2_xattr_delete_inode(struct inode *inode)
-+{
-+      struct buffer_head *bh;
-+      unsigned int block = EXT2_I(inode)->i_file_acl;
-+
-+      if (!block)
-+              return;
-+      down(&ext2_xattr_sem);
-+
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh) {
-+              ext2_error(inode->i_sb, "ext2_xattr_delete_inode",
-+                      "inode %ld: block %d read error", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "b_count=%d", atomic_read(&(bh->b_count)));
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+              ext2_error(inode->i_sb, "ext2_xattr_delete_inode",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "refcount now=%d", le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+      if (HDR(bh)->h_refcount == cpu_to_le32(1)) {
-+              ext2_xattr_cache_remove(bh);
-+              ext2_xattr_free_block(inode, block);
-+              bforget(bh);
-+              bh = NULL;
-+      } else {
-+              HDR(bh)->h_refcount = cpu_to_le32(
-+                      le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+              mark_buffer_dirty(bh);
-+              if (IS_SYNC(inode)) {
-+                      ll_rw_block(WRITE, 1, &bh);
-+                      wait_on_buffer(bh);
-+              }
-+              ext2_xattr_quota_free(inode);
-+      }
-+      EXT2_I(inode)->i_file_acl = 0;
-+
-+cleanup:
-+      brelse(bh);
-+      up(&ext2_xattr_sem);
-+}
-+
-+/*
-+ * ext2_xattr_put_super()
-+ *
-+ * This is called when a file system is unmounted.
-+ */
-+void
-+ext2_xattr_put_super(struct super_block *sb)
-+{
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+      mb_cache_shrink(ext2_xattr_cache, sb->s_dev);
-+#endif
-+}
-+
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+
-+/*
-+ * ext2_xattr_cache_insert()
-+ *
-+ * Create a new entry in the extended attribute cache, and insert
-+ * it unless such an entry is already in the cache.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+static int
-+ext2_xattr_cache_insert(struct buffer_head *bh)
-+{
-+      __u32 hash = le32_to_cpu(HDR(bh)->h_hash);
-+      struct mb_cache_entry *ce;
-+      int error;
-+
-+      ce = mb_cache_entry_alloc(ext2_xattr_cache);
-+      if (!ce)
-+              return -ENOMEM;
-+      error = mb_cache_entry_insert(ce, bh->b_dev, bh->b_blocknr, &hash);
-+      if (error) {
-+              mb_cache_entry_free(ce);
-+              if (error == -EBUSY) {
-+                      ea_bdebug(bh, "already in cache (%d cache entries)",
-+                              atomic_read(&ext2_xattr_cache->c_entry_count));
-+                      error = 0;
-+              }
-+      } else {
-+              ea_bdebug(bh, "inserting [%x] (%d cache entries)", (int)hash,
-+                        atomic_read(&ext2_xattr_cache->c_entry_count));
-+              mb_cache_entry_release(ce);
-+      }
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_cmp()
-+ *
-+ * Compare two extended attribute blocks for equality.
-+ *
-+ * Returns 0 if the blocks are equal, 1 if they differ, and
-+ * a negative error number on errors.
-+ */
-+static int
-+ext2_xattr_cmp(struct ext2_xattr_header *header1,
-+             struct ext2_xattr_header *header2)
-+{
-+      struct ext2_xattr_entry *entry1, *entry2;
-+
-+      entry1 = ENTRY(header1+1);
-+      entry2 = ENTRY(header2+1);
-+      while (!IS_LAST_ENTRY(entry1)) {
-+              if (IS_LAST_ENTRY(entry2))
-+                      return 1;
-+              if (entry1->e_hash != entry2->e_hash ||
-+                  entry1->e_name_len != entry2->e_name_len ||
-+                  entry1->e_value_size != entry2->e_value_size ||
-+                  memcmp(entry1->e_name, entry2->e_name, entry1->e_name_len))
-+                      return 1;
-+              if (entry1->e_value_block != 0 || entry2->e_value_block != 0)
-+                      return -EIO;
-+              if (memcmp((char *)header1 + le16_to_cpu(entry1->e_value_offs),
-+                         (char *)header2 + le16_to_cpu(entry2->e_value_offs),
-+                         le32_to_cpu(entry1->e_value_size)))
-+                      return 1;
-+
-+              entry1 = EXT2_XATTR_NEXT(entry1);
-+              entry2 = EXT2_XATTR_NEXT(entry2);
-+      }
-+      if (!IS_LAST_ENTRY(entry2))
-+              return 1;
-+      return 0;
-+}
-+
-+/*
-+ * ext2_xattr_cache_find()
-+ *
-+ * Find an identical extended attribute block.
-+ *
-+ * Returns a pointer to the block found, or NULL if such a block was
-+ * not found or an error occurred.
-+ */
-+static struct buffer_head *
-+ext2_xattr_cache_find(struct inode *inode, struct ext2_xattr_header *header)
-+{
-+      __u32 hash = le32_to_cpu(header->h_hash);
-+      struct mb_cache_entry *ce;
-+
-+      if (!header->h_hash)
-+              return NULL;  /* never share */
-+      ea_idebug(inode, "looking for cached blocks [%x]", (int)hash);
-+      ce = mb_cache_entry_find_first(ext2_xattr_cache, 0, inode->i_dev, hash);
-+      while (ce) {
-+              struct buffer_head *bh = sb_bread(inode->i_sb, ce->e_block);
-+
-+              if (!bh) {
-+                      ext2_error(inode->i_sb, "ext2_xattr_cache_find",
-+                              "inode %ld: block %ld read error",
-+                              inode->i_ino, ce->e_block);
-+              } else if (le32_to_cpu(HDR(bh)->h_refcount) >
-+                         EXT2_XATTR_REFCOUNT_MAX) {
-+                      ea_idebug(inode, "block %ld refcount %d>%d",ce->e_block,
-+                              le32_to_cpu(HDR(bh)->h_refcount),
-+                              EXT2_XATTR_REFCOUNT_MAX);
-+              } else if (!ext2_xattr_cmp(header, HDR(bh))) {
-+                      ea_bdebug(bh, "b_count=%d",atomic_read(&(bh->b_count)));
-+                      mb_cache_entry_release(ce);
-+                      return bh;
-+              }
-+              brelse(bh);
-+              ce = mb_cache_entry_find_next(ce, 0, inode->i_dev, hash);
-+      }
-+      return NULL;
-+}
-+
-+/*
-+ * ext2_xattr_cache_remove()
-+ *
-+ * Remove the cache entry of a block from the cache. Called when a
-+ * block becomes invalid.
-+ */
-+static void
-+ext2_xattr_cache_remove(struct buffer_head *bh)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      ce = mb_cache_entry_get(ext2_xattr_cache, bh->b_dev, bh->b_blocknr);
-+      if (ce) {
-+              ea_bdebug(bh, "removing (%d cache entries remaining)",
-+                        atomic_read(&ext2_xattr_cache->c_entry_count)-1);
-+              mb_cache_entry_free(ce);
-+      } else 
-+              ea_bdebug(bh, "no cache entry");
-+}
-+
-+#define NAME_HASH_SHIFT 5
-+#define VALUE_HASH_SHIFT 16
-+
-+/*
-+ * ext2_xattr_hash_entry()
-+ *
-+ * Compute the hash of an extended attribute.
-+ */
-+static inline void ext2_xattr_hash_entry(struct ext2_xattr_header *header,
-+                                       struct ext2_xattr_entry *entry)
-+{
-+      __u32 hash = 0;
-+      char *name = entry->e_name;
-+      int n;
-+
-+      for (n=0; n < entry->e_name_len; n++) {
-+              hash = (hash << NAME_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - NAME_HASH_SHIFT)) ^
-+                     *name++;
-+      }
-+
-+      if (entry->e_value_block == 0 && entry->e_value_size != 0) {
-+              __u32 *value = (__u32 *)((char *)header +
-+                      le16_to_cpu(entry->e_value_offs));
-+              for (n = (le32_to_cpu(entry->e_value_size) +
-+                   EXT2_XATTR_ROUND) >> EXT2_XATTR_PAD_BITS; n; n--) {
-+                      hash = (hash << VALUE_HASH_SHIFT) ^
-+                             (hash >> (8*sizeof(hash) - VALUE_HASH_SHIFT)) ^
-+                             le32_to_cpu(*value++);
-+              }
-+      }
-+      entry->e_hash = cpu_to_le32(hash);
-+}
-+
-+#undef NAME_HASH_SHIFT
-+#undef VALUE_HASH_SHIFT
-+
-+#define BLOCK_HASH_SHIFT 16
-+
-+/*
-+ * ext2_xattr_rehash()
-+ *
-+ * Re-compute the extended attribute hash value after an entry has changed.
-+ */
-+static void ext2_xattr_rehash(struct ext2_xattr_header *header,
-+                            struct ext2_xattr_entry *entry)
-+{
-+      struct ext2_xattr_entry *here;
-+      __u32 hash = 0;
-+      
-+      ext2_xattr_hash_entry(header, entry);
-+      here = ENTRY(header+1);
-+      while (!IS_LAST_ENTRY(here)) {
-+              if (!here->e_hash) {
-+                      /* Block is not shared if an entry's hash value == 0 */
-+                      hash = 0;
-+                      break;
-+              }
-+              hash = (hash << BLOCK_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - BLOCK_HASH_SHIFT)) ^
-+                     le32_to_cpu(here->e_hash);
-+              here = EXT2_XATTR_NEXT(here);
-+      }
-+      header->h_hash = cpu_to_le32(hash);
-+}
-+
-+#undef BLOCK_HASH_SHIFT
-+
-+int __init
-+init_ext2_xattr(void)
-+{
-+      ext2_xattr_cache = mb_cache_create("ext2_xattr", NULL,
-+              sizeof(struct mb_cache_entry) +
-+              sizeof(struct mb_cache_entry_index), 1, 61);
-+      if (!ext2_xattr_cache)
-+              return -ENOMEM;
-+
-+      return 0;
-+}
-+
-+void
-+exit_ext2_xattr(void)
-+{
-+      mb_cache_destroy(ext2_xattr_cache);
-+}
-+
-+#else  /* CONFIG_EXT2_FS_XATTR_SHARING */
-+
-+int __init
-+init_ext2_xattr(void)
-+{
-+      return 0;
-+}
-+
-+void
-+exit_ext2_xattr(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT2_FS_XATTR_SHARING */
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext2/xattr_user.c       2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,103 @@
-+/*
-+ * linux/fs/ext2/xattr_user.c
-+ * Handler for extended user attributes.
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/string.h>
-+#include <linux/fs.h>
-+#include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
-+
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+# include <linux/ext2_acl.h>
-+#endif
-+
-+#define XATTR_USER_PREFIX "user."
-+
-+static size_t
-+ext2_xattr_user_list(char *list, struct inode *inode,
-+                   const char *name, int name_len)
-+{
-+      const int prefix_len = sizeof(XATTR_USER_PREFIX)-1;
-+
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return 0;
-+
-+      if (list) {
-+              memcpy(list, XATTR_USER_PREFIX, prefix_len);
-+              memcpy(list+prefix_len, name, name_len);
-+              list[prefix_len + name_len] = '\0';
-+      }
-+      return prefix_len + name_len + 1;
-+}
-+
-+static int
-+ext2_xattr_user_get(struct inode *inode, const char *name,
-+                  void *buffer, size_t size)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+      error = ext2_permission_locked(inode, MAY_READ);
-+#else
-+      error = permission(inode, MAY_READ);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext2_xattr_get(inode, EXT2_XATTR_INDEX_USER, name,
-+                            buffer, size);
-+}
-+
-+static int
-+ext2_xattr_user_set(struct inode *inode, const char *name,
-+                  const void *value, size_t size, int flags)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+      if ( !S_ISREG(inode->i_mode) &&
-+          (!S_ISDIR(inode->i_mode) || inode->i_mode & S_ISVTX))
-+              return -EPERM;
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+      error = ext2_permission_locked(inode, MAY_WRITE);
-+#else
-+      error = permission(inode, MAY_WRITE);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext2_xattr_set(inode, EXT2_XATTR_INDEX_USER, name,
-+                            value, size, flags);
-+}
-+
-+struct ext2_xattr_handler ext2_xattr_user_handler = {
-+      prefix: XATTR_USER_PREFIX,
-+      list:   ext2_xattr_user_list,
-+      get:    ext2_xattr_user_get,
-+      set:    ext2_xattr_user_set,
-+};
-+
-+int __init
-+init_ext2_xattr_user(void)
-+{
-+      return ext2_xattr_register(EXT2_XATTR_INDEX_USER,
-+                                 &ext2_xattr_user_handler);
-+}
-+
-+void
-+exit_ext2_xattr_user(void)
-+{
-+      ext2_xattr_unregister(EXT2_XATTR_INDEX_USER,
-+                            &ext2_xattr_user_handler);
-+}
---- kernel-2.4.20-6chaos_18_7/fs/ext3/Makefile~linux-2.4.20-xattr-0.8.54-chaos 2003-07-12 15:33:38.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/Makefile   2003-07-12 15:34:44.000000000 -0600
-@@ -1,5 +1,5 @@
- #
--# Makefile for the linux ext2-filesystem routines.
-+# Makefile for the linux ext3-filesystem routines.
- #
- # Note! Dependencies are done automagically by 'make dep', which also
- # removes any old dependencies. DON'T put your own dependencies here
-@@ -9,10 +9,14 @@
- O_TARGET := ext3.o
--export-objs :=        super.o inode.o
-+export-objs := ext3-exports.o
- obj-y    := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o \
--              ioctl.o namei.o super.o symlink.o hash.o
-+              ioctl.o namei.o super.o symlink.o hash.o ext3-exports.o
- obj-m    := $(O_TARGET)
-+export-objs += xattr.o
-+obj-$(CONFIG_EXT3_FS_XATTR) += xattr.o
-+obj-$(CONFIG_EXT3_FS_XATTR_USER) += xattr_user.o
-+
- include $(TOPDIR)/Rules.make
---- kernel-2.4.20-6chaos_18_7/fs/ext3/file.c~linux-2.4.20-xattr-0.8.54-chaos   2003-07-12 15:33:38.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/file.c     2003-07-12 15:34:44.000000000 -0600
-@@ -23,6 +23,7 @@
- #include <linux/locks.h>
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/ext3_jbd.h>
- #include <linux/smp_lock.h>
-@@ -126,5 +127,9 @@ struct file_operations ext3_file_operati
- struct inode_operations ext3_file_inode_operations = {
-       truncate:       ext3_truncate,          /* BKL held */
-       setattr:        ext3_setattr,           /* BKL held */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
---- kernel-2.4.20-6chaos_18_7/fs/ext3/ialloc.c~linux-2.4.20-xattr-0.8.54-chaos 2003-05-15 21:14:30.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/ialloc.c   2003-07-12 15:34:44.000000000 -0600
-@@ -17,6 +17,7 @@
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/stat.h>
- #include <linux/string.h>
- #include <linux/locks.h>
-@@ -216,6 +217,7 @@ void ext3_free_inode (handle_t *handle, 
-        * as writing the quota to disk may need the lock as well.
-        */
-       DQUOT_INIT(inode);
-+      ext3_xattr_delete_inode(handle, inode);
-       DQUOT_FREE_INODE(inode);
-       DQUOT_DROP(inode);
---- kernel-2.4.20-6chaos_18_7/fs/ext3/inode.c~linux-2.4.20-xattr-0.8.54-chaos  2003-05-15 21:14:30.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/inode.c    2003-07-12 15:34:44.000000000 -0600
-@@ -39,6 +39,18 @@
-  */
- #undef SEARCH_FROM_ZERO
-+/*
-+ * Test whether an inode is a fast symlink.
-+ */
-+static inline int ext3_inode_is_fast_symlink(struct inode *inode)
-+{
-+      int ea_blocks = inode->u.ext3_i.i_file_acl ?
-+              (inode->i_sb->s_blocksize >> 9) : 0;
-+
-+      return (S_ISLNK(inode->i_mode) &&
-+              inode->i_blocks - ea_blocks == 0);
-+}
-+
- /* The ext3 forget function must perform a revoke if we are freeing data
-  * which has been journaled.  Metadata (eg. indirect blocks) must be
-  * revoked in all cases. 
-@@ -48,7 +60,7 @@
-  * still needs to be revoked.
-  */
--static int ext3_forget(handle_t *handle, int is_metadata,
-+int ext3_forget(handle_t *handle, int is_metadata,
-                      struct inode *inode, struct buffer_head *bh,
-                      int blocknr)
- {
-@@ -179,9 +191,7 @@ void ext3_delete_inode (struct inode * i
- {
-       handle_t *handle;
-       
--      if (is_bad_inode(inode) ||
--          inode->i_ino == EXT3_ACL_IDX_INO ||
--          inode->i_ino == EXT3_ACL_DATA_INO)
-+      if (is_bad_inode(inode))
-               goto no_delete;
-       lock_kernel();
-@@ -1874,6 +1884,8 @@ void ext3_truncate(struct inode * inode)
-       if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
-           S_ISLNK(inode->i_mode)))
-               return;
-+      if (ext3_inode_is_fast_symlink(inode))
-+              return;
-       if (IS_APPEND(inode) || IS_IMMUTABLE(inode))
-               return;
-@@ -2021,8 +2033,6 @@ int ext3_get_inode_loc (struct inode *in
-       struct ext3_group_desc * gdp;
-               
-       if ((inode->i_ino != EXT3_ROOT_INO &&
--              inode->i_ino != EXT3_ACL_IDX_INO &&
--              inode->i_ino != EXT3_ACL_DATA_INO &&
-               inode->i_ino != EXT3_JOURNAL_INO &&
-               inode->i_ino < EXT3_FIRST_INO(inode->i_sb)) ||
-               inode->i_ino > le32_to_cpu(
-@@ -2149,10 +2159,7 @@ void ext3_read_inode(struct inode * inod
-       brelse (iloc.bh);
--      if (inode->i_ino == EXT3_ACL_IDX_INO ||
--          inode->i_ino == EXT3_ACL_DATA_INO)
--              /* Nothing to do */ ;
--      else if (S_ISREG(inode->i_mode)) {
-+      if (S_ISREG(inode->i_mode)) {
-               inode->i_op = &ext3_file_inode_operations;
-               inode->i_fop = &ext3_file_operations;
-               inode->i_mapping->a_ops = &ext3_aops;
-@@ -2160,15 +2167,17 @@ void ext3_read_inode(struct inode * inod
-               inode->i_op = &ext3_dir_inode_operations;
-               inode->i_fop = &ext3_dir_operations;
-       } else if (S_ISLNK(inode->i_mode)) {
--              if (!inode->i_blocks)
-+              if (ext3_inode_is_fast_symlink(inode))
-                       inode->i_op = &ext3_fast_symlink_inode_operations;
-               else {
--                      inode->i_op = &page_symlink_inode_operations;
-+                      inode->i_op = &ext3_symlink_inode_operations;
-                       inode->i_mapping->a_ops = &ext3_aops;
-               }
--      } else 
-+      } else {
-+              inode->i_op = &ext3_special_inode_operations;
-               init_special_inode(inode, inode->i_mode,
-                                  le32_to_cpu(iloc.raw_inode->i_block[0]));
-+      }
-       /* inode->i_attr_flags = 0;                             unused */
-       if (inode->u.ext3_i.i_flags & EXT3_SYNC_FL) {
-               /* inode->i_attr_flags |= ATTR_FLAG_SYNCRONOUS; unused */
---- kernel-2.4.20-6chaos_18_7/fs/ext3/namei.c~linux-2.4.20-xattr-0.8.54-chaos  2003-07-12 15:33:43.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/namei.c    2003-07-12 15:34:44.000000000 -0600
-@@ -29,6 +29,7 @@
- #include <linux/sched.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/fcntl.h>
- #include <linux/stat.h>
- #include <linux/string.h>
-@@ -1613,7 +1614,7 @@ static int ext3_mkdir(struct inode * dir
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
--      inode = ext3_new_inode (handle, dir, S_IFDIR);
-+      inode = ext3_new_inode (handle, dir, S_IFDIR | mode);
-       err = PTR_ERR(inode);
-       if (IS_ERR(inode))
-               goto out_stop;
-@@ -1621,7 +1622,6 @@ static int ext3_mkdir(struct inode * dir
-       inode->i_op = &ext3_dir_inode_operations;
-       inode->i_fop = &ext3_dir_operations;
-       inode->i_size = EXT3_I(inode)->i_disksize = inode->i_sb->s_blocksize;
--      inode->i_blocks = 0;    
-       dir_block = ext3_bread (handle, inode, 0, 1, &err);
-       if (!dir_block) {
-               inode->i_nlink--; /* is this nlink == 0? */
-@@ -1648,9 +1648,6 @@ static int ext3_mkdir(struct inode * dir
-       BUFFER_TRACE(dir_block, "call ext3_journal_dirty_metadata");
-       ext3_journal_dirty_metadata(handle, dir_block);
-       brelse (dir_block);
--      inode->i_mode = S_IFDIR | mode;
--      if (dir->i_mode & S_ISGID)
--              inode->i_mode |= S_ISGID;
-       ext3_mark_inode_dirty(handle, inode);
-       err = ext3_add_entry (handle, dentry, inode);
-       if (err) {
-@@ -2019,7 +2016,7 @@ static int ext3_symlink (struct inode * 
-               goto out_stop;
-       if (l > sizeof (EXT3_I(inode)->i_data)) {
--              inode->i_op = &page_symlink_inode_operations;
-+              inode->i_op = &ext3_symlink_inode_operations;
-               inode->i_mapping->a_ops = &ext3_aops;
-               /*
-                * block_symlink() calls back into ext3_prepare/commit_write.
-@@ -2245,4 +2242,16 @@ struct inode_operations ext3_dir_inode_o
-       rmdir:          ext3_rmdir,             /* BKL held */
-       mknod:          ext3_mknod,             /* BKL held */
-       rename:         ext3_rename,            /* BKL held */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
-+
-+struct inode_operations ext3_special_inode_operations = {
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
-+};
-+
---- kernel-2.4.20-6chaos_18_7/fs/ext3/super.c~linux-2.4.20-xattr-0.8.54-chaos  2003-07-12 15:33:38.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/super.c    2003-07-12 15:34:44.000000000 -0600
-@@ -24,6 +24,7 @@
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/slab.h>
- #include <linux/init.h>
- #include <linux/locks.h>
-@@ -406,6 +407,7 @@ void ext3_put_super (struct super_block 
-       kdev_t j_dev = sbi->s_journal->j_dev;
-       int i;
-+      ext3_xattr_put_super(sb);
-       journal_destroy(sbi->s_journal);
-       if (!(sb->s_flags & MS_RDONLY)) {
-               EXT3_CLEAR_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_RECOVER);
-@@ -502,6 +504,7 @@ static int parse_options (char * options
-                         int is_remount)
- {
-       unsigned long *mount_options = &sbi->s_mount_opt;
-+      
-       uid_t *resuid = &sbi->s_resuid;
-       gid_t *resgid = &sbi->s_resgid;
-       char * this_char;
-@@ -514,6 +517,13 @@ static int parse_options (char * options
-            this_char = strtok (NULL, ",")) {
-               if ((value = strchr (this_char, '=')) != NULL)
-                       *value++ = 0;
-+#ifdef CONFIG_EXT3_FS_XATTR_USER
-+              if (!strcmp (this_char, "user_xattr"))
-+                      set_opt (*mount_options, XATTR_USER);
-+              else if (!strcmp (this_char, "nouser_xattr"))
-+                      clear_opt (*mount_options, XATTR_USER);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -931,6 +941,12 @@ struct super_block * ext3_read_super (st
-       sbi->s_mount_opt = 0;
-       sbi->s_resuid = EXT3_DEF_RESUID;
-       sbi->s_resgid = EXT3_DEF_RESGID;
-+
-+      /* Default extended attribute flags */
-+#ifdef CONFIG_EXT3_FS_XATTR_USER
-+      /* set_opt(sbi->s_mount_opt, XATTR_USER); */
-+#endif
-+
-       if (!parse_options ((char *) data, &sb_block, sbi, &journal_inum, 0)) {
-               sb->s_dev = 0;
-               goto out_fail;
-@@ -1768,17 +1784,29 @@ static DECLARE_FSTYPE_DEV(ext3_fs_type, 
- static int __init init_ext3_fs(void)
- {
--        return register_filesystem(&ext3_fs_type);
-+      int error = init_ext3_xattr();
-+      if (error)
-+              return error;
-+      error = init_ext3_xattr_user();
-+      if (error)
-+              goto fail;
-+      error = register_filesystem(&ext3_fs_type);
-+      if (!error)
-+              return 0;
-+      
-+      exit_ext3_xattr_user();
-+fail:
-+      exit_ext3_xattr();
-+      return error;
- }
- static void __exit exit_ext3_fs(void)
- {
-       unregister_filesystem(&ext3_fs_type);
-+      exit_ext3_xattr_user();
-+      exit_ext3_xattr();
- }
--EXPORT_SYMBOL(ext3_force_commit);
--EXPORT_SYMBOL(ext3_bread);
--
- MODULE_AUTHOR("Remy Card, Stephen Tweedie, Andrew Morton, Andreas Dilger, Theodore Ts'o and others");
- MODULE_DESCRIPTION("Second Extended Filesystem with journaling extensions");
- MODULE_LICENSE("GPL");
---- kernel-2.4.20-6chaos_18_7/fs/ext3/symlink.c~linux-2.4.20-xattr-0.8.54-chaos        2002-05-07 15:53:46.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/symlink.c  2003-07-12 15:34:44.000000000 -0600
-@@ -20,6 +20,7 @@
- #include <linux/fs.h>
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
- static int ext3_readlink(struct dentry *dentry, char *buffer, int buflen)
- {
-@@ -33,7 +34,20 @@ static int ext3_follow_link(struct dentr
-       return vfs_follow_link(nd, s);
- }
-+struct inode_operations ext3_symlink_inode_operations = {
-+      readlink:       page_readlink,          /* BKL not held.  Don't need */
-+      follow_link:    page_follow_link,       /* BKL not held.  Don't need */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
-+};
-+
- struct inode_operations ext3_fast_symlink_inode_operations = {
-       readlink:       ext3_readlink,          /* BKL not held.  Don't need */
-       follow_link:    ext3_follow_link,       /* BKL not held.  Don't need */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/xattr.c    2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,1225 @@
-+/*
-+ * linux/fs/ext3/xattr.c
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ *
-+ * Fix by Harrison Xing <harrison@mountainviewdata.com>.
-+ * Ext3 code with a lot of help from Eric Jarman <ejarman@acm.org>.
-+ * Extended attributes for symlinks and special files added per
-+ *  suggestion of Luka Renko <luka.renko@hermes.si>.
-+ */
-+
-+/*
-+ * Extended attributes are stored on disk blocks allocated outside of
-+ * any inode. The i_file_acl field is then made to point to this allocated
-+ * block. If all extended attributes of an inode are identical, these
-+ * inodes may share the same extended attribute block. Such situations
-+ * are automatically detected by keeping a cache of recent attribute block
-+ * numbers and hashes over the block's contents in memory.
-+ *
-+ *
-+ * Extended attribute block layout:
-+ *
-+ *   +------------------+
-+ *   | header           |
-+ *   | entry 1          | |
-+ *   | entry 2          | | growing downwards
-+ *   | entry 3          | v
-+ *   | four null bytes  |
-+ *   | . . .            |
-+ *   | value 1          | ^
-+ *   | value 3          | | growing upwards
-+ *   | value 2          | |
-+ *   +------------------+
-+ *
-+ * The block header is followed by multiple entry descriptors. These entry
-+ * descriptors are variable in size, and alligned to EXT3_XATTR_PAD
-+ * byte boundaries. The entry descriptors are sorted by attribute name,
-+ * so that two extended attribute blocks can be compared efficiently.
-+ *
-+ * Attribute values are aligned to the end of the block, stored in
-+ * no specific order. They are also padded to EXT3_XATTR_PAD byte
-+ * boundaries. No additional gaps are left between them.
-+ *
-+ * Locking strategy
-+ * ----------------
-+ * The VFS already holds the BKL and the inode->i_sem semaphore when any of
-+ * the xattr inode operations are called, so we are guaranteed that only one
-+ * processes accesses extended attributes of an inode at any time.
-+ *
-+ * For writing we also grab the ext3_xattr_sem semaphore. This ensures that
-+ * only a single process is modifying an extended attribute block, even
-+ * if the block is shared among inodes.
-+ *
-+ * Note for porting to 2.5
-+ * -----------------------
-+ * The BKL will no longer be held in the xattr inode operations.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/fs.h>
-+#include <linux/locks.h>
-+#include <linux/slab.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
-+#include <linux/mbcache.h>
-+#include <linux/quotaops.h>
-+#include <asm/semaphore.h>
-+#include <linux/compatmac.h>
-+
-+#define EXT3_EA_USER "user."
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+# define mark_buffer_dirty(bh) mark_buffer_dirty(bh, 1)
-+#endif
-+
-+#define HDR(bh) ((struct ext3_xattr_header *)((bh)->b_data))
-+#define ENTRY(ptr) ((struct ext3_xattr_entry *)(ptr))
-+#define FIRST_ENTRY(bh) ENTRY(HDR(bh)+1)
-+#define IS_LAST_ENTRY(entry) (*(__u32 *)(entry) == 0)
-+
-+#ifdef EXT3_XATTR_DEBUG
-+# define ea_idebug(inode, f...) do { \
-+              printk(KERN_DEBUG "inode %s:%ld: ", \
-+                      kdevname(inode->i_dev), inode->i_ino); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+# define ea_bdebug(bh, f...) do { \
-+              printk(KERN_DEBUG "block %s:%ld: ", \
-+                      kdevname(bh->b_dev), bh->b_blocknr); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+#else
-+# define ea_idebug(f...)
-+# define ea_bdebug(f...)
-+#endif
-+
-+static int ext3_xattr_set2(handle_t *, struct inode *, struct buffer_head *,
-+                         struct ext3_xattr_header *);
-+
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+
-+static int ext3_xattr_cache_insert(struct buffer_head *);
-+static struct buffer_head *ext3_xattr_cache_find(struct inode *,
-+                                               struct ext3_xattr_header *);
-+static void ext3_xattr_cache_remove(struct buffer_head *);
-+static void ext3_xattr_rehash(struct ext3_xattr_header *,
-+                            struct ext3_xattr_entry *);
-+
-+static struct mb_cache *ext3_xattr_cache;
-+
-+#else
-+# define ext3_xattr_cache_insert(bh) 0
-+# define ext3_xattr_cache_find(inode, header) NULL
-+# define ext3_xattr_cache_remove(bh) while(0) {}
-+# define ext3_xattr_rehash(header, entry) while(0) {}
-+#endif
-+
-+/*
-+ * If a file system does not share extended attributes among inodes,
-+ * we should not need the ext3_xattr_sem semaphore. However, the
-+ * filesystem may still contain shared blocks, so we always take
-+ * the lock.
-+ */
-+
-+DECLARE_MUTEX(ext3_xattr_sem);
-+
-+static inline int
-+ext3_xattr_new_block(handle_t *handle, struct inode *inode,
-+                   int * errp, int force)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      int goal = le32_to_cpu(EXT3_SB(sb)->s_es->s_first_data_block) +
-+              EXT3_I(inode)->i_block_group * EXT3_BLOCKS_PER_GROUP(sb);
-+
-+      /* How can we enforce the allocation? */
-+      int block = ext3_new_block(handle, inode, goal, 0, 0, errp);
-+#ifdef OLD_QUOTAS
-+      if (!*errp)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#endif
-+      return block;
-+}
-+
-+static inline int
-+ext3_xattr_quota_alloc(struct inode *inode, int force)
-+{
-+      /* How can we enforce the allocation? */
-+#ifdef OLD_QUOTAS
-+      int error = DQUOT_ALLOC_BLOCK(inode->i_sb, inode, 1);
-+      if (!error)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#else
-+      int error = DQUOT_ALLOC_BLOCK(inode, 1);
-+#endif
-+      return error;
-+}
-+
-+#ifdef OLD_QUOTAS
-+
-+static inline void
-+ext3_xattr_quota_free(struct inode *inode)
-+{
-+      DQUOT_FREE_BLOCK(inode->i_sb, inode, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+static inline void
-+ext3_xattr_free_block(handle_t *handle, struct inode * inode,
-+                    unsigned long block)
-+{
-+      ext3_free_blocks(handle, inode, block, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+#else
-+# define ext3_xattr_quota_free(inode) \
-+      DQUOT_FREE_BLOCK(inode, 1)
-+# define ext3_xattr_free_block(handle, inode, block) \
-+      ext3_free_blocks(handle, inode, block, 1)
-+#endif
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,18)
-+
-+static inline struct buffer_head *
-+sb_bread(struct super_block *sb, int block)
-+{
-+      return bread(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+static inline struct buffer_head *
-+sb_getblk(struct super_block *sb, int block)
-+{
-+      return getblk(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+#endif
-+
-+struct ext3_xattr_handler *ext3_xattr_handlers[EXT3_XATTR_INDEX_MAX];
-+rwlock_t ext3_handler_lock = RW_LOCK_UNLOCKED;
-+
-+int
-+ext3_xattr_register(int name_index, struct ext3_xattr_handler *handler)
-+{
-+      int error = -EINVAL;
-+
-+      if (name_index > 0 && name_index <= EXT3_XATTR_INDEX_MAX) {
-+              write_lock(&ext3_handler_lock);
-+              if (!ext3_xattr_handlers[name_index-1]) {
-+                      ext3_xattr_handlers[name_index-1] = handler;
-+                      error = 0;
-+              }
-+              write_unlock(&ext3_handler_lock);
-+      }
-+      return error;
-+}
-+
-+void
-+ext3_xattr_unregister(int name_index, struct ext3_xattr_handler *handler)
-+{
-+      if (name_index > 0 || name_index <= EXT3_XATTR_INDEX_MAX) {
-+              write_lock(&ext3_handler_lock);
-+              ext3_xattr_handlers[name_index-1] = NULL;
-+              write_unlock(&ext3_handler_lock);
-+      }
-+}
-+
-+static inline const char *
-+strcmp_prefix(const char *a, const char *a_prefix)
-+{
-+      while (*a_prefix && *a == *a_prefix) {
-+              a++;
-+              a_prefix++;
-+      }
-+      return *a_prefix ? NULL : a;
-+}
-+
-+/*
-+ * Decode the extended attribute name, and translate it into
-+ * the name_index and name suffix.
-+ */
-+static inline struct ext3_xattr_handler *
-+ext3_xattr_resolve_name(const char **name)
-+{
-+      struct ext3_xattr_handler *handler = NULL;
-+      int i;
-+
-+      if (!*name)
-+              return NULL;
-+      read_lock(&ext3_handler_lock);
-+      for (i=0; i<EXT3_XATTR_INDEX_MAX; i++) {
-+              if (ext3_xattr_handlers[i]) {
-+                      const char *n = strcmp_prefix(*name,
-+                              ext3_xattr_handlers[i]->prefix);
-+                      if (n) {
-+                              handler = ext3_xattr_handlers[i];
-+                              *name = n;
-+                              break;
-+                      }
-+              }
-+      }
-+      read_unlock(&ext3_handler_lock);
-+      return handler;
-+}
-+
-+static inline struct ext3_xattr_handler *
-+ext3_xattr_handler(int name_index)
-+{
-+      struct ext3_xattr_handler *handler = NULL;
-+      if (name_index > 0 && name_index <= EXT3_XATTR_INDEX_MAX) {
-+              read_lock(&ext3_handler_lock);
-+              handler = ext3_xattr_handlers[name_index-1];
-+              read_unlock(&ext3_handler_lock);
-+      }
-+      return handler;
-+}
-+
-+/*
-+ * Inode operation getxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext3_getxattr(struct dentry *dentry, const char *name,
-+            void *buffer, size_t size)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->get(inode, name, buffer, size);
-+}
-+
-+/*
-+ * Inode operation listxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext3_listxattr(struct dentry *dentry, char *buffer, size_t size)
-+{
-+      return ext3_xattr_list(dentry->d_inode, buffer, size);
-+}
-+
-+/*
-+ * Inode operation setxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext3_setxattr(struct dentry *dentry, const char *name,
-+            const void *value, size_t size, int flags)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      if (size == 0)
-+              value = "";  /* empty EA, do not remove */
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, value, size, flags);
-+}
-+
-+/*
-+ * Inode operation removexattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext3_removexattr(struct dentry *dentry, const char *name)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, NULL, 0, XATTR_REPLACE);
-+}
-+
-+/*
-+ * ext3_xattr_get()
-+ *
-+ * Copy an extended attribute into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext3_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_entry *entry;
-+      unsigned int block, size;
-+      char *end;
-+      int name_len, error;
-+
-+      ea_idebug(inode, "name=%d.%s, buffer=%p, buffer_size=%ld",
-+                name_index, name, buffer, (long)buffer_size);
-+
-+      if (name == NULL)
-+              return -EINVAL;
-+      if (!EXT3_I(inode)->i_file_acl)
-+              return -ENOATTR;
-+      block = EXT3_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext3_error(inode->i_sb, "ext3_xattr_get",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* find named attribute */
-+      name_len = strlen(name);
-+
-+      error = -ERANGE;
-+      if (name_len > 255)
-+              goto cleanup;
-+      entry = FIRST_ENTRY(bh);
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              if (name_index == entry->e_name_index &&
-+                  name_len == entry->e_name_len &&
-+                  memcmp(name, entry->e_name, name_len) == 0)
-+                      goto found;
-+              entry = next;
-+      }
-+      /* Check the remaining name entries */
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              entry = next;
-+      }
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      error = -ENOATTR;
-+      goto cleanup;
-+found:
-+      /* check the buffer size */
-+      if (entry->e_value_block != 0)
-+              goto bad_block;
-+      size = le32_to_cpu(entry->e_value_size);
-+      if (size > inode->i_sb->s_blocksize ||
-+          le16_to_cpu(entry->e_value_offs) + size > inode->i_sb->s_blocksize)
-+              goto bad_block;
-+
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (buffer) {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+              /* return value of attribute */
-+              memcpy(buffer, bh->b_data + le16_to_cpu(entry->e_value_offs),
-+                      size);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_list()
-+ *
-+ * Copy a list of attribute names into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext3_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_entry *entry;
-+      unsigned int block, size = 0;
-+      char *buf, *end;
-+      int error;
-+
-+      ea_idebug(inode, "buffer=%p, buffer_size=%ld",
-+                buffer, (long)buffer_size);
-+
-+      if (!EXT3_I(inode)->i_file_acl)
-+              return 0;
-+      block = EXT3_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext3_error(inode->i_sb, "ext3_xattr_list",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* compute the size required for the list of attribute names */
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT3_XATTR_NEXT(entry)) {
-+              struct ext3_xattr_handler *handler;
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+
-+              handler = ext3_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      size += handler->list(NULL, inode, entry->e_name,
-+                                            entry->e_name_len);
-+      }
-+
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (!buffer) {
-+              error = size;
-+              goto cleanup;
-+      } else {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+      }
-+
-+      /* list the attribute names */
-+      buf = buffer;
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT3_XATTR_NEXT(entry)) {
-+              struct ext3_xattr_handler *handler;
-+
-+              handler = ext3_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      buf += handler->list(buf, inode, entry->e_name,
-+                                           entry->e_name_len);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * If the EXT3_FEATURE_COMPAT_EXT_ATTR feature of this file system is
-+ * not set, set it.
-+ */
-+static void ext3_xattr_update_super_block(handle_t *handle,
-+                                        struct super_block *sb)
-+{
-+      if (EXT3_HAS_COMPAT_FEATURE(sb, EXT3_FEATURE_COMPAT_EXT_ATTR))
-+              return;
-+
-+      lock_super(sb);
-+      ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+      EXT3_SB(sb)->s_feature_compat |= EXT3_FEATURE_COMPAT_EXT_ATTR;
-+#endif
-+      EXT3_SB(sb)->s_es->s_feature_compat |=
-+              cpu_to_le32(EXT3_FEATURE_COMPAT_EXT_ATTR);
-+      sb->s_dirt = 1;
-+      ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
-+      unlock_super(sb);
-+}
-+
-+/*
-+ * ext3_xattr_set()
-+ *
-+ * Create, replace or remove an extended attribute for this inode. Buffer
-+ * is NULL to remove an existing extended attribute, and non-NULL to
-+ * either replace an existing extended attribute, or create a new extended
-+ * attribute. The flags XATTR_REPLACE and XATTR_CREATE
-+ * specify that an extended attribute must exist and must not exist
-+ * previous to the call, respectively.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+int
-+ext3_xattr_set(handle_t *handle, struct inode *inode, int name_index,
-+             const char *name, const void *value, size_t value_len, int flags)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_header *header = NULL;
-+      struct ext3_xattr_entry *here, *last;
-+      unsigned int name_len;
-+      int block = EXT3_I(inode)->i_file_acl;
-+      int min_offs = sb->s_blocksize, not_found = 1, free, error;
-+      char *end;
-+      
-+      /*
-+       * header -- Points either into bh, or to a temporarily
-+       *           allocated buffer.
-+       * here -- The named entry found, or the place for inserting, within
-+       *         the block pointed to by header.
-+       * last -- Points right after the last named entry within the block
-+       *         pointed to by header.
-+       * min_offs -- The offset of the first value (values are aligned
-+       *             towards the end of the block).
-+       * end -- Points right after the block pointed to by header.
-+       */
-+      
-+      ea_idebug(inode, "name=%d.%s, value=%p, value_len=%ld",
-+                name_index, name, value, (long)value_len);
-+
-+      if (IS_RDONLY(inode))
-+              return -EROFS;
-+      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-+              return -EPERM;
-+      if (value == NULL)
-+              value_len = 0;
-+      if (name == NULL)
-+              return -EINVAL;
-+      name_len = strlen(name);
-+      if (name_len > 255 || value_len > sb->s_blocksize)
-+              return -ERANGE;
-+      down(&ext3_xattr_sem);
-+
-+      if (block) {
-+              /* The inode already has an extended attribute block. */
-+              bh = sb_bread(sb, block);
-+              error = -EIO;
-+              if (!bh)
-+                      goto cleanup;
-+              ea_bdebug(bh, "b_count=%d, refcount=%d",
-+                      atomic_read(&(bh->b_count)),
-+                      le32_to_cpu(HDR(bh)->h_refcount));
-+              header = HDR(bh);
-+              end = bh->b_data + bh->b_size;
-+              if (header->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+                  header->h_blocks != cpu_to_le32(1)) {
-+bad_block:            ext3_error(sb, "ext3_xattr_set",
-+                              "inode %ld: bad block %d", inode->i_ino, block);
-+                      error = -EIO;
-+                      goto cleanup;
-+              }
-+              /* Find the named attribute. */
-+              here = FIRST_ENTRY(bh);
-+              while (!IS_LAST_ENTRY(here)) {
-+                      struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(here);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!here->e_value_block && here->e_value_size) {
-+                              int offs = le16_to_cpu(here->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      not_found = name_index - here->e_name_index;
-+                      if (!not_found)
-+                              not_found = name_len - here->e_name_len;
-+                      if (!not_found)
-+                              not_found = memcmp(name, here->e_name,name_len);
-+                      if (not_found <= 0)
-+                              break;
-+                      here = next;
-+              }
-+              last = here;
-+              /* We still need to compute min_offs and last. */
-+              while (!IS_LAST_ENTRY(last)) {
-+                      struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(last);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!last->e_value_block && last->e_value_size) {
-+                              int offs = le16_to_cpu(last->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      last = next;
-+              }
-+
-+              /* Check whether we have enough space left. */
-+              free = min_offs - ((char*)last - (char*)header) - sizeof(__u32);
-+      } else {
-+              /* We will use a new extended attribute block. */
-+              free = sb->s_blocksize -
-+                      sizeof(struct ext3_xattr_header) - sizeof(__u32);
-+              here = last = NULL;  /* avoid gcc uninitialized warning. */
-+      }
-+
-+      if (not_found) {
-+              /* Request to remove a nonexistent attribute? */
-+              error = -ENOATTR;
-+              if (flags & XATTR_REPLACE)
-+                      goto cleanup;
-+              error = 0;
-+              if (value == NULL)
-+                      goto cleanup;
-+              else
-+                      free -= EXT3_XATTR_LEN(name_len);
-+      } else {
-+              /* Request to create an existing attribute? */
-+              error = -EEXIST;
-+              if (flags & XATTR_CREATE)
-+                      goto cleanup;
-+              if (!here->e_value_block && here->e_value_size) {
-+                      unsigned int size = le32_to_cpu(here->e_value_size);
-+
-+                      if (le16_to_cpu(here->e_value_offs) + size > 
-+                          sb->s_blocksize || size > sb->s_blocksize)
-+                              goto bad_block;
-+                      free += EXT3_XATTR_SIZE(size);
-+              }
-+      }
-+      free -= EXT3_XATTR_SIZE(value_len);
-+      error = -ENOSPC;
-+      if (free < 0)
-+              goto cleanup;
-+
-+      /* Here we know that we can set the new attribute. */
-+
-+      if (header) {
-+              if (header->h_refcount == cpu_to_le32(1)) {
-+                      ea_bdebug(bh, "modifying in-place");
-+                      ext3_xattr_cache_remove(bh);
-+                      error = ext3_journal_get_write_access(handle, bh);
-+                      if (error)
-+                              goto cleanup;
-+              } else {
-+                      int offset;
-+
-+                      ea_bdebug(bh, "cloning");
-+                      header = kmalloc(bh->b_size, GFP_KERNEL);
-+                      error = -ENOMEM;
-+                      if (header == NULL)
-+                              goto cleanup;
-+                      memcpy(header, HDR(bh), bh->b_size);
-+                      header->h_refcount = cpu_to_le32(1);
-+                      offset = (char *)header - bh->b_data;
-+                      here = ENTRY((char *)here + offset);
-+                      last = ENTRY((char *)last + offset);
-+              }
-+      } else {
-+              /* Allocate a buffer where we construct the new block. */
-+              header = kmalloc(sb->s_blocksize, GFP_KERNEL);
-+              error = -ENOMEM;
-+              if (header == NULL)
-+                      goto cleanup;
-+              memset(header, 0, sb->s_blocksize);
-+              end = (char *)header + sb->s_blocksize;
-+              header->h_magic = cpu_to_le32(EXT3_XATTR_MAGIC);
-+              header->h_blocks = header->h_refcount = cpu_to_le32(1);
-+              last = here = ENTRY(header+1);
-+      }
-+
-+      if (not_found) {
-+              /* Insert the new name. */
-+              int size = EXT3_XATTR_LEN(name_len);
-+              int rest = (char *)last - (char *)here;
-+              memmove((char *)here + size, here, rest);
-+              memset(here, 0, size);
-+              here->e_name_index = name_index;
-+              here->e_name_len = name_len;
-+              memcpy(here->e_name, name, name_len);
-+      } else {
-+              /* Remove the old value. */
-+              if (!here->e_value_block && here->e_value_size) {
-+                      char *first_val = (char *)header + min_offs;
-+                      int offs = le16_to_cpu(here->e_value_offs);
-+                      char *val = (char *)header + offs;
-+                      size_t size = EXT3_XATTR_SIZE(
-+                              le32_to_cpu(here->e_value_size));
-+                      memmove(first_val + size, first_val, val - first_val);
-+                      memset(first_val, 0, size);
-+                      here->e_value_offs = 0;
-+                      min_offs += size;
-+
-+                      /* Adjust all value offsets. */
-+                      last = ENTRY(header+1);
-+                      while (!IS_LAST_ENTRY(last)) {
-+                              int o = le16_to_cpu(last->e_value_offs);
-+                              if (!last->e_value_block && o < offs)
-+                                      last->e_value_offs =
-+                                              cpu_to_le16(o + size);
-+                              last = EXT3_XATTR_NEXT(last);
-+                      }
-+              }
-+              if (value == NULL) {
-+                      /* Remove this attribute. */
-+                      if (EXT3_XATTR_NEXT(ENTRY(header+1)) == last) {
-+                              /* This block is now empty. */
-+                              error = ext3_xattr_set2(handle, inode, bh,NULL);
-+                              goto cleanup;
-+                      } else {
-+                              /* Remove the old name. */
-+                              int size = EXT3_XATTR_LEN(name_len);
-+                              last = ENTRY((char *)last - size);
-+                              memmove(here, (char*)here + size,
-+                                      (char*)last - (char*)here);
-+                              memset(last, 0, size);
-+                      }
-+              }
-+      }
-+
-+      if (value != NULL) {
-+              /* Insert the new value. */
-+              here->e_value_size = cpu_to_le32(value_len);
-+              if (value_len) {
-+                      size_t size = EXT3_XATTR_SIZE(value_len);
-+                      char *val = (char *)header + min_offs - size;
-+                      here->e_value_offs =
-+                              cpu_to_le16((char *)val - (char *)header);
-+                      memset(val + size - EXT3_XATTR_PAD, 0,
-+                             EXT3_XATTR_PAD); /* Clear the pad bytes. */
-+                      memcpy(val, value, value_len);
-+              }
-+      }
-+      ext3_xattr_rehash(header, here);
-+
-+      error = ext3_xattr_set2(handle, inode, bh, header);
-+
-+cleanup:
-+      brelse(bh);
-+      if (!(bh && header == HDR(bh)))
-+              kfree(header);
-+      up(&ext3_xattr_sem);
-+
-+      return error;
-+}
-+
-+/*
-+ * Second half of ext3_xattr_set(): Update the file system.
-+ */
-+static int
-+ext3_xattr_set2(handle_t *handle, struct inode *inode,
-+              struct buffer_head *old_bh, struct ext3_xattr_header *header)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *new_bh = NULL;
-+      int error;
-+
-+      if (header) {
-+              new_bh = ext3_xattr_cache_find(inode, header);
-+              if (new_bh) {
-+                      /*
-+                       * We found an identical block in the cache.
-+                       * The old block will be released after updating
-+                       * the inode.
-+                       */
-+                      ea_bdebug(old_bh, "reusing block %ld",
-+                              new_bh->b_blocknr);
-+                      
-+                      error = -EDQUOT;
-+                      if (ext3_xattr_quota_alloc(inode, 1))
-+                              goto cleanup;
-+                      
-+                      error = ext3_journal_get_write_access(handle, new_bh);
-+                      if (error)
-+                              goto cleanup;
-+                      HDR(new_bh)->h_refcount = cpu_to_le32(
-+                              le32_to_cpu(HDR(new_bh)->h_refcount) + 1);
-+                      ea_bdebug(new_bh, "refcount now=%d",
-+                              le32_to_cpu(HDR(new_bh)->h_refcount));
-+              } else if (old_bh && header == HDR(old_bh)) {
-+                      /* Keep this block. */
-+                      new_bh = old_bh;
-+                      (void)ext3_xattr_cache_insert(new_bh);
-+              } else {
-+                      /* We need to allocate a new block */
-+                      int force = EXT3_I(inode)->i_file_acl != 0;
-+                      int block = ext3_xattr_new_block(handle, inode,
-+                                                       &error, force);
-+                      if (error)
-+                              goto cleanup;
-+                      ea_idebug(inode, "creating block %d", block);
-+
-+                      new_bh = sb_getblk(sb, block);
-+                      if (!new_bh) {
-+getblk_failed:                        ext3_xattr_free_block(handle, inode, block);
-+                              error = -EIO;
-+                              goto cleanup;
-+                      }
-+                      lock_buffer(new_bh);
-+                      error = ext3_journal_get_create_access(handle, new_bh);
-+                      if (error) {
-+                              unlock_buffer(new_bh);
-+                              goto getblk_failed;
-+                      }
-+                      memcpy(new_bh->b_data, header, new_bh->b_size);
-+                      mark_buffer_uptodate(new_bh, 1);
-+                      unlock_buffer(new_bh);
-+                      (void)ext3_xattr_cache_insert(new_bh);
-+                      
-+                      ext3_xattr_update_super_block(handle, sb);
-+              }
-+              error = ext3_journal_dirty_metadata(handle, new_bh);
-+              if (error)
-+                      goto cleanup;
-+      }
-+
-+      /* Update the inode. */
-+      EXT3_I(inode)->i_file_acl = new_bh ? new_bh->b_blocknr : 0;
-+      inode->i_ctime = CURRENT_TIME;
-+      ext3_mark_inode_dirty(handle, inode);
-+      if (IS_SYNC(inode))
-+              handle->h_sync = 1;
-+
-+      error = 0;
-+      if (old_bh && old_bh != new_bh) {
-+              /*
-+               * If there was an old block, and we are not still using it,
-+               * we now release the old block.
-+              */
-+              unsigned int refcount = le32_to_cpu(HDR(old_bh)->h_refcount);
-+
-+              error = ext3_journal_get_write_access(handle, old_bh);
-+              if (error)
-+                      goto cleanup;
-+              if (refcount == 1) {
-+                      /* Free the old block. */
-+                      ea_bdebug(old_bh, "freeing");
-+                      ext3_xattr_free_block(handle, inode, old_bh->b_blocknr);
-+
-+                      /* ext3_forget() calls bforget() for us, but we
-+                         let our caller release old_bh, so we need to
-+                         duplicate the handle before. */
-+                      get_bh(old_bh);
-+                      ext3_forget(handle, 1, inode, old_bh,old_bh->b_blocknr);
-+              } else {
-+                      /* Decrement the refcount only. */
-+                      refcount--;
-+                      HDR(old_bh)->h_refcount = cpu_to_le32(refcount);
-+                      ext3_xattr_quota_free(inode);
-+                      ext3_journal_dirty_metadata(handle, old_bh);
-+                      ea_bdebug(old_bh, "refcount now=%d", refcount);
-+              }
-+      }
-+
-+cleanup:
-+      if (old_bh != new_bh)
-+              brelse(new_bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_delete_inode()
-+ *
-+ * Free extended attribute resources associated with this inode. This
-+ * is called immediately before an inode is freed.
-+ */
-+void
-+ext3_xattr_delete_inode(handle_t *handle, struct inode *inode)
-+{
-+      struct buffer_head *bh;
-+      unsigned int block = EXT3_I(inode)->i_file_acl;
-+
-+      if (!block)
-+              return;
-+      down(&ext3_xattr_sem);
-+
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh) {
-+              ext3_error(inode->i_sb, "ext3_xattr_delete_inode",
-+                      "inode %ld: block %d read error", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "b_count=%d", atomic_read(&(bh->b_count)));
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+              ext3_error(inode->i_sb, "ext3_xattr_delete_inode",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ext3_journal_get_write_access(handle, bh);
-+      ea_bdebug(bh, "refcount now=%d", le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+      if (HDR(bh)->h_refcount == cpu_to_le32(1)) {
-+              ext3_xattr_cache_remove(bh);
-+              ext3_xattr_free_block(handle, inode, block);
-+              ext3_forget(handle, 1, inode, bh, block);
-+              bh = NULL;
-+      } else {
-+              HDR(bh)->h_refcount = cpu_to_le32(
-+                      le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+              ext3_journal_dirty_metadata(handle, bh);
-+              if (IS_SYNC(inode))
-+                      handle->h_sync = 1;
-+              ext3_xattr_quota_free(inode);
-+      }
-+      EXT3_I(inode)->i_file_acl = 0;
-+
-+cleanup:
-+      brelse(bh);
-+      up(&ext3_xattr_sem);
-+}
-+
-+/*
-+ * ext3_xattr_put_super()
-+ *
-+ * This is called when a file system is unmounted.
-+ */
-+void
-+ext3_xattr_put_super(struct super_block *sb)
-+{
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+      mb_cache_shrink(ext3_xattr_cache, sb->s_dev);
-+#endif
-+}
-+
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+
-+/*
-+ * ext3_xattr_cache_insert()
-+ *
-+ * Create a new entry in the extended attribute cache, and insert
-+ * it unless such an entry is already in the cache.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+static int
-+ext3_xattr_cache_insert(struct buffer_head *bh)
-+{
-+      __u32 hash = le32_to_cpu(HDR(bh)->h_hash);
-+      struct mb_cache_entry *ce;
-+      int error;
-+
-+      ce = mb_cache_entry_alloc(ext3_xattr_cache);
-+      if (!ce)
-+              return -ENOMEM;
-+      error = mb_cache_entry_insert(ce, bh->b_dev, bh->b_blocknr, &hash);
-+      if (error) {
-+              mb_cache_entry_free(ce);
-+              if (error == -EBUSY) {
-+                      ea_bdebug(bh, "already in cache (%d cache entries)",
-+                              atomic_read(&ext3_xattr_cache->c_entry_count));
-+                      error = 0;
-+              }
-+      } else {
-+              ea_bdebug(bh, "inserting [%x] (%d cache entries)", (int)hash,
-+                        atomic_read(&ext3_xattr_cache->c_entry_count));
-+              mb_cache_entry_release(ce);
-+      }
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_cmp()
-+ *
-+ * Compare two extended attribute blocks for equality.
-+ *
-+ * Returns 0 if the blocks are equal, 1 if they differ, and
-+ * a negative error number on errors.
-+ */
-+static int
-+ext3_xattr_cmp(struct ext3_xattr_header *header1,
-+             struct ext3_xattr_header *header2)
-+{
-+      struct ext3_xattr_entry *entry1, *entry2;
-+
-+      entry1 = ENTRY(header1+1);
-+      entry2 = ENTRY(header2+1);
-+      while (!IS_LAST_ENTRY(entry1)) {
-+              if (IS_LAST_ENTRY(entry2))
-+                      return 1;
-+              if (entry1->e_hash != entry2->e_hash ||
-+                  entry1->e_name_len != entry2->e_name_len ||
-+                  entry1->e_value_size != entry2->e_value_size ||
-+                  memcmp(entry1->e_name, entry2->e_name, entry1->e_name_len))
-+                      return 1;
-+              if (entry1->e_value_block != 0 || entry2->e_value_block != 0)
-+                      return -EIO;
-+              if (memcmp((char *)header1 + le16_to_cpu(entry1->e_value_offs),
-+                         (char *)header2 + le16_to_cpu(entry2->e_value_offs),
-+                         le32_to_cpu(entry1->e_value_size)))
-+                      return 1;
-+
-+              entry1 = EXT3_XATTR_NEXT(entry1);
-+              entry2 = EXT3_XATTR_NEXT(entry2);
-+      }
-+      if (!IS_LAST_ENTRY(entry2))
-+              return 1;
-+      return 0;
-+}
-+
-+/*
-+ * ext3_xattr_cache_find()
-+ *
-+ * Find an identical extended attribute block.
-+ *
-+ * Returns a pointer to the block found, or NULL if such a block was
-+ * not found or an error occurred.
-+ */
-+static struct buffer_head *
-+ext3_xattr_cache_find(struct inode *inode, struct ext3_xattr_header *header)
-+{
-+      __u32 hash = le32_to_cpu(header->h_hash);
-+      struct mb_cache_entry *ce;
-+
-+      if (!header->h_hash)
-+              return NULL;  /* never share */
-+      ea_idebug(inode, "looking for cached blocks [%x]", (int)hash);
-+      ce = mb_cache_entry_find_first(ext3_xattr_cache, 0, inode->i_dev, hash);
-+      while (ce) {
-+              struct buffer_head *bh = sb_bread(inode->i_sb, ce->e_block);
-+
-+              if (!bh) {
-+                      ext3_error(inode->i_sb, "ext3_xattr_cache_find",
-+                              "inode %ld: block %ld read error",
-+                              inode->i_ino, ce->e_block);
-+              } else if (le32_to_cpu(HDR(bh)->h_refcount) >
-+                         EXT3_XATTR_REFCOUNT_MAX) {
-+                      ea_idebug(inode, "block %ld refcount %d>%d",ce->e_block,
-+                              le32_to_cpu(HDR(bh)->h_refcount),
-+                              EXT3_XATTR_REFCOUNT_MAX);
-+              } else if (!ext3_xattr_cmp(header, HDR(bh))) {
-+                      ea_bdebug(bh, "b_count=%d",atomic_read(&(bh->b_count)));
-+                      mb_cache_entry_release(ce);
-+                      return bh;
-+              }
-+              brelse(bh);
-+              ce = mb_cache_entry_find_next(ce, 0, inode->i_dev, hash);
-+      }
-+      return NULL;
-+}
-+
-+/*
-+ * ext3_xattr_cache_remove()
-+ *
-+ * Remove the cache entry of a block from the cache. Called when a
-+ * block becomes invalid.
-+ */
-+static void
-+ext3_xattr_cache_remove(struct buffer_head *bh)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      ce = mb_cache_entry_get(ext3_xattr_cache, bh->b_dev, bh->b_blocknr);
-+      if (ce) {
-+              ea_bdebug(bh, "removing (%d cache entries remaining)",
-+                        atomic_read(&ext3_xattr_cache->c_entry_count)-1);
-+              mb_cache_entry_free(ce);
-+      } else 
-+              ea_bdebug(bh, "no cache entry");
-+}
-+
-+#define NAME_HASH_SHIFT 5
-+#define VALUE_HASH_SHIFT 16
-+
-+/*
-+ * ext3_xattr_hash_entry()
-+ *
-+ * Compute the hash of an extended attribute.
-+ */
-+static inline void ext3_xattr_hash_entry(struct ext3_xattr_header *header,
-+                                       struct ext3_xattr_entry *entry)
-+{
-+      __u32 hash = 0;
-+      char *name = entry->e_name;
-+      int n;
-+
-+      for (n=0; n < entry->e_name_len; n++) {
-+              hash = (hash << NAME_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - NAME_HASH_SHIFT)) ^
-+                     *name++;
-+      }
-+
-+      if (entry->e_value_block == 0 && entry->e_value_size != 0) {
-+              __u32 *value = (__u32 *)((char *)header +
-+                      le16_to_cpu(entry->e_value_offs));
-+              for (n = (le32_to_cpu(entry->e_value_size) +
-+                   EXT3_XATTR_ROUND) >> EXT3_XATTR_PAD_BITS; n; n--) {
-+                      hash = (hash << VALUE_HASH_SHIFT) ^
-+                             (hash >> (8*sizeof(hash) - VALUE_HASH_SHIFT)) ^
-+                             le32_to_cpu(*value++);
-+              }
-+      }
-+      entry->e_hash = cpu_to_le32(hash);
-+}
-+
-+#undef NAME_HASH_SHIFT
-+#undef VALUE_HASH_SHIFT
-+
-+#define BLOCK_HASH_SHIFT 16
-+
-+/*
-+ * ext3_xattr_rehash()
-+ *
-+ * Re-compute the extended attribute hash value after an entry has changed.
-+ */
-+static void ext3_xattr_rehash(struct ext3_xattr_header *header,
-+                            struct ext3_xattr_entry *entry)
-+{
-+      struct ext3_xattr_entry *here;
-+      __u32 hash = 0;
-+      
-+      ext3_xattr_hash_entry(header, entry);
-+      here = ENTRY(header+1);
-+      while (!IS_LAST_ENTRY(here)) {
-+              if (!here->e_hash) {
-+                      /* Block is not shared if an entry's hash value == 0 */
-+                      hash = 0;
-+                      break;
-+              }
-+              hash = (hash << BLOCK_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - BLOCK_HASH_SHIFT)) ^
-+                     le32_to_cpu(here->e_hash);
-+              here = EXT3_XATTR_NEXT(here);
-+      }
-+      header->h_hash = cpu_to_le32(hash);
-+}
-+
-+#undef BLOCK_HASH_SHIFT
-+
-+int __init
-+init_ext3_xattr(void)
-+{
-+      ext3_xattr_cache = mb_cache_create("ext3_xattr", NULL,
-+              sizeof(struct mb_cache_entry) +
-+              sizeof(struct mb_cache_entry_index), 1, 61);
-+      if (!ext3_xattr_cache)
-+              return -ENOMEM;
-+
-+      return 0;
-+}
-+
-+void
-+exit_ext3_xattr(void)
-+{
-+      if (ext3_xattr_cache)
-+              mb_cache_destroy(ext3_xattr_cache);
-+      ext3_xattr_cache = NULL;
-+}
-+
-+#else  /* CONFIG_EXT3_FS_XATTR_SHARING */
-+
-+int __init
-+init_ext3_xattr(void)
-+{
-+      return 0;
-+}
-+
-+void
-+exit_ext3_xattr(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT3_FS_XATTR_SHARING */
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/xattr_user.c       2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,111 @@
-+/*
-+ * linux/fs/ext3/xattr_user.c
-+ * Handler for extended user attributes.
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/string.h>
-+#include <linux/fs.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
-+
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+# include <linux/ext3_acl.h>
-+#endif
-+
-+#define XATTR_USER_PREFIX "user."
-+
-+static size_t
-+ext3_xattr_user_list(char *list, struct inode *inode,
-+                   const char *name, int name_len)
-+{
-+      const int prefix_len = sizeof(XATTR_USER_PREFIX)-1;
-+
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return 0;
-+
-+      if (list) {
-+              memcpy(list, XATTR_USER_PREFIX, prefix_len);
-+              memcpy(list+prefix_len, name, name_len);
-+              list[prefix_len + name_len] = '\0';
-+      }
-+      return prefix_len + name_len + 1;
-+}
-+
-+static int
-+ext3_xattr_user_get(struct inode *inode, const char *name,
-+                  void *buffer, size_t size)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+      error = ext3_permission_locked(inode, MAY_READ);
-+#else
-+      error = permission(inode, MAY_READ);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext3_xattr_get(inode, EXT3_XATTR_INDEX_USER, name,
-+                            buffer, size);
-+}
-+
-+static int
-+ext3_xattr_user_set(struct inode *inode, const char *name,
-+                  const void *value, size_t size, int flags)
-+{
-+      handle_t *handle;
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+      if ( !S_ISREG(inode->i_mode) &&
-+          (!S_ISDIR(inode->i_mode) || inode->i_mode & S_ISVTX))
-+              return -EPERM;
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+      error = ext3_permission_locked(inode, MAY_WRITE);
-+#else
-+      error = permission(inode, MAY_WRITE);
-+#endif
-+      if (error)
-+              return error;
-+
-+      handle = ext3_journal_start(inode, EXT3_XATTR_TRANS_BLOCKS);
-+      if (IS_ERR(handle))
-+              return PTR_ERR(handle);
-+      error = ext3_xattr_set(handle, inode, EXT3_XATTR_INDEX_USER, name,
-+                             value, size, flags);
-+      ext3_journal_stop(handle, inode);
-+
-+      return error;
-+}
-+
-+struct ext3_xattr_handler ext3_xattr_user_handler = {
-+      prefix: XATTR_USER_PREFIX,
-+      list:   ext3_xattr_user_list,
-+      get:    ext3_xattr_user_get,
-+      set:    ext3_xattr_user_set,
-+};
-+
-+int __init
-+init_ext3_xattr_user(void)
-+{
-+      return ext3_xattr_register(EXT3_XATTR_INDEX_USER,
-+                                 &ext3_xattr_user_handler);
-+}
-+
-+void
-+exit_ext3_xattr_user(void)
-+{
-+      ext3_xattr_unregister(EXT3_XATTR_INDEX_USER,
-+                            &ext3_xattr_user_handler);
-+}
---- kernel-2.4.20-6chaos_18_7/fs/jfs/jfs_xattr.h~linux-2.4.20-xattr-0.8.54-chaos       2003-02-14 15:59:11.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/jfs/jfs_xattr.h 2003-07-12 15:34:44.000000000 -0600
-@@ -52,8 +52,10 @@ struct jfs_ea_list {
- #define       END_EALIST(ealist) \
-       ((struct jfs_ea *) (((char *) (ealist)) + EALIST_SIZE(ealist)))
--extern int __jfs_setxattr(struct inode *, const char *, void *, size_t, int);
--extern int jfs_setxattr(struct dentry *, const char *, void *, size_t, int);
-+extern int __jfs_setxattr(struct inode *, const char *, const void *, size_t,
-+                        int);
-+extern int jfs_setxattr(struct dentry *, const char *, const void *, size_t,
-+                      int);
- extern ssize_t __jfs_getxattr(struct inode *, const char *, void *, size_t);
- extern ssize_t jfs_getxattr(struct dentry *, const char *, void *, size_t);
- extern ssize_t jfs_listxattr(struct dentry *, char *, size_t);
---- kernel-2.4.20-6chaos_18_7/fs/jfs/xattr.c~linux-2.4.20-xattr-0.8.54-chaos   2003-02-14 15:59:11.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/jfs/xattr.c     2003-07-12 15:34:44.000000000 -0600
-@@ -641,7 +641,7 @@ static int ea_put(struct inode *inode, s
- }
- static int can_set_xattr(struct inode *inode, const char *name,
--                       void *value, size_t value_len)
-+                       const void *value, size_t value_len)
- {
-       if (IS_RDONLY(inode))
-               return -EROFS;
-@@ -660,7 +660,7 @@ static int can_set_xattr(struct inode *i
-       return permission(inode, MAY_WRITE);
- }
--int __jfs_setxattr(struct inode *inode, const char *name, void *value,
-+int __jfs_setxattr(struct inode *inode, const char *name, const void *value,
-                  size_t value_len, int flags)
- {
-       struct jfs_ea_list *ealist;
-@@ -799,7 +799,7 @@ int __jfs_setxattr(struct inode *inode, 
-       return rc;
- }
--int jfs_setxattr(struct dentry *dentry, const char *name, void *value,
-+int jfs_setxattr(struct dentry *dentry, const char *name, const void *value,
-                size_t value_len, int flags)
- {
-       if (value == NULL) {    /* empty EA, do not remove */
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/mbcache.c       2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,648 @@
-+/*
-+ * linux/fs/mbcache.c
-+ * (C) 2001-2002 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+/*
-+ * Filesystem Meta Information Block Cache (mbcache)
-+ *
-+ * The mbcache caches blocks of block devices that need to be located
-+ * by their device/block number, as well as by other criteria (such
-+ * as the block's contents).
-+ *
-+ * There can only be one cache entry in a cache per device and block number.
-+ * Additional indexes need not be unique in this sense. The number of
-+ * additional indexes (=other criteria) can be hardwired at compile time
-+ * or specified at cache create time.
-+ *
-+ * Each cache entry is of fixed size. An entry may be `valid' or `invalid'
-+ * in the cache. A valid entry is in the main hash tables of the cache,
-+ * and may also be in the lru list. An invalid entry is not in any hashes
-+ * or lists.
-+ *
-+ * A valid cache entry is only in the lru list if no handles refer to it.
-+ * Invalid cache entries will be freed when the last handle to the cache
-+ * entry is released. Entries that cannot be freed immediately are put
-+ * back on the lru list.
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+
-+#include <linux/fs.h>
-+#include <linux/slab.h>
-+#include <linux/sched.h>
-+#include <linux/cache_def.h>
-+#include <linux/version.h>
-+#include <linux/init.h>
-+#include <linux/mbcache.h>
-+
-+
-+#ifdef MB_CACHE_DEBUG
-+# define mb_debug(f...) do { \
-+              printk(KERN_DEBUG f); \
-+              printk("\n"); \
-+      } while (0)
-+#define mb_assert(c) do { if (!(c)) \
-+              printk(KERN_ERR "assertion " #c " failed\n"); \
-+      } while(0)
-+#else
-+# define mb_debug(f...) do { } while(0)
-+# define mb_assert(c) do { } while(0)
-+#endif
-+#define mb_error(f...) do { \
-+              printk(KERN_ERR f); \
-+              printk("\n"); \
-+      } while(0)
-+              
-+MODULE_AUTHOR("Andreas Gruenbacher <a.gruenbacher@computer.org>");
-+MODULE_DESCRIPTION("Meta block cache (for extended attributes)");
-+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,0)
-+MODULE_LICENSE("GPL");
-+#endif
-+
-+EXPORT_SYMBOL(mb_cache_create);
-+EXPORT_SYMBOL(mb_cache_shrink);
-+EXPORT_SYMBOL(mb_cache_destroy);
-+EXPORT_SYMBOL(mb_cache_entry_alloc);
-+EXPORT_SYMBOL(mb_cache_entry_insert);
-+EXPORT_SYMBOL(mb_cache_entry_release);
-+EXPORT_SYMBOL(mb_cache_entry_takeout);
-+EXPORT_SYMBOL(mb_cache_entry_free);
-+EXPORT_SYMBOL(mb_cache_entry_dup);
-+EXPORT_SYMBOL(mb_cache_entry_get);
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+EXPORT_SYMBOL(mb_cache_entry_find_first);
-+EXPORT_SYMBOL(mb_cache_entry_find_next);
-+#endif
-+
-+
-+/*
-+ * Global data: list of all mbcache's, lru list, and a spinlock for
-+ * accessing cache data structures on SMP machines. The lru list is
-+ * global across all mbcaches.
-+ */
-+
-+static LIST_HEAD(mb_cache_list);
-+static LIST_HEAD(mb_cache_lru_list);
-+static spinlock_t mb_cache_spinlock = SPIN_LOCK_UNLOCKED;
-+
-+static inline int
-+mb_cache_indexes(struct mb_cache *cache)
-+{
-+#ifdef MB_CACHE_INDEXES_COUNT
-+      return MB_CACHE_INDEXES_COUNT;
-+#else
-+      return cache->c_indexes_count;
-+#endif
-+}
-+
-+/*
-+ * What the mbcache registers as to get shrunk dynamically.
-+ */
-+
-+static void
-+mb_cache_memory_pressure(int priority, unsigned int gfp_mask);
-+
-+static struct cache_definition mb_cache_definition = {
-+      "mb_cache",
-+      mb_cache_memory_pressure
-+};
-+
-+
-+static inline int
-+__mb_cache_entry_is_hashed(struct mb_cache_entry *ce)
-+{
-+      return !list_empty(&ce->e_block_list);
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_unhash(struct mb_cache_entry *ce)
-+{
-+      int n;
-+
-+      if (__mb_cache_entry_is_hashed(ce)) {
-+              list_del_init(&ce->e_block_list);
-+              for (n=0; n<mb_cache_indexes(ce->e_cache); n++)
-+                      list_del(&ce->e_indexes[n].o_list);
-+      }
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_forget(struct mb_cache_entry *ce, int gfp_mask)
-+{
-+      struct mb_cache *cache = ce->e_cache;
-+
-+      mb_assert(atomic_read(&ce->e_used) == 0);
-+      if (cache->c_op.free && cache->c_op.free(ce, gfp_mask)) {
-+              /* free failed -- put back on the lru list
-+                 for freeing later. */
-+              spin_lock(&mb_cache_spinlock);
-+              list_add(&ce->e_lru_list, &mb_cache_lru_list);
-+              spin_unlock(&mb_cache_spinlock);
-+      } else {
-+              kmem_cache_free(cache->c_entry_cache, ce);
-+              atomic_dec(&cache->c_entry_count);
-+      }
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_release_unlock(struct mb_cache_entry *ce)
-+{
-+      if (atomic_dec_and_test(&ce->e_used)) {
-+              if (__mb_cache_entry_is_hashed(ce))
-+                      list_add_tail(&ce->e_lru_list, &mb_cache_lru_list);
-+              else {
-+                      spin_unlock(&mb_cache_spinlock);
-+                      __mb_cache_entry_forget(ce, GFP_KERNEL);
-+                      return;
-+              }
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+}
-+
-+
-+/*
-+ * mb_cache_memory_pressure()  memory pressure callback
-+ *
-+ * This function is called by the kernel memory management when memory
-+ * gets low.
-+ *
-+ * @priority: Amount by which to shrink the cache (0 = highes priority)
-+ * @gfp_mask: (ignored)
-+ */
-+static void
-+mb_cache_memory_pressure(int priority, unsigned int gfp_mask)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+      int count = 0;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &mb_cache_list) {
-+              struct mb_cache *cache =
-+                      list_entry(l, struct mb_cache, c_cache_list);
-+              mb_debug("cache %s (%d)", cache->c_name,
-+                        atomic_read(&cache->c_entry_count));
-+              count += atomic_read(&cache->c_entry_count);
-+      }
-+      mb_debug("trying to free %d of %d entries",
-+                count / (priority ? priority : 1), count);
-+      if (priority)
-+              count /= priority;
-+      while (count-- && !list_empty(&mb_cache_lru_list)) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(mb_cache_lru_list.next,
-+                                 struct mb_cache_entry, e_lru_list);
-+              list_del(&ce->e_lru_list);
-+              __mb_cache_entry_unhash(ce);
-+              list_add_tail(&ce->e_lru_list, &free_list);
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), gfp_mask);
-+      }
-+}
-+
-+
-+/*
-+ * mb_cache_create()  create a new cache
-+ *
-+ * All entries in one cache are equal size. Cache entries may be from
-+ * multiple devices. If this is the first mbcache created, registers
-+ * the cache with kernel memory management. Returns NULL if no more
-+ * memory was available.
-+ *
-+ * @name: name of the cache (informal)
-+ * @cache_op: contains the callback called when freeing a cache entry
-+ * @entry_size: The size of a cache entry, including
-+ *              struct mb_cache_entry
-+ * @indexes_count: number of additional indexes in the cache. Must equal
-+ *                 MB_CACHE_INDEXES_COUNT if the number of indexes is
-+ *                 hardwired.
-+ * @bucket_count: number of hash buckets
-+ */
-+struct mb_cache *
-+mb_cache_create(const char *name, struct mb_cache_op *cache_op,
-+              size_t entry_size, int indexes_count, int bucket_count)
-+{
-+      int m=0, n;
-+      struct mb_cache *cache = NULL;
-+
-+      if(entry_size < sizeof(struct mb_cache_entry) +
-+         indexes_count * sizeof(struct mb_cache_entry_index))
-+              return NULL;
-+
-+      MOD_INC_USE_COUNT;
-+      cache = kmalloc(sizeof(struct mb_cache) +
-+                      indexes_count * sizeof(struct list_head), GFP_KERNEL);
-+      if (!cache)
-+              goto fail;
-+      cache->c_name = name;
-+      cache->c_op.free = NULL;
-+      if (cache_op)
-+              cache->c_op.free = cache_op->free;
-+      atomic_set(&cache->c_entry_count, 0);
-+      cache->c_bucket_count = bucket_count;
-+#ifdef MB_CACHE_INDEXES_COUNT
-+      mb_assert(indexes_count == MB_CACHE_INDEXES_COUNT);
-+#else
-+      cache->c_indexes_count = indexes_count;
-+#endif
-+      cache->c_block_hash = kmalloc(bucket_count * sizeof(struct list_head),
-+                                    GFP_KERNEL);
-+      if (!cache->c_block_hash)
-+              goto fail;
-+      for (n=0; n<bucket_count; n++)
-+              INIT_LIST_HEAD(&cache->c_block_hash[n]);
-+      for (m=0; m<indexes_count; m++) {
-+              cache->c_indexes_hash[m] = kmalloc(bucket_count *
-+                                               sizeof(struct list_head),
-+                                               GFP_KERNEL);
-+              if (!cache->c_indexes_hash[m])
-+                      goto fail;
-+              for (n=0; n<bucket_count; n++)
-+                      INIT_LIST_HEAD(&cache->c_indexes_hash[m][n]);
-+      }
-+      cache->c_entry_cache = kmem_cache_create(name, entry_size, 0,
-+              0 /*SLAB_POISON | SLAB_RED_ZONE*/, NULL, NULL);
-+      if (!cache->c_entry_cache)
-+              goto fail;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_add(&cache->c_cache_list, &mb_cache_list);
-+      spin_unlock(&mb_cache_spinlock);
-+      return cache;
-+
-+fail:
-+      if (cache) {
-+              while (--m >= 0)
-+                      kfree(cache->c_indexes_hash[m]);
-+              if (cache->c_block_hash)
-+                      kfree(cache->c_block_hash);
-+              kfree(cache);
-+      }
-+      MOD_DEC_USE_COUNT;
-+      return NULL;
-+}
-+
-+
-+/*
-+ * mb_cache_shrink()
-+ *
-+ * Removes all cache entires of a device from the cache. All cache entries
-+ * currently in use cannot be freed, and thus remain in the cache.
-+ *
-+ * @cache: which cache to shrink
-+ * @dev: which device's cache entries to shrink
-+ */
-+void
-+mb_cache_shrink(struct mb_cache *cache, kdev_t dev)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &mb_cache_lru_list) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_lru_list);
-+              if (ce->e_dev == dev) {
-+                      list_del(&ce->e_lru_list);
-+                      list_add_tail(&ce->e_lru_list, &free_list);
-+                      __mb_cache_entry_unhash(ce);
-+              }
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), GFP_KERNEL);
-+      }
-+}
-+
-+
-+/*
-+ * mb_cache_destroy()
-+ *
-+ * Shrinks the cache to its minimum possible size (hopefully 0 entries),
-+ * and then destroys it. If this was the last mbcache, un-registers the
-+ * mbcache from kernel memory management.
-+ */
-+void
-+mb_cache_destroy(struct mb_cache *cache)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+      int n;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &mb_cache_lru_list) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_lru_list);
-+              if (ce->e_cache == cache) {
-+                      list_del(&ce->e_lru_list);
-+                      list_add_tail(&ce->e_lru_list, &free_list);
-+                      __mb_cache_entry_unhash(ce);
-+              }
-+      }
-+      list_del(&cache->c_cache_list);
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), GFP_KERNEL);
-+      }
-+
-+      if (atomic_read(&cache->c_entry_count) > 0) {
-+              mb_error("cache %s: %d orphaned entries",
-+                        cache->c_name,
-+                        atomic_read(&cache->c_entry_count));
-+      }
-+
-+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,3,0))
-+      /* We don't have kmem_cache_destroy() in 2.2.x */
-+      kmem_cache_shrink(cache->c_entry_cache);
-+#else
-+      kmem_cache_destroy(cache->c_entry_cache);
-+#endif
-+      for (n=0; n < mb_cache_indexes(cache); n++)
-+              kfree(cache->c_indexes_hash[n]);
-+      kfree(cache->c_block_hash);
-+      kfree(cache);
-+
-+      MOD_DEC_USE_COUNT;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_alloc()
-+ *
-+ * Allocates a new cache entry. The new entry will not be valid initially,
-+ * and thus cannot be looked up yet. It should be filled with data, and
-+ * then inserted into the cache using mb_cache_entry_insert(). Returns NULL
-+ * if no more memory was available.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_alloc(struct mb_cache *cache)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      atomic_inc(&cache->c_entry_count);
-+      ce = kmem_cache_alloc(cache->c_entry_cache, GFP_KERNEL);
-+      if (ce) {
-+              INIT_LIST_HEAD(&ce->e_lru_list);
-+              INIT_LIST_HEAD(&ce->e_block_list);
-+              ce->e_cache = cache;
-+              atomic_set(&ce->e_used, 1);
-+      }
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_insert()
-+ *
-+ * Inserts an entry that was allocated using mb_cache_entry_alloc() into
-+ * the cache. After this, the cache entry can be looked up, but is not yet
-+ * in the lru list as the caller still holds a handle to it. Returns 0 on
-+ * success, or -EBUSY if a cache entry for that device + inode exists
-+ * already (this may happen after a failed lookup, if another process has
-+ * inserted the same cache entry in the meantime).
-+ *
-+ * @dev: device the cache entry belongs to
-+ * @block: block number
-+ * @keys: array of additional keys. There must be indexes_count entries
-+ *        in the array (as specified when creating the cache).
-+ */
-+int
-+mb_cache_entry_insert(struct mb_cache_entry *ce, kdev_t dev,
-+                    unsigned long block, unsigned int keys[])
-+{
-+      struct mb_cache *cache = ce->e_cache;
-+      unsigned int bucket = (HASHDEV(dev) + block) % cache->c_bucket_count;
-+      struct list_head *l;
-+      int error = -EBUSY, n;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &cache->c_block_hash[bucket]) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_block_list);
-+              if (ce->e_dev == dev && ce->e_block == block)
-+                      goto out;
-+      }
-+      __mb_cache_entry_unhash(ce);
-+      ce->e_dev = dev;
-+      ce->e_block = block;
-+      list_add(&ce->e_block_list, &cache->c_block_hash[bucket]);
-+      for (n=0; n<mb_cache_indexes(cache); n++) {
-+              ce->e_indexes[n].o_key = keys[n];
-+              bucket = keys[n] % cache->c_bucket_count;
-+              list_add(&ce->e_indexes[n].o_list,
-+                       &cache->c_indexes_hash[n][bucket]);
-+      }
-+out:
-+      spin_unlock(&mb_cache_spinlock);
-+      return error;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_release()
-+ *
-+ * Release a handle to a cache entry. When the last handle to a cache entry
-+ * is released it is either freed (if it is invalid) or otherwise inserted
-+ * in to the lru list.
-+ */
-+void
-+mb_cache_entry_release(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      __mb_cache_entry_release_unlock(ce);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_takeout()
-+ *
-+ * Take a cache entry out of the cache, making it invalid. The entry can later
-+ * be re-inserted using mb_cache_entry_insert(), or released using
-+ * mb_cache_entry_release().
-+ */
-+void
-+mb_cache_entry_takeout(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      mb_assert(list_empty(&ce->e_lru_list));
-+      __mb_cache_entry_unhash(ce);
-+      spin_unlock(&mb_cache_spinlock);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_free()
-+ *
-+ * This is equivalent to the sequence mb_cache_entry_takeout() --
-+ * mb_cache_entry_release().
-+ */
-+void
-+mb_cache_entry_free(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      mb_assert(list_empty(&ce->e_lru_list));
-+      __mb_cache_entry_unhash(ce);
-+      __mb_cache_entry_release_unlock(ce);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_dup()
-+ *
-+ * Duplicate a handle to a cache entry (does not duplicate the cache entry
-+ * itself). After the call, both the old and the new handle must be released.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_dup(struct mb_cache_entry *ce)
-+{
-+      atomic_inc(&ce->e_used);
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_get()
-+ *
-+ * Get a cache entry  by device / block number. (There can only be one entry
-+ * in the cache per device and block.) Returns NULL if no such cache entry
-+ * exists.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_get(struct mb_cache *cache, kdev_t dev, unsigned long block)
-+{
-+      unsigned int bucket = (HASHDEV(dev) + block) % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &cache->c_block_hash[bucket]) {
-+              ce = list_entry(l, struct mb_cache_entry, e_block_list);
-+              if (ce->e_dev == dev && ce->e_block == block) {
-+                      if (!list_empty(&ce->e_lru_list))
-+                              list_del_init(&ce->e_lru_list);
-+                      atomic_inc(&ce->e_used);
-+                      goto cleanup;
-+              }
-+      }
-+      ce = NULL;
-+
-+cleanup:
-+      spin_unlock(&mb_cache_spinlock);
-+      return ce;
-+}
-+
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+
-+static struct mb_cache_entry *
-+__mb_cache_entry_find(struct list_head *l, struct list_head *head,
-+                    int index, kdev_t dev, unsigned int key)
-+{
-+      while (l != head) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry,
-+                                 e_indexes[index].o_list);
-+              if (ce->e_dev == dev && ce->e_indexes[index].o_key == key) {
-+                      if (!list_empty(&ce->e_lru_list))
-+                              list_del_init(&ce->e_lru_list);
-+                      atomic_inc(&ce->e_used);
-+                      return ce;
-+              }
-+              l = l->next;
-+      }
-+      return NULL;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_find_first()
-+ *
-+ * Find the first cache entry on a given device with a certain key in
-+ * an additional index. Additonal matches can be found with
-+ * mb_cache_entry_find_next(). Returns NULL if no match was found.
-+ *
-+ * @cache: the cache to search
-+ * @index: the number of the additonal index to search (0<=index<indexes_count)
-+ * @dev: the device the cache entry should belong to
-+ * @key: the key in the index
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_find_first(struct mb_cache *cache, int index, kdev_t dev,
-+                        unsigned int key)
-+{
-+      unsigned int bucket = key % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      mb_assert(index < mb_cache_indexes(cache));
-+      spin_lock(&mb_cache_spinlock);
-+      l = cache->c_indexes_hash[index][bucket].next;
-+      ce = __mb_cache_entry_find(l, &cache->c_indexes_hash[index][bucket],
-+                                 index, dev, key);
-+      spin_unlock(&mb_cache_spinlock);
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_find_next()
-+ *
-+ * Find the next cache entry on a given device with a certain key in an
-+ * additional index. Returns NULL if no match could be found. The previous
-+ * entry is atomatically released, so that mb_cache_entry_find_next() can
-+ * be called like this:
-+ *
-+ * entry = mb_cache_entry_find_first();
-+ * while (entry) {
-+ *    ...
-+ *    entry = mb_cache_entry_find_next(entry, ...);
-+ * }
-+ *
-+ * @prev: The previous match
-+ * @index: the number of the additonal index to search (0<=index<indexes_count)
-+ * @dev: the device the cache entry should belong to
-+ * @key: the key in the index
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_find_next(struct mb_cache_entry *prev, int index, kdev_t dev,
-+                       unsigned int key)
-+{
-+      struct mb_cache *cache = prev->e_cache;
-+      unsigned int bucket = key % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      mb_assert(index < mb_cache_indexes(cache));
-+      spin_lock(&mb_cache_spinlock);
-+      l = prev->e_indexes[index].o_list.next;
-+      ce = __mb_cache_entry_find(l, &cache->c_indexes_hash[index][bucket],
-+                                 index, dev, key);
-+      __mb_cache_entry_release_unlock(prev);
-+      return ce;
-+}
-+
-+#endif  /* !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0) */
-+
-+static int __init init_mbcache(void)
-+{
-+      register_cache(&mb_cache_definition);
-+      return 0;
-+}
-+
-+static void __exit exit_mbcache(void)
-+{
-+      unregister_cache(&mb_cache_definition);
-+}
-+
-+module_init(init_mbcache)
-+module_exit(exit_mbcache)
-+
---- kernel-2.4.20-6chaos_18_7/include/asm-arm/unistd.h~linux-2.4.20-xattr-0.8.54-chaos 2003-05-15 21:14:42.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/asm-arm/unistd.h   2003-07-12 15:34:44.000000000 -0600
-@@ -244,7 +244,6 @@
- #define __NR_security                 (__NR_SYSCALL_BASE+223)
- #define __NR_gettid                   (__NR_SYSCALL_BASE+224)
- #define __NR_readahead                        (__NR_SYSCALL_BASE+225)
--#if 0 /* allocated in 2.5 */
- #define __NR_setxattr                 (__NR_SYSCALL_BASE+226)
- #define __NR_lsetxattr                        (__NR_SYSCALL_BASE+227)
- #define __NR_fsetxattr                        (__NR_SYSCALL_BASE+228)
-@@ -257,7 +256,6 @@
- #define __NR_removexattr              (__NR_SYSCALL_BASE+235)
- #define __NR_lremovexattr             (__NR_SYSCALL_BASE+236)
- #define __NR_fremovexattr             (__NR_SYSCALL_BASE+237)
--#endif
- #define __NR_tkill                    (__NR_SYSCALL_BASE+238)
- /*
-  * Please check 2.5 _before_ adding calls here,
---- kernel-2.4.20-6chaos_18_7/include/asm-ppc64/unistd.h~linux-2.4.20-xattr-0.8.54-chaos       2002-09-25 11:13:42.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/asm-ppc64/unistd.h 2003-07-12 15:34:44.000000000 -0600
-@@ -218,6 +218,7 @@
- #define __NR_gettid           207
- #if 0 /* Reserved syscalls */
- #define __NR_tkill            208
-+#endif
- #define __NR_setxattr         209
- #define __NR_lsetxattr                210
- #define __NR_fsetxattr                211
-@@ -230,6 +231,7 @@
- #define __NR_removexattr      218
- #define __NR_lremovexattr     219
- #define __NR_fremovexattr     220
-+#if 0 /* Reserved syscalls */
- #define __NR_futex            221
- #endif
---- kernel-2.4.20-6chaos_18_7/include/asm-s390/unistd.h~linux-2.4.20-xattr-0.8.54-chaos        2002-09-25 11:13:44.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/asm-s390/unistd.h  2003-07-12 15:34:44.000000000 -0600
-@@ -212,9 +212,18 @@
- #define __NR_madvise            219
- #define __NR_getdents64               220
- #define __NR_fcntl64          221
--/*
-- * Numbers 224-235 are reserved for posix acl
-- */
-+#define __NR_setxattr         224
-+#define __NR_lsetxattr                225
-+#define __NR_fsetxattr                226
-+#define __NR_getxattr         227
-+#define __NR_lgetxattr                228
-+#define __NR_fgetxattr                229
-+#define __NR_listxattr                230
-+#define __NR_llistxattr               231
-+#define __NR_flistxattr               232
-+#define __NR_removexattr      233
-+#define __NR_lremovexattr     234
-+#define __NR_fremovexattr     235
- #define __NR_gettid           236
- #define __NR_tkill            237
---- kernel-2.4.20-6chaos_18_7/include/asm-s390x/unistd.h~linux-2.4.20-xattr-0.8.54-chaos       2002-09-25 11:13:45.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/asm-s390x/unistd.h 2003-07-12 15:34:44.000000000 -0600
-@@ -180,9 +180,18 @@
- #define __NR_pivot_root         217
- #define __NR_mincore            218
- #define __NR_madvise            219
--/*
-- * Numbers 224-235 are reserved for posix acl
-- */
-+#define __NR_setxattr         224
-+#define __NR_lsetxattr                225
-+#define __NR_fsetxattr                226
-+#define __NR_getxattr         227
-+#define __NR_lgetxattr                228
-+#define __NR_fgetxattr                229
-+#define __NR_listxattr                230
-+#define __NR_llistxattr               231
-+#define __NR_flistxattr               232
-+#define __NR_removexattr      233
-+#define __NR_lremovexattr     234
-+#define __NR_fremovexattr     235
- #define __NR_gettid           236
- #define __NR_tkill            237
---- kernel-2.4.20-6chaos_18_7/include/asm-sparc/unistd.h~linux-2.4.20-xattr-0.8.54-chaos       2002-09-25 11:13:46.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/asm-sparc/unistd.h 2003-07-12 15:34:44.000000000 -0600
-@@ -184,24 +184,24 @@
- /* #define __NR_exportfs        166    SunOS Specific                              */
- #define __NR_mount              167 /* Common                                      */
- #define __NR_ustat              168 /* Common                                      */
--/* #define __NR_semsys          169    SunOS Specific                              */
--/* #define __NR_msgsys          170    SunOS Specific                              */
--/* #define __NR_shmsys          171    SunOS Specific                              */
--/* #define __NR_auditsys        172    SunOS Specific                              */
--/* #define __NR_rfssys          173    SunOS Specific                              */
-+#define __NR_setxattr           169 /* SunOS: semsys                               */
-+#define __NR_lsetxattr          170 /* SunOS: msgsys                               */
-+#define __NR_fsetxattr          171 /* SunOS: shmsys                               */
-+#define __NR_getxattr           172 /* SunOS: auditsys                             */
-+#define __NR_lgetxattr          173 /* SunOS: rfssys                               */
- #define __NR_getdents           174 /* Common                                      */
- #define __NR_setsid             175 /* Common                                      */
- #define __NR_fchdir             176 /* Common                                      */
--/* #define __NR_fchroot         177    SunOS Specific                              */
--/* #define __NR_vpixsys         178    SunOS Specific                              */
--/* #define __NR_aioread         179    SunOS Specific                              */
--/* #define __NR_aiowrite        180    SunOS Specific                              */
--/* #define __NR_aiowait         181    SunOS Specific                              */
--/* #define __NR_aiocancel       182    SunOS Specific                              */
-+#define __NR_fgetxattr          177 /* SunOS: fchroot                              */
-+#define __NR_listxattr          178 /* SunOS: vpixsys                              */
-+#define __NR_llistxattr         179 /* SunOS: aioread                              */
-+#define __NR_flistxattr         180 /* SunOS: aiowrite                             */
-+#define __NR_removexattr        181 /* SunOS: aiowait                              */
-+#define __NR_lremovexattr       182 /* SunOS: aiocancel                            */
- #define __NR_sigpending         183 /* Common                                      */
- #define __NR_query_module     184 /* Linux Specific                              */
- #define __NR_setpgid            185 /* Common                                      */
--/* #define __NR_pathconf        186    SunOS Specific                              */
-+#define __NR_fremovexattr       186 /* SunOS: pathconf                             */
- #define __NR_tkill              187 /* SunOS: fpathconf                            */
- /* #define __NR_sysconf         188    SunOS Specific                              */
- #define __NR_uname              189 /* Linux Specific                              */
---- kernel-2.4.20-6chaos_18_7/include/asm-sparc64/unistd.h~linux-2.4.20-xattr-0.8.54-chaos     2002-09-25 11:13:48.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/asm-sparc64/unistd.h       2003-07-12 15:34:44.000000000 -0600
-@@ -184,24 +184,24 @@
- /* #define __NR_exportfs        166    SunOS Specific                              */
- #define __NR_mount              167 /* Common                                      */
- #define __NR_ustat              168 /* Common                                      */
--/* #define __NR_semsys          169    SunOS Specific                              */
--/* #define __NR_msgsys          170    SunOS Specific                              */
--/* #define __NR_shmsys          171    SunOS Specific                              */
--/* #define __NR_auditsys        172    SunOS Specific                              */
--/* #define __NR_rfssys          173    SunOS Specific                              */
-+#define __NR_setxattr           169 /* SunOS: semsys                               */
-+#define __NR_lsetxattr          170 /* SunOS: msgsys                               */
-+#define __NR_fsetxattr          171 /* SunOS: shmsys                               */
-+#define __NR_getxattr           172 /* SunOS: auditsys                             */
-+#define __NR_lgetxattr          173 /* SunOS: rfssys                               */
- #define __NR_getdents           174 /* Common                                      */
- #define __NR_setsid             175 /* Common                                      */
- #define __NR_fchdir             176 /* Common                                      */
--/* #define __NR_fchroot         177    SunOS Specific                              */
--/* #define __NR_vpixsys         178    SunOS Specific                              */
--/* #define __NR_aioread         179    SunOS Specific                              */
--/* #define __NR_aiowrite        180    SunOS Specific                              */
--/* #define __NR_aiowait         181    SunOS Specific                              */
--/* #define __NR_aiocancel       182    SunOS Specific                              */
-+#define __NR_fgetxattr          177 /* SunOS: fchroot                              */
-+#define __NR_listxattr          178 /* SunOS: vpixsys                              */
-+#define __NR_llistxattr         179 /* SunOS: aioread                              */
-+#define __NR_flistxattr         180 /* SunOS: aiowrite                             */
-+#define __NR_removexattr        181 /* SunOS: aiowait                              */
-+#define __NR_lremovexattr       182 /* SunOS: aiocancel                            */
- #define __NR_sigpending         183 /* Common                                      */
- #define __NR_query_module     184 /* Linux Specific                              */
- #define __NR_setpgid            185 /* Common                                      */
--/* #define __NR_pathconf        186    SunOS Specific                              */
-+#define __NR_fremovexattr       186 /* SunOS: pathconf                             */
- #define __NR_tkill              187 /* SunOS: fpathconf                            */
- /* #define __NR_sysconf         188    SunOS Specific                              */
- #define __NR_uname              189 /* Linux Specific                              */
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/cache_def.h  2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,15 @@
-+/*
-+ * linux/cache_def.h
-+ * Handling of caches defined in drivers, filesystems, ...
-+ *
-+ * Copyright (C) 2002 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+struct cache_definition {
-+      const char *name;
-+      void (*shrink)(int, unsigned int);
-+      struct list_head link;
-+};
-+
-+extern void register_cache(struct cache_definition *);
-+extern void unregister_cache(struct cache_definition *);
---- kernel-2.4.20-6chaos_18_7/include/linux/errno.h~linux-2.4.20-xattr-0.8.54-chaos    2003-05-15 21:15:06.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/errno.h      2003-07-12 15:34:44.000000000 -0600
-@@ -26,4 +26,8 @@
- #endif
-+/* Defined for extended attributes */
-+#define ENOATTR ENODATA               /* No such attribute */
-+#define ENOTSUP EOPNOTSUPP    /* Operation not supported */
-+
- #endif
---- kernel-2.4.20-6chaos_18_7/include/linux/ext2_fs.h~linux-2.4.20-xattr-0.8.54-chaos  2003-06-24 11:31:16.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/ext2_fs.h    2003-07-12 15:34:44.000000000 -0600
-@@ -57,8 +57,6 @@
-  */
- #define       EXT2_BAD_INO             1      /* Bad blocks inode */
- #define EXT2_ROOT_INO          2      /* Root inode */
--#define EXT2_ACL_IDX_INO       3      /* ACL inode */
--#define EXT2_ACL_DATA_INO      4      /* ACL inode */
- #define EXT2_BOOT_LOADER_INO   5      /* Boot loader inode */
- #define EXT2_UNDEL_DIR_INO     6      /* Undelete directory inode */
-@@ -86,7 +84,6 @@
- #else
- # define EXT2_BLOCK_SIZE(s)           (EXT2_MIN_BLOCK_SIZE << (s)->s_log_block_size)
- #endif
--#define EXT2_ACLE_PER_BLOCK(s)                (EXT2_BLOCK_SIZE(s) / sizeof (struct ext2_acl_entry))
- #define       EXT2_ADDR_PER_BLOCK(s)          (EXT2_BLOCK_SIZE(s) / sizeof (__u32))
- #ifdef __KERNEL__
- # define EXT2_BLOCK_SIZE_BITS(s)      ((s)->s_blocksize_bits)
-@@ -121,28 +118,6 @@
- #endif
- /*
-- * ACL structures
-- */
--struct ext2_acl_header        /* Header of Access Control Lists */
--{
--      __u32   aclh_size;
--      __u32   aclh_file_count;
--      __u32   aclh_acle_count;
--      __u32   aclh_first_acle;
--};
--
--struct ext2_acl_entry /* Access Control List Entry */
--{
--      __u32   acle_size;
--      __u16   acle_perms;     /* Access permissions */
--      __u16   acle_type;      /* Type of entry */
--      __u16   acle_tag;       /* User or group identity */
--      __u16   acle_pad1;
--      __u32   acle_next;      /* Pointer on next entry for the */
--                                      /* same inode or on next free entry */
--};
--
--/*
-  * Structure of a blocks group descriptor
-  */
- struct ext2_group_desc
-@@ -314,6 +289,7 @@ struct ext2_inode {
- #define EXT2_MOUNT_ERRORS_PANIC               0x0040  /* Panic on errors */
- #define EXT2_MOUNT_MINIX_DF           0x0080  /* Mimics the Minix statfs */
- #define EXT2_MOUNT_NO_UID32           0x0200  /* Disable 32-bit UIDs */
-+#define EXT2_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
- #define clear_opt(o, opt)             o &= ~EXT2_MOUNT_##opt
- #define set_opt(o, opt)                       o |= EXT2_MOUNT_##opt
-@@ -397,6 +373,7 @@ struct ext2_super_block {
- #ifdef __KERNEL__
- #define EXT2_SB(sb)   (&((sb)->u.ext2_sb))
-+#define EXT2_I(inode) (&((inode)->u.ext2_i))
- #else
- /* Assume that user mode programs are passing in an ext2fs superblock, not
-  * a kernel struct super_block.  This will allow us to call the feature-test
-@@ -466,7 +443,7 @@ struct ext2_super_block {
- #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008
- #define EXT2_FEATURE_INCOMPAT_ANY             0xffffffff
--#define EXT2_FEATURE_COMPAT_SUPP      0
-+#define EXT2_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
- #define EXT2_FEATURE_INCOMPAT_SUPP    EXT2_FEATURE_INCOMPAT_FILETYPE
- #define EXT2_FEATURE_RO_COMPAT_SUPP   (EXT2_FEATURE_RO_COMPAT_SPARSE_SUPER| \
-                                        EXT2_FEATURE_RO_COMPAT_LARGE_FILE| \
-@@ -624,8 +601,10 @@ extern struct address_space_operations e
- /* namei.c */
- extern struct inode_operations ext2_dir_inode_operations;
-+extern struct inode_operations ext2_special_inode_operations;
- /* symlink.c */
-+extern struct inode_operations ext2_symlink_inode_operations;
- extern struct inode_operations ext2_fast_symlink_inode_operations;
- #endif        /* __KERNEL__ */
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/ext2_xattr.h 2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,157 @@
-+/*
-+  File: linux/ext2_xattr.h
-+
-+  On-disk format of extended attributes for the ext2 filesystem.
-+
-+  (C) 2001 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+#include <linux/config.h>
-+#include <linux/init.h>
-+#include <linux/xattr.h>
-+
-+/* Magic value in attribute blocks */
-+#define EXT2_XATTR_MAGIC              0xEA020000
-+
-+/* Maximum number of references to one attribute block */
-+#define EXT2_XATTR_REFCOUNT_MAX               1024
-+
-+/* Name indexes */
-+#define EXT2_XATTR_INDEX_MAX                  10
-+#define EXT2_XATTR_INDEX_USER                 1
-+#define EXT2_XATTR_INDEX_POSIX_ACL_ACCESS     2
-+#define EXT2_XATTR_INDEX_POSIX_ACL_DEFAULT    3
-+
-+struct ext2_xattr_header {
-+      __u32   h_magic;        /* magic number for identification */
-+      __u32   h_refcount;     /* reference count */
-+      __u32   h_blocks;       /* number of disk blocks used */
-+      __u32   h_hash;         /* hash value of all attributes */
-+      __u32   h_reserved[4];  /* zero right now */
-+};
-+
-+struct ext2_xattr_entry {
-+      __u8    e_name_len;     /* length of name */
-+      __u8    e_name_index;   /* attribute name index */
-+      __u16   e_value_offs;   /* offset in disk block of value */
-+      __u32   e_value_block;  /* disk block attribute is stored on (n/i) */
-+      __u32   e_value_size;   /* size of attribute value */
-+      __u32   e_hash;         /* hash value of name and value */
-+      char    e_name[0];      /* attribute name */
-+};
-+
-+#define EXT2_XATTR_PAD_BITS           2
-+#define EXT2_XATTR_PAD                (1<<EXT2_XATTR_PAD_BITS)
-+#define EXT2_XATTR_ROUND              (EXT2_XATTR_PAD-1)
-+#define EXT2_XATTR_LEN(name_len) \
-+      (((name_len) + EXT2_XATTR_ROUND + \
-+      sizeof(struct ext2_xattr_entry)) & ~EXT2_XATTR_ROUND)
-+#define EXT2_XATTR_NEXT(entry) \
-+      ( (struct ext2_xattr_entry *)( \
-+        (char *)(entry) + EXT2_XATTR_LEN((entry)->e_name_len)) )
-+#define EXT2_XATTR_SIZE(size) \
-+      (((size) + EXT2_XATTR_ROUND) & ~EXT2_XATTR_ROUND)
-+
-+#ifdef __KERNEL__
-+
-+# ifdef CONFIG_EXT2_FS_XATTR
-+
-+struct ext2_xattr_handler {
-+      char *prefix;
-+      size_t (*list)(char *list, struct inode *inode, const char *name,
-+                     int name_len);
-+      int (*get)(struct inode *inode, const char *name, void *buffer,
-+                 size_t size);
-+      int (*set)(struct inode *inode, const char *name, const void *buffer,
-+                 size_t size, int flags);
-+};
-+
-+extern int ext2_xattr_register(int, struct ext2_xattr_handler *);
-+extern void ext2_xattr_unregister(int, struct ext2_xattr_handler *);
-+
-+extern int ext2_setxattr(struct dentry *, const char *, const void *, size_t, int);
-+extern ssize_t ext2_getxattr(struct dentry *, const char *, void *, size_t);
-+extern ssize_t ext2_listxattr(struct dentry *, char *, size_t);
-+extern int ext2_removexattr(struct dentry *, const char *);
-+
-+extern int ext2_xattr_get(struct inode *, int, const char *, void *, size_t);
-+extern int ext2_xattr_list(struct inode *, char *, size_t);
-+extern int ext2_xattr_set(struct inode *, int, const char *, const void *, size_t, int);
-+
-+extern void ext2_xattr_delete_inode(struct inode *);
-+extern void ext2_xattr_put_super(struct super_block *);
-+
-+extern int init_ext2_xattr(void) __init;
-+extern void exit_ext2_xattr(void);
-+
-+# else  /* CONFIG_EXT2_FS_XATTR */
-+#  define ext2_setxattr               NULL
-+#  define ext2_getxattr               NULL
-+#  define ext2_listxattr      NULL
-+#  define ext2_removexattr    NULL
-+
-+static inline int
-+ext2_xattr_get(struct inode *inode, int name_index,
-+             const char *name, void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext2_xattr_list(struct inode *inode, char *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext2_xattr_set(struct inode *inode, int name_index, const char *name,
-+             const void *value, size_t size, int flags)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline void
-+ext2_xattr_delete_inode(struct inode *inode)
-+{
-+}
-+
-+static inline void
-+ext2_xattr_put_super(struct super_block *sb)
-+{
-+}
-+
-+static inline int
-+init_ext2_xattr(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext2_xattr(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT2_FS_XATTR */
-+
-+# ifdef CONFIG_EXT2_FS_XATTR_USER
-+
-+extern int init_ext2_xattr_user(void) __init;
-+extern void exit_ext2_xattr_user(void);
-+
-+# else  /* CONFIG_EXT2_FS_XATTR_USER */
-+
-+static inline int
-+init_ext2_xattr_user(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext2_xattr_user(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT2_FS_XATTR_USER */
-+
-+#endif  /* __KERNEL__ */
-+
---- kernel-2.4.20-6chaos_18_7/include/linux/ext3_fs.h~linux-2.4.20-xattr-0.8.54-chaos  2003-07-12 15:33:41.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/ext3_fs.h    2003-07-12 15:34:44.000000000 -0600
-@@ -63,8 +63,6 @@
-  */
- #define       EXT3_BAD_INO             1      /* Bad blocks inode */
- #define EXT3_ROOT_INO          2      /* Root inode */
--#define EXT3_ACL_IDX_INO       3      /* ACL inode */
--#define EXT3_ACL_DATA_INO      4      /* ACL inode */
- #define EXT3_BOOT_LOADER_INO   5      /* Boot loader inode */
- #define EXT3_UNDEL_DIR_INO     6      /* Undelete directory inode */
- #define EXT3_RESIZE_INO                7      /* Reserved group descriptors inode */
-@@ -94,7 +92,6 @@
- #else
- # define EXT3_BLOCK_SIZE(s)           (EXT3_MIN_BLOCK_SIZE << (s)->s_log_block_size)
- #endif
--#define EXT3_ACLE_PER_BLOCK(s)                (EXT3_BLOCK_SIZE(s) / sizeof (struct ext3_acl_entry))
- #define       EXT3_ADDR_PER_BLOCK(s)          (EXT3_BLOCK_SIZE(s) / sizeof (__u32))
- #ifdef __KERNEL__
- # define EXT3_BLOCK_SIZE_BITS(s)      ((s)->s_blocksize_bits)
-@@ -129,28 +126,6 @@
- #endif
- /*
-- * ACL structures
-- */
--struct ext3_acl_header        /* Header of Access Control Lists */
--{
--      __u32   aclh_size;
--      __u32   aclh_file_count;
--      __u32   aclh_acle_count;
--      __u32   aclh_first_acle;
--};
--
--struct ext3_acl_entry /* Access Control List Entry */
--{
--      __u32   acle_size;
--      __u16   acle_perms;     /* Access permissions */
--      __u16   acle_type;      /* Type of entry */
--      __u16   acle_tag;       /* User or group identity */
--      __u16   acle_pad1;
--      __u32   acle_next;      /* Pointer on next entry for the */
--                                      /* same inode or on next free entry */
--};
--
--/*
-  * Structure of a blocks group descriptor
-  */
- struct ext3_group_desc
-@@ -344,6 +319,7 @@ struct ext3_inode {
-   #define EXT3_MOUNT_WRITEBACK_DATA   0x0C00  /* No data ordering */
- #define EXT3_MOUNT_UPDATE_JOURNAL     0x1000  /* Update the journal format */
- #define EXT3_MOUNT_NO_UID32           0x2000  /* Disable 32-bit UIDs */
-+#define EXT3_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
- /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
- #ifndef _LINUX_EXT2_FS_H
-@@ -521,7 +497,7 @@ struct ext3_super_block {
- #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
- #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
--#define EXT3_FEATURE_COMPAT_SUPP      0
-+#define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
- #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
-                                        EXT3_FEATURE_INCOMPAT_RECOVER)
- #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
-@@ -704,6 +680,7 @@ extern void ext3_check_inodes_bitmap (st
- extern unsigned long ext3_count_free (struct buffer_head *, unsigned);
- /* inode.c */
-+extern int ext3_forget(handle_t *, int, struct inode *, struct buffer_head *, int);
- extern struct buffer_head * ext3_getblk (handle_t *, struct inode *, long, int, int *);
- extern struct buffer_head * ext3_bread (handle_t *, struct inode *, int, int, int *);
-@@ -773,8 +750,10 @@ extern struct address_space_operations e
- /* namei.c */
- extern struct inode_operations ext3_dir_inode_operations;
-+extern struct inode_operations ext3_special_inode_operations;
- /* symlink.c */
-+extern struct inode_operations ext3_symlink_inode_operations;
- extern struct inode_operations ext3_fast_symlink_inode_operations;
---- kernel-2.4.20-6chaos_18_7/include/linux/ext3_jbd.h~linux-2.4.20-xattr-0.8.54-chaos 2003-07-12 15:33:38.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/ext3_jbd.h   2003-07-12 15:34:44.000000000 -0600
-@@ -30,13 +30,19 @@
- #define EXT3_SINGLEDATA_TRANS_BLOCKS  8U
-+/* Extended attributes may touch two data buffers, two bitmap buffers,
-+ * and two group and summaries. */
-+
-+#define EXT3_XATTR_TRANS_BLOCKS               8
-+
- /* Define the minimum size for a transaction which modifies data.  This
-  * needs to take into account the fact that we may end up modifying two
-  * quota files too (one for the group, one for the user quota).  The
-  * superblock only gets updated once, of course, so don't bother
-  * counting that again for the quota updates. */
--#define EXT3_DATA_TRANS_BLOCKS                (3 * EXT3_SINGLEDATA_TRANS_BLOCKS - 2)
-+#define EXT3_DATA_TRANS_BLOCKS                (3 * EXT3_SINGLEDATA_TRANS_BLOCKS + \
-+                                       EXT3_XATTR_TRANS_BLOCKS - 2)
- extern int ext3_writepage_trans_blocks(struct inode *inode);
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/ext3_xattr.h 2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,157 @@
-+/*
-+  File: linux/ext3_xattr.h
-+
-+  On-disk format of extended attributes for the ext3 filesystem.
-+
-+  (C) 2001 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+#include <linux/config.h>
-+#include <linux/init.h>
-+#include <linux/xattr.h>
-+
-+/* Magic value in attribute blocks */
-+#define EXT3_XATTR_MAGIC              0xEA020000
-+
-+/* Maximum number of references to one attribute block */
-+#define EXT3_XATTR_REFCOUNT_MAX               1024
-+
-+/* Name indexes */
-+#define EXT3_XATTR_INDEX_MAX                  10
-+#define EXT3_XATTR_INDEX_USER                 1
-+#define EXT3_XATTR_INDEX_POSIX_ACL_ACCESS     2
-+#define EXT3_XATTR_INDEX_POSIX_ACL_DEFAULT    3
-+
-+struct ext3_xattr_header {
-+      __u32   h_magic;        /* magic number for identification */
-+      __u32   h_refcount;     /* reference count */
-+      __u32   h_blocks;       /* number of disk blocks used */
-+      __u32   h_hash;         /* hash value of all attributes */
-+      __u32   h_reserved[4];  /* zero right now */
-+};
-+
-+struct ext3_xattr_entry {
-+      __u8    e_name_len;     /* length of name */
-+      __u8    e_name_index;   /* attribute name index */
-+      __u16   e_value_offs;   /* offset in disk block of value */
-+      __u32   e_value_block;  /* disk block attribute is stored on (n/i) */
-+      __u32   e_value_size;   /* size of attribute value */
-+      __u32   e_hash;         /* hash value of name and value */
-+      char    e_name[0];      /* attribute name */
-+};
-+
-+#define EXT3_XATTR_PAD_BITS           2
-+#define EXT3_XATTR_PAD                (1<<EXT3_XATTR_PAD_BITS)
-+#define EXT3_XATTR_ROUND              (EXT3_XATTR_PAD-1)
-+#define EXT3_XATTR_LEN(name_len) \
-+      (((name_len) + EXT3_XATTR_ROUND + \
-+      sizeof(struct ext3_xattr_entry)) & ~EXT3_XATTR_ROUND)
-+#define EXT3_XATTR_NEXT(entry) \
-+      ( (struct ext3_xattr_entry *)( \
-+        (char *)(entry) + EXT3_XATTR_LEN((entry)->e_name_len)) )
-+#define EXT3_XATTR_SIZE(size) \
-+      (((size) + EXT3_XATTR_ROUND) & ~EXT3_XATTR_ROUND)
-+
-+#ifdef __KERNEL__
-+
-+# ifdef CONFIG_EXT3_FS_XATTR
-+
-+struct ext3_xattr_handler {
-+      char *prefix;
-+      size_t (*list)(char *list, struct inode *inode, const char *name,
-+                     int name_len);
-+      int (*get)(struct inode *inode, const char *name, void *buffer,
-+                 size_t size);
-+      int (*set)(struct inode *inode, const char *name, const void *buffer,
-+                 size_t size, int flags);
-+};
-+
-+extern int ext3_xattr_register(int, struct ext3_xattr_handler *);
-+extern void ext3_xattr_unregister(int, struct ext3_xattr_handler *);
-+
-+extern int ext3_setxattr(struct dentry *, const char *, const void *, size_t, int);
-+extern ssize_t ext3_getxattr(struct dentry *, const char *, void *, size_t);
-+extern ssize_t ext3_listxattr(struct dentry *, char *, size_t);
-+extern int ext3_removexattr(struct dentry *, const char *);
-+
-+extern int ext3_xattr_get(struct inode *, int, const char *, void *, size_t);
-+extern int ext3_xattr_list(struct inode *, char *, size_t);
-+extern int ext3_xattr_set(handle_t *handle, struct inode *, int, const char *, const void *, size_t, int);
-+
-+extern void ext3_xattr_delete_inode(handle_t *, struct inode *);
-+extern void ext3_xattr_put_super(struct super_block *);
-+
-+extern int init_ext3_xattr(void) __init;
-+extern void exit_ext3_xattr(void);
-+
-+# else  /* CONFIG_EXT3_FS_XATTR */
-+#  define ext3_setxattr               NULL
-+#  define ext3_getxattr               NULL
-+#  define ext3_listxattr      NULL
-+#  define ext3_removexattr    NULL
-+
-+static inline int
-+ext3_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext3_xattr_list(struct inode *inode, void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext3_xattr_set(handle_t *handle, struct inode *inode, int name_index,
-+             const char *name, const void *value, size_t size, int flags)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline void
-+ext3_xattr_delete_inode(handle_t *handle, struct inode *inode)
-+{
-+}
-+
-+static inline void
-+ext3_xattr_put_super(struct super_block *sb)
-+{
-+}
-+
-+static inline int
-+init_ext3_xattr(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext3_xattr(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT3_FS_XATTR */
-+
-+# ifdef CONFIG_EXT3_FS_XATTR_USER
-+
-+extern int init_ext3_xattr_user(void) __init;
-+extern void exit_ext3_xattr_user(void);
-+
-+# else  /* CONFIG_EXT3_FS_XATTR_USER */
-+
-+static inline int
-+init_ext3_xattr_user(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext3_xattr_user(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT3_FS_XATTR_USER */
-+
-+#endif  /* __KERNEL__ */
-+
---- kernel-2.4.20-6chaos_18_7/include/linux/fs.h~linux-2.4.20-xattr-0.8.54-chaos       2003-07-12 15:31:35.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/fs.h 2003-07-12 15:34:44.000000000 -0600
-@@ -914,7 +914,7 @@ struct inode_operations {
-       int (*setattr) (struct dentry *, struct iattr *);
-       int (*setattr_raw) (struct inode *, struct iattr *);
-       int (*getattr) (struct dentry *, struct iattr *);
--      int (*setxattr) (struct dentry *, const char *, void *, size_t, int);
-+      int (*setxattr) (struct dentry *, const char *, const void *, size_t, int);
-       ssize_t (*getxattr) (struct dentry *, const char *, void *, size_t);
-       ssize_t (*listxattr) (struct dentry *, char *, size_t);
-       int (*removexattr) (struct dentry *, const char *);
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/include/linux/mbcache.h    2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,69 @@
-+/*
-+  File: linux/mbcache.h
-+
-+  (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+/* Hardwire the number of additional indexes */
-+#define MB_CACHE_INDEXES_COUNT 1
-+
-+struct mb_cache_entry;
-+
-+struct mb_cache_op {
-+      int (*free)(struct mb_cache_entry *, int);
-+};
-+
-+struct mb_cache {
-+      struct list_head                c_cache_list;
-+      const char                      *c_name;
-+      struct mb_cache_op              c_op;
-+      atomic_t                        c_entry_count;
-+      int                             c_bucket_count;
-+#ifndef MB_CACHE_INDEXES_COUNT
-+      int                             c_indexes_count;
-+#endif
-+      kmem_cache_t                    *c_entry_cache;
-+      struct list_head                *c_block_hash;
-+      struct list_head                *c_indexes_hash[0];
-+};
-+
-+struct mb_cache_entry_index {
-+      struct list_head                o_list;
-+      unsigned int                    o_key;
-+};
-+
-+struct mb_cache_entry {
-+      struct list_head                e_lru_list;
-+      struct mb_cache                 *e_cache;
-+      atomic_t                        e_used;
-+      kdev_t                          e_dev;
-+      unsigned long                   e_block;
-+      struct list_head                e_block_list;
-+      struct mb_cache_entry_index     e_indexes[0];
-+};
-+
-+/* Functions on caches */
-+
-+struct mb_cache * mb_cache_create(const char *, struct mb_cache_op *, size_t,
-+                                int, int);
-+void mb_cache_shrink(struct mb_cache *, kdev_t);
-+void mb_cache_destroy(struct mb_cache *);
-+
-+/* Functions on cache entries */
-+
-+struct mb_cache_entry *mb_cache_entry_alloc(struct mb_cache *);
-+int mb_cache_entry_insert(struct mb_cache_entry *, kdev_t, unsigned long,
-+                        unsigned int[]);
-+void mb_cache_entry_rehash(struct mb_cache_entry *, unsigned int[]);
-+void mb_cache_entry_release(struct mb_cache_entry *);
-+void mb_cache_entry_takeout(struct mb_cache_entry *);
-+void mb_cache_entry_free(struct mb_cache_entry *);
-+struct mb_cache_entry *mb_cache_entry_dup(struct mb_cache_entry *);
-+struct mb_cache_entry *mb_cache_entry_get(struct mb_cache *, kdev_t,
-+                                        unsigned long);
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+struct mb_cache_entry *mb_cache_entry_find_first(struct mb_cache *cache, int,
-+                                               kdev_t, unsigned int);
-+struct mb_cache_entry *mb_cache_entry_find_next(struct mb_cache_entry *, int,
-+                                              kdev_t, unsigned int);
-+#endif
---- kernel-2.4.20-6chaos_18_7/kernel/ksyms.c~linux-2.4.20-xattr-0.8.54-chaos   2003-07-12 15:14:02.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/kernel/ksyms.c     2003-07-12 15:35:19.000000000 -0600
-@@ -12,6 +12,7 @@
- #define __KERNEL_SYSCALLS__
- #include <linux/config.h>
- #include <linux/slab.h>
-+#include <linux/cache_def.h>
- #include <linux/smp.h>
- #include <linux/module.h>
- #include <linux/blkdev.h>
-@@ -106,6 +107,7 @@ EXPORT_SYMBOL(do_brk);
- EXPORT_SYMBOL(exit_mm);
- EXPORT_SYMBOL(exit_files);
- EXPORT_SYMBOL(exit_fs);
-+EXPORT_SYMBOL(copy_fs_struct);
- EXPORT_SYMBOL(exit_sighand);
- EXPORT_SYMBOL_GPL(make_pages_present);
-@@ -126,6 +128,8 @@ EXPORT_SYMBOL(kmem_cache_alloc);
- EXPORT_SYMBOL(kmem_cache_free);
- EXPORT_SYMBOL(kmem_cache_validate);
- EXPORT_SYMBOL(kmem_cache_size);
-+EXPORT_SYMBOL(register_cache);
-+EXPORT_SYMBOL(unregister_cache);
- EXPORT_SYMBOL(kmalloc);
- EXPORT_SYMBOL(kfree);
- EXPORT_SYMBOL(vfree);
---- kernel-2.4.20-6chaos_18_7/mm/vmscan.c~linux-2.4.20-xattr-0.8.54-chaos      2003-07-12 15:33:34.000000000 -0600
-+++ kernel-2.4.20-6chaos_18_7-braam/mm/vmscan.c        2003-07-12 15:34:44.000000000 -0600
-@@ -21,6 +21,7 @@
- #include <linux/kernel_stat.h>
- #include <linux/swap.h>
- #include <linux/swapctl.h>
-+#include <linux/cache_def.h>
- #include <linux/smp_lock.h>
- #include <linux/pagemap.h>
- #include <linux/init.h>
-@@ -444,6 +445,39 @@ static inline void kachunk_cache(struct 
- #define BATCH_WORK_AMOUNT     64
-+static DECLARE_MUTEX(other_caches_sem);
-+static LIST_HEAD(cache_definitions);
-+
-+void register_cache(struct cache_definition *cache)
-+{
-+      down(&other_caches_sem);
-+      list_add(&cache->link, &cache_definitions);
-+      up(&other_caches_sem);
-+}
-+
-+void unregister_cache(struct cache_definition *cache)
-+{
-+      down(&other_caches_sem);
-+      list_del(&cache->link);
-+      up(&other_caches_sem);
-+}
-+
-+static void shrink_other_caches(unsigned int priority, int gfp_mask)
-+{
-+      struct list_head *p;
-+
-+      if (down_trylock(&other_caches_sem))
-+              return;
-+
-+      list_for_each_prev(p, &cache_definitions) {
-+              struct cache_definition *cache =
-+                      list_entry(p, struct cache_definition, link);
-+
-+              cache->shrink(priority, gfp_mask);
-+      }
-+      up(&other_caches_sem);
-+}
-+
- /*
-  * returns the active cache ratio relative to the total active list
-  * times 10 (eg. 30% cache returns 3)
-@@ -887,7 +921,7 @@ static int do_try_to_free_pages_kswapd(u
-       ret += shrink_dcache_memory(DEF_PRIORITY, gfp_mask);
-       ret += shrink_icache_memory(DEF_PRIORITY, gfp_mask);
--      // ret += shrink_other_caches(DEF_PRIORITY, gfp_mask); 
-+      shrink_other_caches(DEF_PRIORITY, gfp_mask); 
- #ifdef CONFIG_QUOTA
-       ret += shrink_dqcache_memory(DEF_PRIORITY, gfp_mask);
- #endif
---- /dev/null  2003-01-30 03:24:37.000000000 -0700
-+++ kernel-2.4.20-6chaos_18_7-braam/fs/ext3/ext3-exports.c     2003-07-12 15:34:44.000000000 -0600
-@@ -0,0 +1,13 @@
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
-+
-+EXPORT_SYMBOL(ext3_force_commit);
-+EXPORT_SYMBOL(ext3_bread);
-+EXPORT_SYMBOL(ext3_xattr_register);
-+EXPORT_SYMBOL(ext3_xattr_unregister);
-+EXPORT_SYMBOL(ext3_xattr_get);
-+EXPORT_SYMBOL(ext3_xattr_list);
-+EXPORT_SYMBOL(ext3_xattr_set);
-
-_
diff --git a/lustre/kernel_patches/patches/linux-2.4.21-xattr-0.8.54-suse.patch b/lustre/kernel_patches/patches/linux-2.4.21-xattr-0.8.54-suse.patch
deleted file mode 100644 (file)
index 9208772..0000000
+++ /dev/null
@@ -1,5349 +0,0 @@
- Documentation/Configure.help  |   66 ++
- arch/alpha/defconfig          |    7 
- arch/alpha/kernel/entry.S     |   12 
- arch/arm/defconfig            |    7 
- arch/arm/kernel/calls.S       |   24 
- arch/i386/defconfig           |    7 
- arch/ia64/defconfig           |    7 
- arch/ia64/kernel/entry.S      |   24 
- arch/m68k/defconfig           |    7 
- arch/mips/defconfig           |    7 
- arch/mips64/defconfig         |    7 
- arch/ppc/defconfig            |   14 
- arch/ppc64/kernel/misc.S      |    2 
- arch/s390/defconfig           |    7 
- arch/s390/kernel/entry.S      |   24 
- arch/s390x/defconfig          |    7 
- arch/s390x/kernel/entry.S     |   24 
- arch/s390x/kernel/wrapper32.S |   92 +++
- arch/sparc/defconfig          |    7 
- arch/sparc/kernel/systbls.S   |   10 
- arch/sparc64/defconfig        |    7 
- arch/sparc64/kernel/systbls.S |   20 
- fs/Config.in                  |   14 
- fs/Makefile                   |    3 
- fs/ext2/Makefile              |    4 
- fs/ext2/file.c                |    5 
- fs/ext2/ialloc.c              |    2 
- fs/ext2/inode.c               |   34 -
- fs/ext2/namei.c               |   14 
- fs/ext2/super.c               |   29 
- fs/ext2/symlink.c             |   14 
- fs/ext2/xattr.c               | 1212 +++++++++++++++++++++++++++++++++++++++++
- fs/ext2/xattr_user.c          |  103 +++
- fs/ext3/Makefile              |   10 
- fs/ext3/file.c                |    5 
- fs/ext3/ialloc.c              |    2 
- fs/ext3/inode.c               |   35 -
- fs/ext3/namei.c               |   21 
- fs/ext3/super.c               |   36 +
- fs/ext3/symlink.c             |   14 
- fs/ext3/xattr.c               | 1225 ++++++++++++++++++++++++++++++++++++++++++
- fs/ext3/xattr_user.c          |  111 +++
- fs/jfs/jfs_xattr.h            |    6 
- fs/jfs/xattr.c                |    6 
- fs/mbcache.c                  |  648 ++++++++++++++++++++++
- include/asm-arm/unistd.h      |    2 
- include/asm-ia64/unistd.h     |   13 
- include/asm-ppc64/unistd.h    |    2 
- include/asm-s390/unistd.h     |   15 
- include/asm-s390x/unistd.h    |   15 
- include/asm-sparc/unistd.h    |   24 
- include/asm-sparc64/unistd.h  |   24 
- include/linux/cache_def.h     |   15 
- include/linux/errno.h         |    4 
- include/linux/ext2_fs.h       |   31 -
- include/linux/ext2_xattr.h    |  157 +++++
- include/linux/ext3_fs.h       |   31 -
- include/linux/ext3_jbd.h      |    8 
- include/linux/ext3_xattr.h    |  157 +++++
- include/linux/fs.h            |    2 
- include/linux/mbcache.h       |   69 ++
- kernel/ksyms.c                |    4 
- mm/vmscan.c                   |   35 +
- fs/ext3/ext3-exports.c        |   14 +  
- 64 files changed, 4355 insertions(+), 195 deletions(-)
-
---- linux-2.4.20/Documentation/Configure.help~linux-2.4.20-xattr-0.8.54        2003-05-05 17:43:06.000000000 +0800
-+++ linux-2.4.20-root/Documentation/Configure.help     2003-05-07 18:08:03.000000000 +0800
-@@ -15242,6 +15242,39 @@ CONFIG_EXT2_FS
-   be compiled as a module, and so this could be dangerous.  Most
-   everyone wants to say Y here.
-+Ext2 extended attributes
-+CONFIG_EXT2_FS_XATTR
-+  Extended attributes are name:value pairs associated with inodes by
-+  the kernel or by users (see the attr(5) manual page, or visit
-+  <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext2 extended attribute block sharing
-+CONFIG_EXT2_FS_XATTR_SHARING
-+  This options enables code for sharing identical extended attribute
-+  blocks among multiple inodes.
-+
-+  Usually, say Y.
-+
-+Ext2 extended user attributes
-+CONFIG_EXT2_FS_XATTR_USER
-+  This option enables extended user attributes on ext2. Processes can
-+  associate extended user attributes with inodes to store additional
-+  information such as the character encoding of files, etc. (see the
-+  attr(5) manual page, or visit <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext2 trusted extended attributes
-+CONFIG_EXT2_FS_XATTR_TRUSTED
-+  This option enables extended attributes on ext2 that are accessible
-+  (and visible) only to users capable of CAP_SYS_ADMIN. Usually this
-+  is only the super user. Trusted extended attributes are meant for
-+  implementing system/security services.
-+
-+  If unsure, say N.
-+
- Ext3 journalling file system support (EXPERIMENTAL)
- CONFIG_EXT3_FS
-   This is the journalling version of the Second extended file system
-@@ -15274,6 +15307,39 @@ CONFIG_EXT3_FS
-   of your root partition (the one containing the directory /) cannot
-   be compiled as a module, and so this may be dangerous.
-+Ext3 extended attributes
-+CONFIG_EXT3_FS_XATTR
-+  Extended attributes are name:value pairs associated with inodes by
-+  the kernel or by users (see the attr(5) manual page, or visit
-+  <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext3 extended attribute block sharing
-+CONFIG_EXT3_FS_XATTR_SHARING
-+  This options enables code for sharing identical extended attribute
-+  blocks among multiple inodes.
-+
-+  Usually, say Y.
-+
-+Ext3 extended user attributes
-+CONFIG_EXT3_FS_XATTR_USER
-+  This option enables extended user attributes on ext3. Processes can
-+  associate extended user attributes with inodes to store additional
-+  information such as the character encoding of files, etc. (see the
-+  attr(5) manual page, or visit <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext3 trusted extended attributes
-+CONFIG_EXT3_FS_XATTR_TRUSTED
-+  This option enables extended attributes on ext3 that are accessible
-+  (and visible) only to users capable of CAP_SYS_ADMIN. Usually this
-+  is only the super user. Trusted extended attributes are meant for
-+  implementing system/security services.
-+
-+  If unsure, say N.
-+
- Journal Block Device support (JBD for ext3) (EXPERIMENTAL)
- CONFIG_JBD
-   This is a generic journalling layer for block devices.  It is
---- linux-2.4.20/arch/alpha/defconfig~linux-2.4.20-xattr-0.8.54        2001-11-20 07:19:42.000000000 +0800
-+++ linux-2.4.20-root/arch/alpha/defconfig     2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_ALPHA=y
- # CONFIG_UID16 is not set
- # CONFIG_RWSEM_GENERIC_SPINLOCK is not set
---- linux-2.4.20/arch/alpha/kernel/entry.S~linux-2.4.20-xattr-0.8.54   2002-08-03 08:39:42.000000000 +0800
-+++ linux-2.4.20-root/arch/alpha/kernel/entry.S        2003-05-07 18:08:03.000000000 +0800
-@@ -1154,6 +1154,18 @@ sys_call_table:
-       .quad sys_readahead
-       .quad sys_ni_syscall                    /* 380, sys_security */
-       .quad sys_tkill
-+      .quad sys_setxattr
-+      .quad sys_lsetxattr
-+      .quad sys_fsetxattr
-+      .quad sys_getxattr                      /* 385 */
-+      .quad sys_lgetxattr
-+      .quad sys_fgetxattr
-+      .quad sys_listxattr
-+      .quad sys_llistxattr
-+      .quad sys_flistxattr                    /* 390 */
-+      .quad sys_removexattr
-+      .quad sys_lremovexattr
-+      .quad sys_fremovexattr
- /* Remember to update everything, kids.  */
- .ifne (. - sys_call_table) - (NR_SYSCALLS * 8)
---- linux-2.4.20/arch/arm/defconfig~linux-2.4.20-xattr-0.8.54  2001-05-20 08:43:05.000000000 +0800
-+++ linux-2.4.20-root/arch/arm/defconfig       2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_ARM=y
- # CONFIG_EISA is not set
- # CONFIG_SBUS is not set
---- linux-2.4.20/arch/arm/kernel/calls.S~linux-2.4.20-xattr-0.8.54     2002-08-03 08:39:42.000000000 +0800
-+++ linux-2.4.20-root/arch/arm/kernel/calls.S  2003-05-07 18:08:03.000000000 +0800
-@@ -240,18 +240,18 @@ __syscall_start:
-               .long   SYMBOL_NAME(sys_ni_syscall) /* Security */
-               .long   SYMBOL_NAME(sys_gettid)
- /* 225 */     .long   SYMBOL_NAME(sys_readahead)
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_setxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_lsetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_fsetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_getxattr */
--/* 230 */     .long   SYMBOL_NAME(sys_ni_syscall) /* sys_lgetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_fgetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_listxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_llistxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_flistxattr */
--/* 235 */     .long   SYMBOL_NAME(sys_ni_syscall) /* sys_removexattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_lremovexattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* sys_fremovexattr */
-+              .long   SYMBOL_NAME(sys_setxattr)
-+              .long   SYMBOL_NAME(sys_lsetxattr)
-+              .long   SYMBOL_NAME(sys_fsetxattr)
-+              .long   SYMBOL_NAME(sys_getxattr)
-+/* 230 */     .long   SYMBOL_NAME(sys_lgetxattr)
-+              .long   SYMBOL_NAME(sys_fgetxattr)
-+              .long   SYMBOL_NAME(sys_listxattr)
-+              .long   SYMBOL_NAME(sys_llistxattr)
-+              .long   SYMBOL_NAME(sys_flistxattr)
-+/* 235 */     .long   SYMBOL_NAME(sys_removexattr)
-+              .long   SYMBOL_NAME(sys_lremovexattr)
-+              .long   SYMBOL_NAME(sys_fremovexattr)
-               .long   SYMBOL_NAME(sys_tkill)
-               /*
-                * Please check 2.5 _before_ adding calls here,
---- linux-2.4.20/arch/i386/defconfig~linux-2.4.20-xattr-0.8.54 2002-11-29 07:53:09.000000000 +0800
-+++ linux-2.4.20-root/arch/i386/defconfig      2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_X86=y
- CONFIG_ISA=y
- # CONFIG_SBUS is not set
---- linux-2.4.20/arch/ia64/defconfig~linux-2.4.20-xattr-0.8.54 2002-11-29 07:53:09.000000000 +0800
-+++ linux-2.4.20-root/arch/ia64/defconfig      2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- #
- # Code maturity level options
---- linux-2.4.20/arch/m68k/defconfig~linux-2.4.20-xattr-0.8.54 2000-06-20 03:56:08.000000000 +0800
-+++ linux-2.4.20-root/arch/m68k/defconfig      2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_UID16=y
- #
---- linux-2.4.20/arch/mips/defconfig~linux-2.4.20-xattr-0.8.54 2002-11-29 07:53:10.000000000 +0800
-+++ linux-2.4.20-root/arch/mips/defconfig      2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_MIPS=y
- CONFIG_MIPS32=y
- # CONFIG_MIPS64 is not set
---- linux-2.4.20/arch/mips64/defconfig~linux-2.4.20-xattr-0.8.54       2002-11-29 07:53:10.000000000 +0800
-+++ linux-2.4.20-root/arch/mips64/defconfig    2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_MIPS=y
- # CONFIG_MIPS32 is not set
- CONFIG_MIPS64=y
---- linux-2.4.20/arch/s390/defconfig~linux-2.4.20-xattr-0.8.54 2002-11-29 07:53:11.000000000 +0800
-+++ linux-2.4.20-root/arch/s390/defconfig      2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_ISA is not set
- # CONFIG_EISA is not set
- # CONFIG_MCA is not set
---- linux-2.4.20/arch/s390/kernel/entry.S~linux-2.4.20-xattr-0.8.54    2002-11-29 07:53:11.000000000 +0800
-+++ linux-2.4.20-root/arch/s390/kernel/entry.S 2003-05-07 18:08:03.000000000 +0800
-@@ -558,18 +558,18 @@ sys_call_table:
-         .long  sys_fcntl64 
-       .long  sys_ni_syscall
-       .long  sys_ni_syscall
--      .long  sys_ni_syscall            /* 224 - reserved for setxattr  */
--      .long  sys_ni_syscall            /* 225 - reserved for lsetxattr */
--      .long  sys_ni_syscall            /* 226 - reserved for fsetxattr */
--      .long  sys_ni_syscall            /* 227 - reserved for getxattr  */
--      .long  sys_ni_syscall            /* 228 - reserved for lgetxattr */
--      .long  sys_ni_syscall            /* 229 - reserved for fgetxattr */
--      .long  sys_ni_syscall            /* 230 - reserved for listxattr */
--      .long  sys_ni_syscall            /* 231 - reserved for llistxattr */
--      .long  sys_ni_syscall            /* 232 - reserved for flistxattr */
--      .long  sys_ni_syscall            /* 233 - reserved for removexattr */
--      .long  sys_ni_syscall            /* 234 - reserved for lremovexattr */
--      .long  sys_ni_syscall            /* 235 - reserved for fremovexattr */
-+      .long  sys_setxattr
-+      .long  sys_lsetxattr            /* 225 */
-+      .long  sys_fsetxattr
-+      .long  sys_getxattr
-+      .long  sys_lgetxattr
-+      .long  sys_fgetxattr
-+      .long  sys_listxattr            /* 230 */
-+      .long  sys_llistxattr
-+      .long  sys_flistxattr
-+      .long  sys_removexattr
-+      .long  sys_lremovexattr
-+      .long  sys_fremovexattr         /* 235 */
-       .long  sys_gettid
-       .long  sys_tkill
-       .rept  255-237
---- linux-2.4.20/arch/s390x/defconfig~linux-2.4.20-xattr-0.8.54        2002-11-29 07:53:11.000000000 +0800
-+++ linux-2.4.20-root/arch/s390x/defconfig     2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_ISA is not set
- # CONFIG_EISA is not set
- # CONFIG_MCA is not set
---- linux-2.4.20/arch/s390x/kernel/entry.S~linux-2.4.20-xattr-0.8.54   2002-11-29 07:53:11.000000000 +0800
-+++ linux-2.4.20-root/arch/s390x/kernel/entry.S        2003-05-07 18:08:03.000000000 +0800
-@@ -591,18 +591,18 @@ sys_call_table:
-       .long  SYSCALL(sys_ni_syscall,sys32_fcntl64_wrapper)
-       .long  SYSCALL(sys_ni_syscall,sys_ni_syscall)
-       .long  SYSCALL(sys_ni_syscall,sys_ni_syscall)
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 224 - reserved for setxattr  */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 225 - reserved for lsetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 226 - reserved for fsetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 227 - reserved for getxattr  */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 228 - reserved for lgetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 229 - reserved for fgetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 230 - reserved for listxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 231 - reserved for llistxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 232 - reserved for flistxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 233 - reserved for removexattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 234 - reserved for lremovexattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 235 - reserved for fremovexattr */
-+      .long  SYSCALL(sys_setxattr,sys32_setxattr_wrapper)
-+      .long  SYSCALL(sys_lsetxattr,sys32_lsetxattr_wrapper)   /* 225 */
-+      .long  SYSCALL(sys_fsetxattr,sys32_fsetxattr_wrapper)
-+      .long  SYSCALL(sys_getxattr,sys32_getxattr_wrapper)
-+      .long  SYSCALL(sys_lgetxattr,sys32_lgetxattr_wrapper)
-+      .long  SYSCALL(sys_fgetxattr,sys32_fgetxattr_wrapper)
-+      .long  SYSCALL(sys_listxattr,sys32_listxattr_wrapper)   /* 230 */
-+      .long  SYSCALL(sys_llistxattr,sys32_llistxattr_wrapper)
-+      .long  SYSCALL(sys_flistxattr,sys32_flistxattr_wrapper)
-+      .long  SYSCALL(sys_removexattr,sys32_removexattr_wrapper)
-+      .long  SYSCALL(sys_lremovexattr,sys32_lremovexattr_wrapper)
-+      .long  SYSCALL(sys_fremovexattr,sys32_fremovexattr_wrapper)/* 235 */
-       .long  SYSCALL(sys_gettid,sys_gettid)
-       .long  SYSCALL(sys_tkill,sys_tkill)
-       .rept  255-237
---- linux-2.4.20/arch/s390x/kernel/wrapper32.S~linux-2.4.20-xattr-0.8.54       2002-02-26 03:37:56.000000000 +0800
-+++ linux-2.4.20-root/arch/s390x/kernel/wrapper32.S    2003-05-07 18:08:03.000000000 +0800
-@@ -1091,3 +1091,95 @@ sys32_fstat64_wrapper:
-       llgtr   %r3,%r3                 # struct stat64 *
-       llgfr   %r4,%r4                 # long
-       jg      sys32_fstat64           # branch to system call
-+
-+      .globl  sys32_setxattr_wrapper
-+sys32_setxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_setxattr
-+
-+      .globl  sys32_lsetxattr_wrapper
-+sys32_lsetxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_lsetxattr
-+
-+      .globl  sys32_fsetxattr_wrapper
-+sys32_fsetxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_fsetxattr
-+
-+      .globl  sys32_getxattr_wrapper
-+sys32_getxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_getxattr
-+
-+      .globl  sys32_lgetxattr_wrapper
-+sys32_lgetxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_lgetxattr
-+
-+      .globl  sys32_fgetxattr_wrapper
-+sys32_fgetxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_fgetxattr
-+
-+      .globl  sys32_listxattr_wrapper
-+sys32_listxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_listxattr
-+
-+      .globl  sys32_llistxattr_wrapper
-+sys32_llistxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_llistxattr
-+
-+      .globl  sys32_flistxattr_wrapper
-+sys32_flistxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_flistxattr
-+
-+      .globl  sys32_removexattr_wrapper
-+sys32_removexattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_removexattr
-+
-+      .globl  sys32_lremovexattr_wrapper
-+sys32_lremovexattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_lremovexattr
-+
-+      .globl  sys32_fremovexattr_wrapper
-+sys32_fremovexattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_fremovexattr
-+
-+
---- linux-2.4.20/arch/sparc64/defconfig~linux-2.4.20-xattr-0.8.54      2002-11-29 07:53:12.000000000 +0800
-+++ linux-2.4.20-root/arch/sparc64/defconfig   2003-05-07 18:08:03.000000000 +0800
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- #
- # Code maturity level options
---- linux-2.4.20/fs/Config.in~linux-2.4.20-xattr-0.8.54        2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/Config.in     2003-05-07 18:08:03.000000000 +0800
-@@ -25,6 +25,11 @@ dep_mbool '  Debug Befs' CONFIG_BEFS_DEB
- dep_tristate 'BFS file system support (EXPERIMENTAL)' CONFIG_BFS_FS $CONFIG_EXPERIMENTAL
- tristate 'Ext3 journalling file system support' CONFIG_EXT3_FS
-+dep_mbool '  Ext3 extended attributes' CONFIG_EXT3_FS_XATTR $CONFIG_EXT3_FS
-+dep_bool '    Ext3 extended attribute block sharing' \
-+    CONFIG_EXT3_FS_XATTR_SHARING $CONFIG_EXT3_FS_XATTR
-+dep_bool '    Ext3 extended user attributes' \
-+    CONFIG_EXT3_FS_XATTR_USER $CONFIG_EXT3_FS_XATTR
- # CONFIG_JBD could be its own option (even modular), but until there are
- # other users than ext3, we will simply make it be the same as CONFIG_EXT3_FS
- # dep_tristate '  Journal Block Device support (JBD for ext3)' CONFIG_JBD $CONFIG_EXT3_FS
-@@ -84,6 +89,11 @@ dep_mbool '  QNX4FS write support (DANGE
- tristate 'ROM file system support' CONFIG_ROMFS_FS
- tristate 'Second extended fs support' CONFIG_EXT2_FS
-+dep_mbool '  Ext2 extended attributes' CONFIG_EXT2_FS_XATTR $CONFIG_EXT2_FS
-+dep_bool '    Ext2 extended attribute block sharing' \
-+    CONFIG_EXT2_FS_XATTR_SHARING $CONFIG_EXT2_FS_XATTR
-+dep_bool '    Ext2 extended user attributes' \
-+    CONFIG_EXT2_FS_XATTR_USER $CONFIG_EXT2_FS_XATTR
- tristate 'System V/Xenix/V7/Coherent file system support' CONFIG_SYSV_FS
-@@ -155,6 +165,10 @@ else
-    define_tristate CONFIG_ZISOFS_FS n
- fi
-+# Meta block cache for Extended Attributes (ext2/ext3)
-+#tristate 'Meta block cache' CONFIG_FS_MBCACHE
-+define_tristate CONFIG_FS_MBCACHE y 
-+
- mainmenu_option next_comment
- comment 'Partition Types'
- source fs/partitions/Config.in
---- linux-2.4.20/fs/Makefile~linux-2.4.20-xattr-0.8.54 2003-05-05 19:00:58.000000000 +0800
-+++ linux-2.4.20-root/fs/Makefile      2003-05-07 18:08:03.000000000 +0800
-@@ -79,6 +79,9 @@ obj-y                                += binfmt_script.o
- obj-$(CONFIG_BINFMT_ELF)      += binfmt_elf.o
-+export-objs += mbcache.o
-+obj-$(CONFIG_FS_MBCACHE)      += mbcache.o
-+
- # persistent filesystems
- obj-y += $(join $(subdir-y),$(subdir-y:%=/%.o))
---- linux-2.4.20/fs/ext2/Makefile~linux-2.4.20-xattr-0.8.54    2001-10-11 23:05:18.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/Makefile 2003-05-07 18:08:03.000000000 +0800
-@@ -13,4 +13,8 @@ obj-y    := balloc.o bitmap.o dir.o file
-               ioctl.o namei.o super.o symlink.o
- obj-m    := $(O_TARGET)
-+export-objs += xattr.o
-+obj-$(CONFIG_EXT2_FS_XATTR) += xattr.o
-+obj-$(CONFIG_EXT2_FS_XATTR_USER) += xattr_user.o
-+
- include $(TOPDIR)/Rules.make
---- linux-2.4.20/fs/ext2/file.c~linux-2.4.20-xattr-0.8.54      2001-10-11 23:05:18.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/file.c   2003-05-07 18:08:03.000000000 +0800
-@@ -20,6 +20,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/sched.h>
- /*
-@@ -51,4 +52,8 @@ struct file_operations ext2_file_operati
- struct inode_operations ext2_file_inode_operations = {
-       truncate:       ext2_truncate,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- linux-2.4.20/fs/ext2/ialloc.c~linux-2.4.20-xattr-0.8.54    2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/ialloc.c 2003-05-07 18:08:03.000000000 +0800
-@@ -15,6 +15,7 @@
- #include <linux/config.h>
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/locks.h>
- #include <linux/quotaops.h>
-@@ -167,6 +168,7 @@ void ext2_free_inode (struct inode * ino
-        */
-       if (!is_bad_inode(inode)) {
-               /* Quota is already initialized in iput() */
-+              ext2_xattr_delete_inode(inode);
-               DQUOT_FREE_INODE(inode);
-               DQUOT_DROP(inode);
-       }
---- linux-2.4.20/fs/ext2/inode.c~linux-2.4.20-xattr-0.8.54     2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/inode.c  2003-05-07 18:08:03.000000000 +0800
-@@ -39,6 +39,18 @@ MODULE_LICENSE("GPL");
- static int ext2_update_inode(struct inode * inode, int do_sync);
- /*
-+ * Test whether an inode is a fast symlink.
-+ */
-+static inline int ext2_inode_is_fast_symlink(struct inode *inode)
-+{
-+      int ea_blocks = inode->u.ext2_i.i_file_acl ?
-+              (inode->i_sb->s_blocksize >> 9) : 0;
-+
-+      return (S_ISLNK(inode->i_mode) &&
-+              inode->i_blocks - ea_blocks == 0);
-+}
-+
-+/*
-  * Called at each iput()
-  */
- void ext2_put_inode (struct inode * inode)
-@@ -53,9 +65,7 @@ void ext2_delete_inode (struct inode * i
- {
-       lock_kernel();
--      if (is_bad_inode(inode) ||
--          inode->i_ino == EXT2_ACL_IDX_INO ||
--          inode->i_ino == EXT2_ACL_DATA_INO)
-+      if (is_bad_inode(inode))
-               goto no_delete;
-       inode->u.ext2_i.i_dtime = CURRENT_TIME;
-       mark_inode_dirty(inode);
-@@ -801,6 +811,8 @@ void ext2_truncate (struct inode * inode
-       if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
-           S_ISLNK(inode->i_mode)))
-               return;
-+      if (ext2_inode_is_fast_symlink(inode))
-+              return;
-       if (IS_APPEND(inode) || IS_IMMUTABLE(inode))
-               return;
-@@ -888,8 +900,7 @@ void ext2_read_inode (struct inode * ino
-       unsigned long offset;
-       struct ext2_group_desc * gdp;
--      if ((inode->i_ino != EXT2_ROOT_INO && inode->i_ino != EXT2_ACL_IDX_INO &&
--           inode->i_ino != EXT2_ACL_DATA_INO &&
-+      if ((inode->i_ino != EXT2_ROOT_INO &&
-            inode->i_ino < EXT2_FIRST_INO(inode->i_sb)) ||
-           inode->i_ino > le32_to_cpu(inode->i_sb->u.ext2_sb.s_es->s_inodes_count)) {
-               ext2_error (inode->i_sb, "ext2_read_inode",
-@@ -974,10 +985,7 @@ void ext2_read_inode (struct inode * ino
-       for (block = 0; block < EXT2_N_BLOCKS; block++)
-               inode->u.ext2_i.i_data[block] = raw_inode->i_block[block];
--      if (inode->i_ino == EXT2_ACL_IDX_INO ||
--          inode->i_ino == EXT2_ACL_DATA_INO)
--              /* Nothing to do */ ;
--      else if (S_ISREG(inode->i_mode)) {
-+      if (S_ISREG(inode->i_mode)) {
-               inode->i_op = &ext2_file_inode_operations;
-               inode->i_fop = &ext2_file_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-@@ -986,15 +994,17 @@ void ext2_read_inode (struct inode * ino
-               inode->i_fop = &ext2_dir_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-       } else if (S_ISLNK(inode->i_mode)) {
--              if (!inode->i_blocks)
-+              if (ext2_inode_is_fast_symlink(inode))
-                       inode->i_op = &ext2_fast_symlink_inode_operations;
-               else {
--                      inode->i_op = &page_symlink_inode_operations;
-+                      inode->i_op = &ext2_symlink_inode_operations;
-                       inode->i_mapping->a_ops = &ext2_aops;
-               }
--      } else 
-+      } else {
-+              inode->i_op = &ext2_special_inode_operations;
-               init_special_inode(inode, inode->i_mode,
-                                  le32_to_cpu(raw_inode->i_block[0]));
-+      }
-       brelse (bh);
-       inode->i_attr_flags = 0;
-       if (inode->u.ext2_i.i_flags & EXT2_SYNC_FL) {
---- linux-2.4.20/fs/ext2/namei.c~linux-2.4.20-xattr-0.8.54     2001-10-04 13:57:36.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/namei.c  2003-05-07 18:08:03.000000000 +0800
-@@ -31,6 +31,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/pagemap.h>
- /*
-@@ -136,7 +137,7 @@ static int ext2_symlink (struct inode * 
-       if (l > sizeof (inode->u.ext2_i.i_data)) {
-               /* slow symlink */
--              inode->i_op = &page_symlink_inode_operations;
-+              inode->i_op = &ext2_symlink_inode_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-               err = block_symlink(inode, symname, l);
-               if (err)
-@@ -345,4 +346,15 @@ struct inode_operations ext2_dir_inode_o
-       rmdir:          ext2_rmdir,
-       mknod:          ext2_mknod,
-       rename:         ext2_rename,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
-+};
-+
-+struct inode_operations ext2_special_inode_operations = {
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- linux-2.4.20/fs/ext2/super.c~linux-2.4.20-xattr-0.8.54     2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/super.c  2003-05-07 18:08:03.000000000 +0800
-@@ -21,6 +21,7 @@
- #include <linux/string.h>
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/slab.h>
- #include <linux/init.h>
- #include <linux/locks.h>
-@@ -125,6 +126,7 @@ void ext2_put_super (struct super_block 
-       int db_count;
-       int i;
-+      ext2_xattr_put_super(sb);
-       if (!(sb->s_flags & MS_RDONLY)) {
-               struct ext2_super_block *es = EXT2_SB(sb)->s_es;
-@@ -175,6 +177,13 @@ static int parse_options (char * options
-            this_char = strtok (NULL, ",")) {
-               if ((value = strchr (this_char, '=')) != NULL)
-                       *value++ = 0;
-+#ifdef CONFIG_EXT2_FS_XATTR_USER
-+              if (!strcmp (this_char, "user_xattr"))
-+                      set_opt (*mount_options, XATTR_USER);
-+              else if (!strcmp (this_char, "nouser_xattr"))
-+                      clear_opt (*mount_options, XATTR_USER);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -424,6 +433,9 @@ struct super_block * ext2_read_super (st
-           blocksize = BLOCK_SIZE;
-       sb->u.ext2_sb.s_mount_opt = 0;
-+#ifdef CONFIG_EXT2_FS_XATTR_USER
-+      /* set_opt (sb->u.ext2_sb.s_mount_opt, XATTR_USER); */
-+#endif
-       if (!parse_options ((char *) data, &sb_block, &resuid, &resgid,
-           &sb->u.ext2_sb.s_mount_opt)) {
-               return NULL;
-@@ -813,12 +825,27 @@ static DECLARE_FSTYPE_DEV(ext2_fs_type, 
- static int __init init_ext2_fs(void)
- {
--        return register_filesystem(&ext2_fs_type);
-+      int error = init_ext2_xattr();
-+      if (error)
-+              return error;
-+      error = init_ext2_xattr_user();
-+      if (error)
-+              goto fail;
-+      error = register_filesystem(&ext2_fs_type);
-+      if (!error)
-+              return 0;
-+
-+      exit_ext2_xattr_user();
-+fail:
-+      exit_ext2_xattr();
-+      return error;
- }
- static void __exit exit_ext2_fs(void)
- {
-       unregister_filesystem(&ext2_fs_type);
-+      exit_ext2_xattr_user();
-+      exit_ext2_xattr();
- }
- EXPORT_NO_SYMBOLS;
---- linux-2.4.20/fs/ext2/symlink.c~linux-2.4.20-xattr-0.8.54   2000-09-28 04:41:33.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/symlink.c        2003-05-07 18:08:03.000000000 +0800
-@@ -19,6 +19,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- static int ext2_readlink(struct dentry *dentry, char *buffer, int buflen)
- {
-@@ -32,7 +33,20 @@ static int ext2_follow_link(struct dentr
-       return vfs_follow_link(nd, s);
- }
-+struct inode_operations ext2_symlink_inode_operations = {
-+      readlink:       page_readlink,
-+      follow_link:    page_follow_link,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
-+};
-+
- struct inode_operations ext2_fast_symlink_inode_operations = {
-       readlink:       ext2_readlink,
-       follow_link:    ext2_follow_link,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/xattr.c  2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,1212 @@
-+/*
-+ * linux/fs/ext2/xattr.c
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ *
-+ * Fix by Harrison Xing <harrison@mountainviewdata.com>.
-+ * Extended attributes for symlinks and special files added per
-+ *  suggestion of Luka Renko <luka.renko@hermes.si>.
-+ */
-+
-+/*
-+ * Extended attributes are stored on disk blocks allocated outside of
-+ * any inode. The i_file_acl field is then made to point to this allocated
-+ * block. If all extended attributes of an inode are identical, these
-+ * inodes may share the same extended attribute block. Such situations
-+ * are automatically detected by keeping a cache of recent attribute block
-+ * numbers and hashes over the block's contents in memory.
-+ *
-+ *
-+ * Extended attribute block layout:
-+ *
-+ *   +------------------+
-+ *   | header           |
-+ *   | entry 1          | |
-+ *   | entry 2          | | growing downwards
-+ *   | entry 3          | v
-+ *   | four null bytes  |
-+ *   | . . .            |
-+ *   | value 1          | ^
-+ *   | value 3          | | growing upwards
-+ *   | value 2          | |
-+ *   +------------------+
-+ *
-+ * The block header is followed by multiple entry descriptors. These entry
-+ * descriptors are variable in size, and alligned to EXT2_XATTR_PAD
-+ * byte boundaries. The entry descriptors are sorted by attribute name,
-+ * so that two extended attribute blocks can be compared efficiently.
-+ *
-+ * Attribute values are aligned to the end of the block, stored in
-+ * no specific order. They are also padded to EXT2_XATTR_PAD byte
-+ * boundaries. No additional gaps are left between them.
-+ *
-+ * Locking strategy
-+ * ----------------
-+ * The VFS already holds the BKL and the inode->i_sem semaphore when any of
-+ * the xattr inode operations are called, so we are guaranteed that only one
-+ * processes accesses extended attributes of an inode at any time.
-+ *
-+ * For writing we also grab the ext2_xattr_sem semaphore. This ensures that
-+ * only a single process is modifying an extended attribute block, even
-+ * if the block is shared among inodes.
-+ *
-+ * Note for porting to 2.5
-+ * -----------------------
-+ * The BKL will no longer be held in the xattr inode operations.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/locks.h>
-+#include <linux/slab.h>
-+#include <linux/fs.h>
-+#include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
-+#include <linux/mbcache.h>
-+#include <linux/quotaops.h>
-+#include <asm/semaphore.h>
-+#include <linux/compatmac.h>
-+
-+/* These symbols may be needed by a module. */
-+EXPORT_SYMBOL(ext2_xattr_register);
-+EXPORT_SYMBOL(ext2_xattr_unregister);
-+EXPORT_SYMBOL(ext2_xattr_get);
-+EXPORT_SYMBOL(ext2_xattr_list);
-+EXPORT_SYMBOL(ext2_xattr_set);
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+# define mark_buffer_dirty(bh) mark_buffer_dirty(bh, 1)
-+#endif
-+
-+#define HDR(bh) ((struct ext2_xattr_header *)((bh)->b_data))
-+#define ENTRY(ptr) ((struct ext2_xattr_entry *)(ptr))
-+#define FIRST_ENTRY(bh) ENTRY(HDR(bh)+1)
-+#define IS_LAST_ENTRY(entry) (*(__u32 *)(entry) == 0)
-+
-+#ifdef EXT2_XATTR_DEBUG
-+# define ea_idebug(inode, f...) do { \
-+              printk(KERN_DEBUG "inode %s:%ld: ", \
-+                      kdevname(inode->i_dev), inode->i_ino); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+# define ea_bdebug(bh, f...) do { \
-+              printk(KERN_DEBUG "block %s:%ld: ", \
-+                      kdevname(bh->b_dev), bh->b_blocknr); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+#else
-+# define ea_idebug(f...)
-+# define ea_bdebug(f...)
-+#endif
-+
-+static int ext2_xattr_set2(struct inode *, struct buffer_head *,
-+                         struct ext2_xattr_header *);
-+
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+
-+static int ext2_xattr_cache_insert(struct buffer_head *);
-+static struct buffer_head *ext2_xattr_cache_find(struct inode *,
-+                                               struct ext2_xattr_header *);
-+static void ext2_xattr_cache_remove(struct buffer_head *);
-+static void ext2_xattr_rehash(struct ext2_xattr_header *,
-+                            struct ext2_xattr_entry *);
-+
-+static struct mb_cache *ext2_xattr_cache;
-+
-+#else
-+# define ext2_xattr_cache_insert(bh) 0
-+# define ext2_xattr_cache_find(inode, header) NULL
-+# define ext2_xattr_cache_remove(bh) while(0) {}
-+# define ext2_xattr_rehash(header, entry) while(0) {}
-+#endif
-+
-+/*
-+ * If a file system does not share extended attributes among inodes,
-+ * we should not need the ext2_xattr_sem semaphore. However, the
-+ * filesystem may still contain shared blocks, so we always take
-+ * the lock.
-+ */
-+
-+DECLARE_MUTEX(ext2_xattr_sem);
-+
-+static inline int
-+ext2_xattr_new_block(struct inode *inode, int * errp, int force)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      int goal = le32_to_cpu(EXT2_SB(sb)->s_es->s_first_data_block) +
-+              EXT2_I(inode)->i_block_group * EXT2_BLOCKS_PER_GROUP(sb);
-+
-+      /* How can we enforce the allocation? */
-+      int block = ext2_new_block(inode, goal, 0, 0, errp);
-+#ifdef OLD_QUOTAS
-+      if (!*errp)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#endif
-+      return block;
-+}
-+
-+static inline int
-+ext2_xattr_quota_alloc(struct inode *inode, int force)
-+{
-+      /* How can we enforce the allocation? */
-+#ifdef OLD_QUOTAS
-+      int error = DQUOT_ALLOC_BLOCK(inode->i_sb, inode, 1);
-+      if (!error)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#else
-+      int error = DQUOT_ALLOC_BLOCK(inode, 1);
-+#endif
-+      return error;
-+}
-+
-+#ifdef OLD_QUOTAS
-+
-+static inline void
-+ext2_xattr_quota_free(struct inode *inode)
-+{
-+      DQUOT_FREE_BLOCK(inode->i_sb, inode, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+static inline void
-+ext2_xattr_free_block(struct inode * inode, unsigned long block)
-+{
-+      ext2_free_blocks(inode, block, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+#else
-+# define ext2_xattr_quota_free(inode) \
-+      DQUOT_FREE_BLOCK(inode, 1)
-+# define ext2_xattr_free_block(inode, block) \
-+      ext2_free_blocks(inode, block, 1)
-+#endif
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,18)
-+
-+static inline struct buffer_head *
-+sb_bread(struct super_block *sb, int block)
-+{
-+      return bread(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+static inline struct buffer_head *
-+sb_getblk(struct super_block *sb, int block)
-+{
-+      return getblk(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+#endif
-+
-+struct ext2_xattr_handler *ext2_xattr_handlers[EXT2_XATTR_INDEX_MAX];
-+rwlock_t ext2_handler_lock = RW_LOCK_UNLOCKED;
-+
-+int
-+ext2_xattr_register(int name_index, struct ext2_xattr_handler *handler)
-+{
-+      int error = -EINVAL;
-+
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              write_lock(&ext2_handler_lock);
-+              if (!ext2_xattr_handlers[name_index-1]) {
-+                      ext2_xattr_handlers[name_index-1] = handler;
-+                      error = 0;
-+              }
-+              write_unlock(&ext2_handler_lock);
-+      }
-+      return error;
-+}
-+
-+void
-+ext2_xattr_unregister(int name_index, struct ext2_xattr_handler *handler)
-+{
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              write_lock(&ext2_handler_lock);
-+              ext2_xattr_handlers[name_index-1] = NULL;
-+              write_unlock(&ext2_handler_lock);
-+      }
-+}
-+
-+static inline const char *
-+strcmp_prefix(const char *a, const char *a_prefix)
-+{
-+      while (*a_prefix && *a == *a_prefix) {
-+              a++;
-+              a_prefix++;
-+      }
-+      return *a_prefix ? NULL : a;
-+}
-+
-+/*
-+ * Decode the extended attribute name, and translate it into
-+ * the name_index and name suffix.
-+ */
-+static struct ext2_xattr_handler *
-+ext2_xattr_resolve_name(const char **name)
-+{
-+      struct ext2_xattr_handler *handler = NULL;
-+      int i;
-+
-+      if (!*name)
-+              return NULL;
-+      read_lock(&ext2_handler_lock);
-+      for (i=0; i<EXT2_XATTR_INDEX_MAX; i++) {
-+              if (ext2_xattr_handlers[i]) {
-+                      const char *n = strcmp_prefix(*name,
-+                              ext2_xattr_handlers[i]->prefix);
-+                      if (n) {
-+                              handler = ext2_xattr_handlers[i];
-+                              *name = n;
-+                              break;
-+                      }
-+              }
-+      }
-+      read_unlock(&ext2_handler_lock);
-+      return handler;
-+}
-+
-+static inline struct ext2_xattr_handler *
-+ext2_xattr_handler(int name_index)
-+{
-+      struct ext2_xattr_handler *handler = NULL;
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              read_lock(&ext2_handler_lock);
-+              handler = ext2_xattr_handlers[name_index-1];
-+              read_unlock(&ext2_handler_lock);
-+      }
-+      return handler;
-+}
-+
-+/*
-+ * Inode operation getxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext2_getxattr(struct dentry *dentry, const char *name,
-+            void *buffer, size_t size)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->get(inode, name, buffer, size);
-+}
-+
-+/*
-+ * Inode operation listxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext2_listxattr(struct dentry *dentry, char *buffer, size_t size)
-+{
-+      return ext2_xattr_list(dentry->d_inode, buffer, size);
-+}
-+
-+/*
-+ * Inode operation setxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext2_setxattr(struct dentry *dentry, const char *name,
-+            const void *value, size_t size, int flags)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      if (size == 0)
-+              value = "";  /* empty EA, do not remove */
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, value, size, flags);
-+}
-+
-+/*
-+ * Inode operation removexattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext2_removexattr(struct dentry *dentry, const char *name)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, NULL, 0, XATTR_REPLACE);
-+}
-+
-+/*
-+ * ext2_xattr_get()
-+ *
-+ * Copy an extended attribute into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext2_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_entry *entry;
-+      unsigned int block, size;
-+      char *end;
-+      int name_len, error;
-+
-+      ea_idebug(inode, "name=%d.%s, buffer=%p, buffer_size=%ld",
-+                name_index, name, buffer, (long)buffer_size);
-+
-+      if (name == NULL)
-+              return -EINVAL;
-+      if (!EXT2_I(inode)->i_file_acl)
-+              return -ENOATTR;
-+      block = EXT2_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext2_error(inode->i_sb, "ext2_xattr_get",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* find named attribute */
-+      name_len = strlen(name);
-+
-+      error = -ERANGE;
-+      if (name_len > 255)
-+              goto cleanup;
-+      entry = FIRST_ENTRY(bh);
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              if (name_index == entry->e_name_index &&
-+                  name_len == entry->e_name_len &&
-+                  memcmp(name, entry->e_name, name_len) == 0)
-+                      goto found;
-+              entry = next;
-+      }
-+      /* Check the remaining name entries */
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              entry = next;
-+      }
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      error = -ENOATTR;
-+      goto cleanup;
-+found:
-+      /* check the buffer size */
-+      if (entry->e_value_block != 0)
-+              goto bad_block;
-+      size = le32_to_cpu(entry->e_value_size);
-+      if (size > inode->i_sb->s_blocksize ||
-+          le16_to_cpu(entry->e_value_offs) + size > inode->i_sb->s_blocksize)
-+              goto bad_block;
-+
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (buffer) {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+              /* return value of attribute */
-+              memcpy(buffer, bh->b_data + le16_to_cpu(entry->e_value_offs),
-+                      size);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_list()
-+ *
-+ * Copy a list of attribute names into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext2_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_entry *entry;
-+      unsigned int block, size = 0;
-+      char *buf, *end;
-+      int error;
-+
-+      ea_idebug(inode, "buffer=%p, buffer_size=%ld",
-+                buffer, (long)buffer_size);
-+
-+      if (!EXT2_I(inode)->i_file_acl)
-+              return 0;
-+      block = EXT2_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext2_error(inode->i_sb, "ext2_xattr_list",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* compute the size required for the list of attribute names */
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT2_XATTR_NEXT(entry)) {
-+              struct ext2_xattr_handler *handler;
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+
-+              handler = ext2_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      size += handler->list(NULL, inode, entry->e_name,
-+                                            entry->e_name_len);
-+      }
-+
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (!buffer) {
-+              error = size;
-+              goto cleanup;
-+      } else {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+      }
-+
-+      /* list the attribute names */
-+      buf = buffer;
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT2_XATTR_NEXT(entry)) {
-+              struct ext2_xattr_handler *handler;
-+              
-+              handler = ext2_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      buf += handler->list(buf, inode, entry->e_name,
-+                                           entry->e_name_len);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * If the EXT2_FEATURE_COMPAT_EXT_ATTR feature of this file system is
-+ * not set, set it.
-+ */
-+static void ext2_xattr_update_super_block(struct super_block *sb)
-+{
-+      if (EXT2_HAS_COMPAT_FEATURE(sb, EXT2_FEATURE_COMPAT_EXT_ATTR))
-+              return;
-+
-+      lock_super(sb);
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+      EXT2_SB(sb)->s_feature_compat |= EXT2_FEATURE_COMPAT_EXT_ATTR;
-+#endif
-+      EXT2_SB(sb)->s_es->s_feature_compat |=
-+              cpu_to_le32(EXT2_FEATURE_COMPAT_EXT_ATTR);
-+      sb->s_dirt = 1;
-+      mark_buffer_dirty(EXT2_SB(sb)->s_sbh);
-+      unlock_super(sb);
-+}
-+
-+/*
-+ * ext2_xattr_set()
-+ *
-+ * Create, replace or remove an extended attribute for this inode. Buffer
-+ * is NULL to remove an existing extended attribute, and non-NULL to
-+ * either replace an existing extended attribute, or create a new extended
-+ * attribute. The flags XATTR_REPLACE and XATTR_CREATE
-+ * specify that an extended attribute must exist and must not exist
-+ * previous to the call, respectively.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+int
-+ext2_xattr_set(struct inode *inode, int name_index, const char *name,
-+             const void *value, size_t value_len, int flags)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_header *header = NULL;
-+      struct ext2_xattr_entry *here, *last;
-+      unsigned int name_len;
-+      int block = EXT2_I(inode)->i_file_acl;
-+      int min_offs = sb->s_blocksize, not_found = 1, free, error;
-+      char *end;
-+      
-+      /*
-+       * header -- Points either into bh, or to a temporarily
-+       *           allocated buffer.
-+       * here -- The named entry found, or the place for inserting, within
-+       *         the block pointed to by header.
-+       * last -- Points right after the last named entry within the block
-+       *         pointed to by header.
-+       * min_offs -- The offset of the first value (values are aligned
-+       *             towards the end of the block).
-+       * end -- Points right after the block pointed to by header.
-+       */
-+      
-+      ea_idebug(inode, "name=%d.%s, value=%p, value_len=%ld",
-+                name_index, name, value, (long)value_len);
-+
-+      if (IS_RDONLY(inode))
-+              return -EROFS;
-+      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-+              return -EPERM;
-+      if (value == NULL)
-+              value_len = 0;
-+      if (name == NULL)
-+              return -EINVAL;
-+      name_len = strlen(name);
-+      if (name_len > 255 || value_len > sb->s_blocksize)
-+              return -ERANGE;
-+      down(&ext2_xattr_sem);
-+
-+      if (block) {
-+              /* The inode already has an extended attribute block. */
-+
-+              bh = sb_bread(sb, block);
-+              error = -EIO;
-+              if (!bh)
-+                      goto cleanup;
-+              ea_bdebug(bh, "b_count=%d, refcount=%d",
-+                      atomic_read(&(bh->b_count)),
-+                      le32_to_cpu(HDR(bh)->h_refcount));
-+              header = HDR(bh);
-+              end = bh->b_data + bh->b_size;
-+              if (header->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+                  header->h_blocks != cpu_to_le32(1)) {
-+bad_block:            ext2_error(sb, "ext2_xattr_set",
-+                              "inode %ld: bad block %d", inode->i_ino, block);
-+                      error = -EIO;
-+                      goto cleanup;
-+              }
-+              /* Find the named attribute. */
-+              here = FIRST_ENTRY(bh);
-+              while (!IS_LAST_ENTRY(here)) {
-+                      struct ext2_xattr_entry *next = EXT2_XATTR_NEXT(here);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!here->e_value_block && here->e_value_size) {
-+                              int offs = le16_to_cpu(here->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      not_found = name_index - here->e_name_index;
-+                      if (!not_found)
-+                              not_found = name_len - here->e_name_len;
-+                      if (!not_found)
-+                              not_found = memcmp(name, here->e_name,name_len);
-+                      if (not_found <= 0)
-+                              break;
-+                      here = next;
-+              }
-+              last = here;
-+              /* We still need to compute min_offs and last. */
-+              while (!IS_LAST_ENTRY(last)) {
-+                      struct ext2_xattr_entry *next = EXT2_XATTR_NEXT(last);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!last->e_value_block && last->e_value_size) {
-+                              int offs = le16_to_cpu(last->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      last = next;
-+              }
-+
-+              /* Check whether we have enough space left. */
-+              free = min_offs - ((char*)last - (char*)header) - sizeof(__u32);
-+      } else {
-+              /* We will use a new extended attribute block. */
-+              free = sb->s_blocksize -
-+                      sizeof(struct ext2_xattr_header) - sizeof(__u32);
-+              here = last = NULL;  /* avoid gcc uninitialized warning. */
-+      }
-+
-+      if (not_found) {
-+              /* Request to remove a nonexistent attribute? */
-+              error = -ENOATTR;
-+              if (flags & XATTR_REPLACE)
-+                      goto cleanup;
-+              error = 0;
-+              if (value == NULL)
-+                      goto cleanup;
-+              else
-+                      free -= EXT2_XATTR_LEN(name_len);
-+      } else {
-+              /* Request to create an existing attribute? */
-+              error = -EEXIST;
-+              if (flags & XATTR_CREATE)
-+                      goto cleanup;
-+              if (!here->e_value_block && here->e_value_size) {
-+                      unsigned int size = le32_to_cpu(here->e_value_size);
-+
-+                      if (le16_to_cpu(here->e_value_offs) + size > 
-+                          sb->s_blocksize || size > sb->s_blocksize)
-+                              goto bad_block;
-+                      free += EXT2_XATTR_SIZE(size);
-+              }
-+      }
-+      free -= EXT2_XATTR_SIZE(value_len);
-+      error = -ENOSPC;
-+      if (free < 0)
-+              goto cleanup;
-+
-+      /* Here we know that we can set the new attribute. */
-+
-+      if (header) {
-+              if (header->h_refcount == cpu_to_le32(1)) {
-+                      ea_bdebug(bh, "modifying in-place");
-+                      ext2_xattr_cache_remove(bh);
-+              } else {
-+                      int offset;
-+
-+                      ea_bdebug(bh, "cloning");
-+                      header = kmalloc(bh->b_size, GFP_KERNEL);
-+                      error = -ENOMEM;
-+                      if (header == NULL)
-+                              goto cleanup;
-+                      memcpy(header, HDR(bh), bh->b_size);
-+                      header->h_refcount = cpu_to_le32(1);
-+                      offset = (char *)header - bh->b_data;
-+                      here = ENTRY((char *)here + offset);
-+                      last = ENTRY((char *)last + offset);
-+              }
-+      } else {
-+              /* Allocate a buffer where we construct the new block. */
-+              header = kmalloc(sb->s_blocksize, GFP_KERNEL);
-+              error = -ENOMEM;
-+              if (header == NULL)
-+                      goto cleanup;
-+              memset(header, 0, sb->s_blocksize);
-+              end = (char *)header + sb->s_blocksize;
-+              header->h_magic = cpu_to_le32(EXT2_XATTR_MAGIC);
-+              header->h_blocks = header->h_refcount = cpu_to_le32(1);
-+              last = here = ENTRY(header+1);
-+      }
-+
-+      if (not_found) {
-+              /* Insert the new name. */
-+              int size = EXT2_XATTR_LEN(name_len);
-+              int rest = (char *)last - (char *)here;
-+              memmove((char *)here + size, here, rest);
-+              memset(here, 0, size);
-+              here->e_name_index = name_index;
-+              here->e_name_len = name_len;
-+              memcpy(here->e_name, name, name_len);
-+      } else {
-+              /* Remove the old value. */
-+              if (!here->e_value_block && here->e_value_size) {
-+                      char *first_val = (char *)header + min_offs;
-+                      int offs = le16_to_cpu(here->e_value_offs);
-+                      char *val = (char *)header + offs;
-+                      size_t size = EXT2_XATTR_SIZE(
-+                              le32_to_cpu(here->e_value_size));
-+                      memmove(first_val + size, first_val, val - first_val);
-+                      memset(first_val, 0, size);
-+                      here->e_value_offs = 0;
-+                      min_offs += size;
-+
-+                      /* Adjust all value offsets. */
-+                      last = ENTRY(header+1);
-+                      while (!IS_LAST_ENTRY(last)) {
-+                              int o = le16_to_cpu(last->e_value_offs);
-+                              if (!last->e_value_block && o < offs)
-+                                      last->e_value_offs =
-+                                              cpu_to_le16(o + size);
-+                              last = EXT2_XATTR_NEXT(last);
-+                      }
-+              }
-+              if (value == NULL) {
-+                      /* Remove this attribute. */
-+                      if (EXT2_XATTR_NEXT(ENTRY(header+1)) == last) {
-+                              /* This block is now empty. */
-+                              error = ext2_xattr_set2(inode, bh, NULL);
-+                              goto cleanup;
-+                      } else {
-+                              /* Remove the old name. */
-+                              int size = EXT2_XATTR_LEN(name_len);
-+                              last = ENTRY((char *)last - size);
-+                              memmove(here, (char*)here + size,
-+                                      (char*)last - (char*)here);
-+                              memset(last, 0, size);
-+                      }
-+              }
-+      }
-+
-+      if (value != NULL) {
-+              /* Insert the new value. */
-+              here->e_value_size = cpu_to_le32(value_len);
-+              if (value_len) {
-+                      size_t size = EXT2_XATTR_SIZE(value_len);
-+                      char *val = (char *)header + min_offs - size;
-+                      here->e_value_offs =
-+                              cpu_to_le16((char *)val - (char *)header);
-+                      memset(val + size - EXT2_XATTR_PAD, 0,
-+                             EXT2_XATTR_PAD); /* Clear the pad bytes. */
-+                      memcpy(val, value, value_len);
-+              }
-+      }
-+      ext2_xattr_rehash(header, here);
-+
-+      error = ext2_xattr_set2(inode, bh, header);
-+
-+cleanup:
-+      brelse(bh);
-+      if (!(bh && header == HDR(bh)))
-+              kfree(header);
-+      up(&ext2_xattr_sem);
-+
-+      return error;
-+}
-+
-+/*
-+ * Second half of ext2_xattr_set(): Update the file system.
-+ */
-+static int
-+ext2_xattr_set2(struct inode *inode, struct buffer_head *old_bh,
-+              struct ext2_xattr_header *header)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *new_bh = NULL;
-+      int error;
-+
-+      if (header) {
-+              new_bh = ext2_xattr_cache_find(inode, header);
-+              if (new_bh) {
-+                      /*
-+                       * We found an identical block in the cache.
-+                       * The old block will be released after updating
-+                       * the inode.
-+                       */
-+                      ea_bdebug(old_bh, "reusing block %ld",
-+                              new_bh->b_blocknr);
-+                      
-+                      error = -EDQUOT;
-+                      if (ext2_xattr_quota_alloc(inode, 1))
-+                              goto cleanup;
-+                      
-+                      HDR(new_bh)->h_refcount = cpu_to_le32(
-+                              le32_to_cpu(HDR(new_bh)->h_refcount) + 1);
-+                      ea_bdebug(new_bh, "refcount now=%d",
-+                              le32_to_cpu(HDR(new_bh)->h_refcount));
-+              } else if (old_bh && header == HDR(old_bh)) {
-+                      /* Keep this block. */
-+                      new_bh = old_bh;
-+                      (void)ext2_xattr_cache_insert(new_bh);
-+              } else {
-+                      /* We need to allocate a new block */
-+                      int force = EXT2_I(inode)->i_file_acl != 0;
-+                      int block = ext2_xattr_new_block(inode, &error, force);
-+                      if (error)
-+                              goto cleanup;
-+                      ea_idebug(inode, "creating block %d", block);
-+
-+                      new_bh = sb_getblk(sb, block);
-+                      if (!new_bh) {
-+                              ext2_xattr_free_block(inode, block);
-+                              error = -EIO;
-+                              goto cleanup;
-+                      }
-+                      lock_buffer(new_bh);
-+                      memcpy(new_bh->b_data, header, new_bh->b_size);
-+                      mark_buffer_uptodate(new_bh, 1);
-+                      unlock_buffer(new_bh);
-+                      (void)ext2_xattr_cache_insert(new_bh);
-+                      
-+                      ext2_xattr_update_super_block(sb);
-+              }
-+              mark_buffer_dirty(new_bh);
-+              if (IS_SYNC(inode)) {
-+                      ll_rw_block(WRITE, 1, &new_bh);
-+                      wait_on_buffer(new_bh); 
-+                      error = -EIO;
-+                      if (buffer_req(new_bh) && !buffer_uptodate(new_bh))
-+                              goto cleanup;
-+              }
-+      }
-+
-+      /* Update the inode. */
-+      EXT2_I(inode)->i_file_acl = new_bh ? new_bh->b_blocknr : 0;
-+      inode->i_ctime = CURRENT_TIME;
-+      if (IS_SYNC(inode)) {
-+              error = ext2_sync_inode (inode);
-+              if (error)
-+                      goto cleanup;
-+      } else
-+              mark_inode_dirty(inode);
-+
-+      error = 0;
-+      if (old_bh && old_bh != new_bh) {
-+              /*
-+               * If there was an old block, and we are not still using it,
-+               * we now release the old block.
-+              */
-+              unsigned int refcount = le32_to_cpu(HDR(old_bh)->h_refcount);
-+
-+              if (refcount == 1) {
-+                      /* Free the old block. */
-+                      ea_bdebug(old_bh, "freeing");
-+                      ext2_xattr_free_block(inode, old_bh->b_blocknr);
-+                      mark_buffer_clean(old_bh);
-+              } else {
-+                      /* Decrement the refcount only. */
-+                      refcount--;
-+                      HDR(old_bh)->h_refcount = cpu_to_le32(refcount);
-+                      ext2_xattr_quota_free(inode);
-+                      mark_buffer_dirty(old_bh);
-+                      ea_bdebug(old_bh, "refcount now=%d", refcount);
-+              }
-+      }
-+
-+cleanup:
-+      if (old_bh != new_bh)
-+              brelse(new_bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_delete_inode()
-+ *
-+ * Free extended attribute resources associated with this inode. This
-+ * is called immediately before an inode is freed.
-+ */
-+void
-+ext2_xattr_delete_inode(struct inode *inode)
-+{
-+      struct buffer_head *bh;
-+      unsigned int block = EXT2_I(inode)->i_file_acl;
-+
-+      if (!block)
-+              return;
-+      down(&ext2_xattr_sem);
-+
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh) {
-+              ext2_error(inode->i_sb, "ext2_xattr_delete_inode",
-+                      "inode %ld: block %d read error", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "b_count=%d", atomic_read(&(bh->b_count)));
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+              ext2_error(inode->i_sb, "ext2_xattr_delete_inode",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "refcount now=%d", le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+      if (HDR(bh)->h_refcount == cpu_to_le32(1)) {
-+              ext2_xattr_cache_remove(bh);
-+              ext2_xattr_free_block(inode, block);
-+              bforget(bh);
-+              bh = NULL;
-+      } else {
-+              HDR(bh)->h_refcount = cpu_to_le32(
-+                      le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+              mark_buffer_dirty(bh);
-+              if (IS_SYNC(inode)) {
-+                      ll_rw_block(WRITE, 1, &bh);
-+                      wait_on_buffer(bh);
-+              }
-+              ext2_xattr_quota_free(inode);
-+      }
-+      EXT2_I(inode)->i_file_acl = 0;
-+
-+cleanup:
-+      brelse(bh);
-+      up(&ext2_xattr_sem);
-+}
-+
-+/*
-+ * ext2_xattr_put_super()
-+ *
-+ * This is called when a file system is unmounted.
-+ */
-+void
-+ext2_xattr_put_super(struct super_block *sb)
-+{
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+      mb_cache_shrink(ext2_xattr_cache, sb->s_dev);
-+#endif
-+}
-+
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+
-+/*
-+ * ext2_xattr_cache_insert()
-+ *
-+ * Create a new entry in the extended attribute cache, and insert
-+ * it unless such an entry is already in the cache.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+static int
-+ext2_xattr_cache_insert(struct buffer_head *bh)
-+{
-+      __u32 hash = le32_to_cpu(HDR(bh)->h_hash);
-+      struct mb_cache_entry *ce;
-+      int error;
-+
-+      ce = mb_cache_entry_alloc(ext2_xattr_cache);
-+      if (!ce)
-+              return -ENOMEM;
-+      error = mb_cache_entry_insert(ce, bh->b_dev, bh->b_blocknr, &hash);
-+      if (error) {
-+              mb_cache_entry_free(ce);
-+              if (error == -EBUSY) {
-+                      ea_bdebug(bh, "already in cache (%d cache entries)",
-+                              atomic_read(&ext2_xattr_cache->c_entry_count));
-+                      error = 0;
-+              }
-+      } else {
-+              ea_bdebug(bh, "inserting [%x] (%d cache entries)", (int)hash,
-+                        atomic_read(&ext2_xattr_cache->c_entry_count));
-+              mb_cache_entry_release(ce);
-+      }
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_cmp()
-+ *
-+ * Compare two extended attribute blocks for equality.
-+ *
-+ * Returns 0 if the blocks are equal, 1 if they differ, and
-+ * a negative error number on errors.
-+ */
-+static int
-+ext2_xattr_cmp(struct ext2_xattr_header *header1,
-+             struct ext2_xattr_header *header2)
-+{
-+      struct ext2_xattr_entry *entry1, *entry2;
-+
-+      entry1 = ENTRY(header1+1);
-+      entry2 = ENTRY(header2+1);
-+      while (!IS_LAST_ENTRY(entry1)) {
-+              if (IS_LAST_ENTRY(entry2))
-+                      return 1;
-+              if (entry1->e_hash != entry2->e_hash ||
-+                  entry1->e_name_len != entry2->e_name_len ||
-+                  entry1->e_value_size != entry2->e_value_size ||
-+                  memcmp(entry1->e_name, entry2->e_name, entry1->e_name_len))
-+                      return 1;
-+              if (entry1->e_value_block != 0 || entry2->e_value_block != 0)
-+                      return -EIO;
-+              if (memcmp((char *)header1 + le16_to_cpu(entry1->e_value_offs),
-+                         (char *)header2 + le16_to_cpu(entry2->e_value_offs),
-+                         le32_to_cpu(entry1->e_value_size)))
-+                      return 1;
-+
-+              entry1 = EXT2_XATTR_NEXT(entry1);
-+              entry2 = EXT2_XATTR_NEXT(entry2);
-+      }
-+      if (!IS_LAST_ENTRY(entry2))
-+              return 1;
-+      return 0;
-+}
-+
-+/*
-+ * ext2_xattr_cache_find()
-+ *
-+ * Find an identical extended attribute block.
-+ *
-+ * Returns a pointer to the block found, or NULL if such a block was
-+ * not found or an error occurred.
-+ */
-+static struct buffer_head *
-+ext2_xattr_cache_find(struct inode *inode, struct ext2_xattr_header *header)
-+{
-+      __u32 hash = le32_to_cpu(header->h_hash);
-+      struct mb_cache_entry *ce;
-+
-+      if (!header->h_hash)
-+              return NULL;  /* never share */
-+      ea_idebug(inode, "looking for cached blocks [%x]", (int)hash);
-+      ce = mb_cache_entry_find_first(ext2_xattr_cache, 0, inode->i_dev, hash);
-+      while (ce) {
-+              struct buffer_head *bh = sb_bread(inode->i_sb, ce->e_block);
-+
-+              if (!bh) {
-+                      ext2_error(inode->i_sb, "ext2_xattr_cache_find",
-+                              "inode %ld: block %ld read error",
-+                              inode->i_ino, ce->e_block);
-+              } else if (le32_to_cpu(HDR(bh)->h_refcount) >
-+                         EXT2_XATTR_REFCOUNT_MAX) {
-+                      ea_idebug(inode, "block %ld refcount %d>%d",ce->e_block,
-+                              le32_to_cpu(HDR(bh)->h_refcount),
-+                              EXT2_XATTR_REFCOUNT_MAX);
-+              } else if (!ext2_xattr_cmp(header, HDR(bh))) {
-+                      ea_bdebug(bh, "b_count=%d",atomic_read(&(bh->b_count)));
-+                      mb_cache_entry_release(ce);
-+                      return bh;
-+              }
-+              brelse(bh);
-+              ce = mb_cache_entry_find_next(ce, 0, inode->i_dev, hash);
-+      }
-+      return NULL;
-+}
-+
-+/*
-+ * ext2_xattr_cache_remove()
-+ *
-+ * Remove the cache entry of a block from the cache. Called when a
-+ * block becomes invalid.
-+ */
-+static void
-+ext2_xattr_cache_remove(struct buffer_head *bh)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      ce = mb_cache_entry_get(ext2_xattr_cache, bh->b_dev, bh->b_blocknr);
-+      if (ce) {
-+              ea_bdebug(bh, "removing (%d cache entries remaining)",
-+                        atomic_read(&ext2_xattr_cache->c_entry_count)-1);
-+              mb_cache_entry_free(ce);
-+      } else 
-+              ea_bdebug(bh, "no cache entry");
-+}
-+
-+#define NAME_HASH_SHIFT 5
-+#define VALUE_HASH_SHIFT 16
-+
-+/*
-+ * ext2_xattr_hash_entry()
-+ *
-+ * Compute the hash of an extended attribute.
-+ */
-+static inline void ext2_xattr_hash_entry(struct ext2_xattr_header *header,
-+                                       struct ext2_xattr_entry *entry)
-+{
-+      __u32 hash = 0;
-+      char *name = entry->e_name;
-+      int n;
-+
-+      for (n=0; n < entry->e_name_len; n++) {
-+              hash = (hash << NAME_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - NAME_HASH_SHIFT)) ^
-+                     *name++;
-+      }
-+
-+      if (entry->e_value_block == 0 && entry->e_value_size != 0) {
-+              __u32 *value = (__u32 *)((char *)header +
-+                      le16_to_cpu(entry->e_value_offs));
-+              for (n = (le32_to_cpu(entry->e_value_size) +
-+                   EXT2_XATTR_ROUND) >> EXT2_XATTR_PAD_BITS; n; n--) {
-+                      hash = (hash << VALUE_HASH_SHIFT) ^
-+                             (hash >> (8*sizeof(hash) - VALUE_HASH_SHIFT)) ^
-+                             le32_to_cpu(*value++);
-+              }
-+      }
-+      entry->e_hash = cpu_to_le32(hash);
-+}
-+
-+#undef NAME_HASH_SHIFT
-+#undef VALUE_HASH_SHIFT
-+
-+#define BLOCK_HASH_SHIFT 16
-+
-+/*
-+ * ext2_xattr_rehash()
-+ *
-+ * Re-compute the extended attribute hash value after an entry has changed.
-+ */
-+static void ext2_xattr_rehash(struct ext2_xattr_header *header,
-+                            struct ext2_xattr_entry *entry)
-+{
-+      struct ext2_xattr_entry *here;
-+      __u32 hash = 0;
-+      
-+      ext2_xattr_hash_entry(header, entry);
-+      here = ENTRY(header+1);
-+      while (!IS_LAST_ENTRY(here)) {
-+              if (!here->e_hash) {
-+                      /* Block is not shared if an entry's hash value == 0 */
-+                      hash = 0;
-+                      break;
-+              }
-+              hash = (hash << BLOCK_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - BLOCK_HASH_SHIFT)) ^
-+                     le32_to_cpu(here->e_hash);
-+              here = EXT2_XATTR_NEXT(here);
-+      }
-+      header->h_hash = cpu_to_le32(hash);
-+}
-+
-+#undef BLOCK_HASH_SHIFT
-+
-+int __init
-+init_ext2_xattr(void)
-+{
-+      ext2_xattr_cache = mb_cache_create("ext2_xattr", NULL,
-+              sizeof(struct mb_cache_entry) +
-+              sizeof(struct mb_cache_entry_index), 1, 61);
-+      if (!ext2_xattr_cache)
-+              return -ENOMEM;
-+
-+      return 0;
-+}
-+
-+void
-+exit_ext2_xattr(void)
-+{
-+      mb_cache_destroy(ext2_xattr_cache);
-+}
-+
-+#else  /* CONFIG_EXT2_FS_XATTR_SHARING */
-+
-+int __init
-+init_ext2_xattr(void)
-+{
-+      return 0;
-+}
-+
-+void
-+exit_ext2_xattr(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT2_FS_XATTR_SHARING */
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/fs/ext2/xattr_user.c     2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,103 @@
-+/*
-+ * linux/fs/ext2/xattr_user.c
-+ * Handler for extended user attributes.
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/string.h>
-+#include <linux/fs.h>
-+#include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
-+
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+# include <linux/ext2_acl.h>
-+#endif
-+
-+#define XATTR_USER_PREFIX "user."
-+
-+static size_t
-+ext2_xattr_user_list(char *list, struct inode *inode,
-+                   const char *name, int name_len)
-+{
-+      const int prefix_len = sizeof(XATTR_USER_PREFIX)-1;
-+
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return 0;
-+
-+      if (list) {
-+              memcpy(list, XATTR_USER_PREFIX, prefix_len);
-+              memcpy(list+prefix_len, name, name_len);
-+              list[prefix_len + name_len] = '\0';
-+      }
-+      return prefix_len + name_len + 1;
-+}
-+
-+static int
-+ext2_xattr_user_get(struct inode *inode, const char *name,
-+                  void *buffer, size_t size)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+      error = ext2_permission_locked(inode, MAY_READ);
-+#else
-+      error = permission(inode, MAY_READ);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext2_xattr_get(inode, EXT2_XATTR_INDEX_USER, name,
-+                            buffer, size);
-+}
-+
-+static int
-+ext2_xattr_user_set(struct inode *inode, const char *name,
-+                  const void *value, size_t size, int flags)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+      if ( !S_ISREG(inode->i_mode) &&
-+          (!S_ISDIR(inode->i_mode) || inode->i_mode & S_ISVTX))
-+              return -EPERM;
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+      error = ext2_permission_locked(inode, MAY_WRITE);
-+#else
-+      error = permission(inode, MAY_WRITE);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext2_xattr_set(inode, EXT2_XATTR_INDEX_USER, name,
-+                            value, size, flags);
-+}
-+
-+struct ext2_xattr_handler ext2_xattr_user_handler = {
-+      prefix: XATTR_USER_PREFIX,
-+      list:   ext2_xattr_user_list,
-+      get:    ext2_xattr_user_get,
-+      set:    ext2_xattr_user_set,
-+};
-+
-+int __init
-+init_ext2_xattr_user(void)
-+{
-+      return ext2_xattr_register(EXT2_XATTR_INDEX_USER,
-+                                 &ext2_xattr_user_handler);
-+}
-+
-+void
-+exit_ext2_xattr_user(void)
-+{
-+      ext2_xattr_unregister(EXT2_XATTR_INDEX_USER,
-+                            &ext2_xattr_user_handler);
-+}
---- linux-2.4.20/fs/ext3/Makefile~linux-2.4.20-xattr-0.8.54    2003-05-05 19:01:02.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/Makefile 2003-05-07 18:10:33.000000000 +0800
-@@ -1,5 +1,5 @@
- #
--# Makefile for the linux ext2-filesystem routines.
-+# Makefile for the linux ext3-filesystem routines.
- #
- # Note! Dependencies are done automagically by 'make dep', which also
- # removes any old dependencies. DON'T put your own dependencies here
-@@ -9,10 +9,14 @@
- O_TARGET := ext3.o
--export-objs :=        super.o inode.o
-+export-objs := ext3-exports.o
- obj-y    := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o \
--              ioctl.o namei.o super.o symlink.o hash.o
-+              ioctl.o namei.o super.o symlink.o hash.o ext3-exports.o
- obj-m    := $(O_TARGET)
-+export-objs += xattr.o
-+obj-$(CONFIG_EXT3_FS_XATTR) += xattr.o
-+obj-$(CONFIG_EXT3_FS_XATTR_USER) += xattr_user.o
-+
- include $(TOPDIR)/Rules.make
---- linux-2.4.20/fs/ext3/file.c~linux-2.4.20-xattr-0.8.54      2003-05-05 19:01:02.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/file.c   2003-05-07 18:08:03.000000000 +0800
-@@ -23,6 +23,7 @@
- #include <linux/locks.h>
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/ext3_jbd.h>
- #include <linux/smp_lock.h>
-@@ -126,5 +127,9 @@ struct file_operations ext3_file_operati
- struct inode_operations ext3_file_inode_operations = {
-       truncate:       ext3_truncate,          /* BKL held */
-       setattr:        ext3_setattr,           /* BKL held */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
---- linux-2.4.20/fs/ext3/ialloc.c~linux-2.4.20-xattr-0.8.54    2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/ialloc.c 2003-05-07 18:08:03.000000000 +0800
-@@ -17,6 +17,7 @@
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/stat.h>
- #include <linux/string.h>
- #include <linux/locks.h>
-@@ -216,6 +217,7 @@ void ext3_free_inode (handle_t *handle, 
-        * as writing the quota to disk may need the lock as well.
-        */
-       DQUOT_INIT(inode);
-+      ext3_xattr_delete_inode(handle, inode);
-       DQUOT_FREE_INODE(inode);
-       DQUOT_DROP(inode);
---- linux-2.4.20/fs/ext3/inode.c~linux-2.4.20-xattr-0.8.54     2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/inode.c  2003-05-07 18:08:03.000000000 +0800
-@@ -39,6 +39,18 @@
-  */
- #undef SEARCH_FROM_ZERO
-+/*
-+ * Test whether an inode is a fast symlink.
-+ */
-+static inline int ext3_inode_is_fast_symlink(struct inode *inode)
-+{
-+      int ea_blocks = inode->u.ext3_i.i_file_acl ?
-+              (inode->i_sb->s_blocksize >> 9) : 0;
-+
-+      return (S_ISLNK(inode->i_mode) &&
-+              inode->i_blocks - ea_blocks == 0);
-+}
-+
- /* The ext3 forget function must perform a revoke if we are freeing data
-  * which has been journaled.  Metadata (eg. indirect blocks) must be
-  * revoked in all cases. 
-@@ -48,7 +60,7 @@
-  * still needs to be revoked.
-  */
--static int ext3_forget(handle_t *handle, int is_metadata,
-+int ext3_forget(handle_t *handle, int is_metadata,
-                      struct inode *inode, struct buffer_head *bh,
-                      int blocknr)
- {
-@@ -164,9 +176,7 @@ void ext3_delete_inode (struct inode * i
- {
-       handle_t *handle;
-       
--      if (is_bad_inode(inode) ||
--          inode->i_ino == EXT3_ACL_IDX_INO ||
--          inode->i_ino == EXT3_ACL_DATA_INO)
-+      if (is_bad_inode(inode))
-               goto no_delete;
-       lock_kernel();
-@@ -1855,6 +1865,8 @@ void ext3_truncate(struct inode * inode)
-       if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
-           S_ISLNK(inode->i_mode)))
-               return;
-+      if (ext3_inode_is_fast_symlink(inode))
-+              return;
-       if (IS_APPEND(inode) || IS_IMMUTABLE(inode))
-               return;
-@@ -2002,8 +2014,6 @@ int ext3_get_inode_loc (struct inode *in
-       struct ext3_group_desc * gdp;
-               
-       if ((inode->i_ino != EXT3_ROOT_INO &&
--              inode->i_ino != EXT3_ACL_IDX_INO &&
--              inode->i_ino != EXT3_ACL_DATA_INO &&
-               inode->i_ino != EXT3_JOURNAL_INO &&
-               inode->i_ino < EXT3_FIRST_INO(inode->i_sb)) ||
-               inode->i_ino > le32_to_cpu(
-@@ -2130,10 +2140,7 @@ void ext3_read_inode(struct inode * inod
-       brelse (iloc.bh);
--      if (inode->i_ino == EXT3_ACL_IDX_INO ||
--          inode->i_ino == EXT3_ACL_DATA_INO)
--              /* Nothing to do */ ;
--      else if (S_ISREG(inode->i_mode)) {
-+      if (S_ISREG(inode->i_mode)) {
-               inode->i_op = &ext3_file_inode_operations;
-               inode->i_fop = &ext3_file_operations;
-               inode->i_mapping->a_ops = &ext3_aops;
-@@ -2141,15 +2148,17 @@ void ext3_read_inode(struct inode * inod
-               inode->i_op = &ext3_dir_inode_operations;
-               inode->i_fop = &ext3_dir_operations;
-       } else if (S_ISLNK(inode->i_mode)) {
--              if (!inode->i_blocks)
-+              if (ext3_inode_is_fast_symlink(inode))
-                       inode->i_op = &ext3_fast_symlink_inode_operations;
-               else {
--                      inode->i_op = &page_symlink_inode_operations;
-+                      inode->i_op = &ext3_symlink_inode_operations;
-                       inode->i_mapping->a_ops = &ext3_aops;
-               }
--      } else 
-+      } else {
-+              inode->i_op = &ext3_special_inode_operations;
-               init_special_inode(inode, inode->i_mode,
-                                  le32_to_cpu(iloc.raw_inode->i_block[0]));
-+      }
-       ext3_set_inode_flags(inode);
-       return;
-       
---- linux-2.4.20/fs/ext3/namei.c~linux-2.4.20-xattr-0.8.54     2003-05-05 19:01:05.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/namei.c  2003-05-07 18:08:03.000000000 +0800
-@@ -29,6 +29,7 @@
- #include <linux/sched.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/fcntl.h>
- #include <linux/stat.h>
- #include <linux/string.h>
-@@ -1611,7 +1612,7 @@ static int ext3_mkdir(struct inode * dir
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
--      inode = ext3_new_inode (handle, dir, S_IFDIR);
-+      inode = ext3_new_inode (handle, dir, S_IFDIR | mode);
-       err = PTR_ERR(inode);
-       if (IS_ERR(inode))
-               goto out_stop;
-@@ -1619,7 +1620,6 @@ static int ext3_mkdir(struct inode * dir
-       inode->i_op = &ext3_dir_inode_operations;
-       inode->i_fop = &ext3_dir_operations;
-       inode->i_size = EXT3_I(inode)->i_disksize = inode->i_sb->s_blocksize;
--      inode->i_blocks = 0;    
-       dir_block = ext3_bread (handle, inode, 0, 1, &err);
-       if (!dir_block) {
-               inode->i_nlink--; /* is this nlink == 0? */
-@@ -1646,9 +1646,6 @@ static int ext3_mkdir(struct inode * dir
-       BUFFER_TRACE(dir_block, "call ext3_journal_dirty_metadata");
-       ext3_journal_dirty_metadata(handle, dir_block);
-       brelse (dir_block);
--      inode->i_mode = S_IFDIR | mode;
--      if (dir->i_mode & S_ISGID)
--              inode->i_mode |= S_ISGID;
-       ext3_mark_inode_dirty(handle, inode);
-       err = ext3_add_entry (handle, dentry, inode);
-       if (err) {
-@@ -2017,7 +2014,7 @@ static int ext3_symlink (struct inode * 
-               goto out_stop;
-       if (l > sizeof (EXT3_I(inode)->i_data)) {
--              inode->i_op = &page_symlink_inode_operations;
-+              inode->i_op = &ext3_symlink_inode_operations;
-               inode->i_mapping->a_ops = &ext3_aops;
-               /*
-                * block_symlink() calls back into ext3_prepare/commit_write.
-@@ -2244,4 +2241,16 @@ struct inode_operations ext3_dir_inode_o
-       rmdir:          ext3_rmdir,             /* BKL held */
-       mknod:          ext3_mknod,             /* BKL held */
-       rename:         ext3_rename,            /* BKL held */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
-+
-+struct inode_operations ext3_special_inode_operations = {
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
-+};
-+
---- linux-2.4.20/fs/ext3/super.c~linux-2.4.20-xattr-0.8.54     2003-05-05 19:01:02.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/super.c  2003-05-07 18:08:39.000000000 +0800
-@@ -24,6 +24,7 @@
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/slab.h>
- #include <linux/init.h>
- #include <linux/locks.h>
-@@ -404,6 +405,7 @@ void ext3_put_super (struct super_block 
-       kdev_t j_dev = sbi->s_journal->j_dev;
-       int i;
-+      ext3_xattr_put_super(sb);
-       journal_destroy(sbi->s_journal);
-       if (!(sb->s_flags & MS_RDONLY)) {
-               EXT3_CLEAR_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_RECOVER);
-@@ -499,6 +501,7 @@ static int parse_options (char * options
-                         int is_remount)
- {
-       unsigned long *mount_options = &sbi->s_mount_opt;
-+      
-       uid_t *resuid = &sbi->s_resuid;
-       gid_t *resgid = &sbi->s_resgid;
-       char * this_char;
-@@ -511,6 +514,13 @@ static int parse_options (char * options
-            this_char = strtok (NULL, ",")) {
-               if ((value = strchr (this_char, '=')) != NULL)
-                       *value++ = 0;
-+#ifdef CONFIG_EXT3_FS_XATTR_USER
-+              if (!strcmp (this_char, "user_xattr"))
-+                      set_opt (*mount_options, XATTR_USER);
-+              else if (!strcmp (this_char, "nouser_xattr"))
-+                      clear_opt (*mount_options, XATTR_USER);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -928,6 +938,12 @@ struct super_block * ext3_read_super (st
-       sbi->s_mount_opt = 0;
-       sbi->s_resuid = EXT3_DEF_RESUID;
-       sbi->s_resgid = EXT3_DEF_RESGID;
-+
-+      /* Default extended attribute flags */
-+#ifdef CONFIG_EXT3_FS_XATTR_USER
-+      /* set_opt(sbi->s_mount_opt, XATTR_USER); */
-+#endif
-+
-       if (!parse_options ((char *) data, &sb_block, sbi, &journal_inum, 0)) {
-               sb->s_dev = 0;
-               goto out_fail;
-@@ -1767,17 +1783,29 @@ static DECLARE_FSTYPE_DEV(ext3_fs_type, 
- static int __init init_ext3_fs(void)
- {
--        return register_filesystem(&ext3_fs_type);
-+      int error = init_ext3_xattr();
-+      if (error)
-+              return error;
-+      error = init_ext3_xattr_user();
-+      if (error)
-+              goto fail;
-+      error = register_filesystem(&ext3_fs_type);
-+      if (!error)
-+              return 0;
-+      
-+      exit_ext3_xattr_user();
-+fail:
-+      exit_ext3_xattr();
-+      return error;
- }
- static void __exit exit_ext3_fs(void)
- {
-       unregister_filesystem(&ext3_fs_type);
-+      exit_ext3_xattr_user();
-+      exit_ext3_xattr();
- }
--EXPORT_SYMBOL(ext3_force_commit);
--EXPORT_SYMBOL(ext3_bread);
--
- MODULE_AUTHOR("Remy Card, Stephen Tweedie, Andrew Morton, Andreas Dilger, Theodore Ts'o and others");
- MODULE_DESCRIPTION("Second Extended Filesystem with journaling extensions");
- MODULE_LICENSE("GPL");
---- linux-2.4.20/fs/ext3/symlink.c~linux-2.4.20-xattr-0.8.54   2001-11-10 06:25:04.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/symlink.c        2003-05-07 18:08:03.000000000 +0800
-@@ -20,6 +20,7 @@
- #include <linux/fs.h>
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
- static int ext3_readlink(struct dentry *dentry, char *buffer, int buflen)
- {
-@@ -33,7 +34,20 @@ static int ext3_follow_link(struct dentr
-       return vfs_follow_link(nd, s);
- }
-+struct inode_operations ext3_symlink_inode_operations = {
-+      readlink:       page_readlink,          /* BKL not held.  Don't need */
-+      follow_link:    page_follow_link,       /* BKL not held.  Don't need */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
-+};
-+
- struct inode_operations ext3_fast_symlink_inode_operations = {
-       readlink:       ext3_readlink,          /* BKL not held.  Don't need */
-       follow_link:    ext3_follow_link,       /* BKL not held.  Don't need */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/xattr.c  2003-05-07 18:09:23.000000000 +0800
-@@ -0,0 +1,1225 @@
-+/*
-+ * linux/fs/ext3/xattr.c
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ *
-+ * Fix by Harrison Xing <harrison@mountainviewdata.com>.
-+ * Ext3 code with a lot of help from Eric Jarman <ejarman@acm.org>.
-+ * Extended attributes for symlinks and special files added per
-+ *  suggestion of Luka Renko <luka.renko@hermes.si>.
-+ */
-+
-+/*
-+ * Extended attributes are stored on disk blocks allocated outside of
-+ * any inode. The i_file_acl field is then made to point to this allocated
-+ * block. If all extended attributes of an inode are identical, these
-+ * inodes may share the same extended attribute block. Such situations
-+ * are automatically detected by keeping a cache of recent attribute block
-+ * numbers and hashes over the block's contents in memory.
-+ *
-+ *
-+ * Extended attribute block layout:
-+ *
-+ *   +------------------+
-+ *   | header           |
-+ *   | entry 1          | |
-+ *   | entry 2          | | growing downwards
-+ *   | entry 3          | v
-+ *   | four null bytes  |
-+ *   | . . .            |
-+ *   | value 1          | ^
-+ *   | value 3          | | growing upwards
-+ *   | value 2          | |
-+ *   +------------------+
-+ *
-+ * The block header is followed by multiple entry descriptors. These entry
-+ * descriptors are variable in size, and alligned to EXT3_XATTR_PAD
-+ * byte boundaries. The entry descriptors are sorted by attribute name,
-+ * so that two extended attribute blocks can be compared efficiently.
-+ *
-+ * Attribute values are aligned to the end of the block, stored in
-+ * no specific order. They are also padded to EXT3_XATTR_PAD byte
-+ * boundaries. No additional gaps are left between them.
-+ *
-+ * Locking strategy
-+ * ----------------
-+ * The VFS already holds the BKL and the inode->i_sem semaphore when any of
-+ * the xattr inode operations are called, so we are guaranteed that only one
-+ * processes accesses extended attributes of an inode at any time.
-+ *
-+ * For writing we also grab the ext3_xattr_sem semaphore. This ensures that
-+ * only a single process is modifying an extended attribute block, even
-+ * if the block is shared among inodes.
-+ *
-+ * Note for porting to 2.5
-+ * -----------------------
-+ * The BKL will no longer be held in the xattr inode operations.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/fs.h>
-+#include <linux/locks.h>
-+#include <linux/slab.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
-+#include <linux/mbcache.h>
-+#include <linux/quotaops.h>
-+#include <asm/semaphore.h>
-+#include <linux/compatmac.h>
-+
-+#define EXT3_EA_USER "user."
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+# define mark_buffer_dirty(bh) mark_buffer_dirty(bh, 1)
-+#endif
-+
-+#define HDR(bh) ((struct ext3_xattr_header *)((bh)->b_data))
-+#define ENTRY(ptr) ((struct ext3_xattr_entry *)(ptr))
-+#define FIRST_ENTRY(bh) ENTRY(HDR(bh)+1)
-+#define IS_LAST_ENTRY(entry) (*(__u32 *)(entry) == 0)
-+
-+#ifdef EXT3_XATTR_DEBUG
-+# define ea_idebug(inode, f...) do { \
-+              printk(KERN_DEBUG "inode %s:%ld: ", \
-+                      kdevname(inode->i_dev), inode->i_ino); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+# define ea_bdebug(bh, f...) do { \
-+              printk(KERN_DEBUG "block %s:%ld: ", \
-+                      kdevname(bh->b_dev), bh->b_blocknr); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+#else
-+# define ea_idebug(f...)
-+# define ea_bdebug(f...)
-+#endif
-+
-+static int ext3_xattr_set2(handle_t *, struct inode *, struct buffer_head *,
-+                         struct ext3_xattr_header *);
-+
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+
-+static int ext3_xattr_cache_insert(struct buffer_head *);
-+static struct buffer_head *ext3_xattr_cache_find(struct inode *,
-+                                               struct ext3_xattr_header *);
-+static void ext3_xattr_cache_remove(struct buffer_head *);
-+static void ext3_xattr_rehash(struct ext3_xattr_header *,
-+                            struct ext3_xattr_entry *);
-+
-+static struct mb_cache *ext3_xattr_cache;
-+
-+#else
-+# define ext3_xattr_cache_insert(bh) 0
-+# define ext3_xattr_cache_find(inode, header) NULL
-+# define ext3_xattr_cache_remove(bh) while(0) {}
-+# define ext3_xattr_rehash(header, entry) while(0) {}
-+#endif
-+
-+/*
-+ * If a file system does not share extended attributes among inodes,
-+ * we should not need the ext3_xattr_sem semaphore. However, the
-+ * filesystem may still contain shared blocks, so we always take
-+ * the lock.
-+ */
-+
-+DECLARE_MUTEX(ext3_xattr_sem);
-+
-+static inline int
-+ext3_xattr_new_block(handle_t *handle, struct inode *inode,
-+                   int * errp, int force)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      int goal = le32_to_cpu(EXT3_SB(sb)->s_es->s_first_data_block) +
-+              EXT3_I(inode)->i_block_group * EXT3_BLOCKS_PER_GROUP(sb);
-+
-+      /* How can we enforce the allocation? */
-+      int block = ext3_new_block(handle, inode, goal, 0, 0, errp);
-+#ifdef OLD_QUOTAS
-+      if (!*errp)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#endif
-+      return block;
-+}
-+
-+static inline int
-+ext3_xattr_quota_alloc(struct inode *inode, int force)
-+{
-+      /* How can we enforce the allocation? */
-+#ifdef OLD_QUOTAS
-+      int error = DQUOT_ALLOC_BLOCK(inode->i_sb, inode, 1);
-+      if (!error)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#else
-+      int error = DQUOT_ALLOC_BLOCK(inode, 1);
-+#endif
-+      return error;
-+}
-+
-+#ifdef OLD_QUOTAS
-+
-+static inline void
-+ext3_xattr_quota_free(struct inode *inode)
-+{
-+      DQUOT_FREE_BLOCK(inode->i_sb, inode, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+static inline void
-+ext3_xattr_free_block(handle_t *handle, struct inode * inode,
-+                    unsigned long block)
-+{
-+      ext3_free_blocks(handle, inode, block, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+#else
-+# define ext3_xattr_quota_free(inode) \
-+      DQUOT_FREE_BLOCK(inode, 1)
-+# define ext3_xattr_free_block(handle, inode, block) \
-+      ext3_free_blocks(handle, inode, block, 1)
-+#endif
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,18)
-+
-+static inline struct buffer_head *
-+sb_bread(struct super_block *sb, int block)
-+{
-+      return bread(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+static inline struct buffer_head *
-+sb_getblk(struct super_block *sb, int block)
-+{
-+      return getblk(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+#endif
-+
-+struct ext3_xattr_handler *ext3_xattr_handlers[EXT3_XATTR_INDEX_MAX];
-+rwlock_t ext3_handler_lock = RW_LOCK_UNLOCKED;
-+
-+int
-+ext3_xattr_register(int name_index, struct ext3_xattr_handler *handler)
-+{
-+      int error = -EINVAL;
-+
-+      if (name_index > 0 && name_index <= EXT3_XATTR_INDEX_MAX) {
-+              write_lock(&ext3_handler_lock);
-+              if (!ext3_xattr_handlers[name_index-1]) {
-+                      ext3_xattr_handlers[name_index-1] = handler;
-+                      error = 0;
-+              }
-+              write_unlock(&ext3_handler_lock);
-+      }
-+      return error;
-+}
-+
-+void
-+ext3_xattr_unregister(int name_index, struct ext3_xattr_handler *handler)
-+{
-+      if (name_index > 0 || name_index <= EXT3_XATTR_INDEX_MAX) {
-+              write_lock(&ext3_handler_lock);
-+              ext3_xattr_handlers[name_index-1] = NULL;
-+              write_unlock(&ext3_handler_lock);
-+      }
-+}
-+
-+static inline const char *
-+strcmp_prefix(const char *a, const char *a_prefix)
-+{
-+      while (*a_prefix && *a == *a_prefix) {
-+              a++;
-+              a_prefix++;
-+      }
-+      return *a_prefix ? NULL : a;
-+}
-+
-+/*
-+ * Decode the extended attribute name, and translate it into
-+ * the name_index and name suffix.
-+ */
-+static inline struct ext3_xattr_handler *
-+ext3_xattr_resolve_name(const char **name)
-+{
-+      struct ext3_xattr_handler *handler = NULL;
-+      int i;
-+
-+      if (!*name)
-+              return NULL;
-+      read_lock(&ext3_handler_lock);
-+      for (i=0; i<EXT3_XATTR_INDEX_MAX; i++) {
-+              if (ext3_xattr_handlers[i]) {
-+                      const char *n = strcmp_prefix(*name,
-+                              ext3_xattr_handlers[i]->prefix);
-+                      if (n) {
-+                              handler = ext3_xattr_handlers[i];
-+                              *name = n;
-+                              break;
-+                      }
-+              }
-+      }
-+      read_unlock(&ext3_handler_lock);
-+      return handler;
-+}
-+
-+static inline struct ext3_xattr_handler *
-+ext3_xattr_handler(int name_index)
-+{
-+      struct ext3_xattr_handler *handler = NULL;
-+      if (name_index > 0 && name_index <= EXT3_XATTR_INDEX_MAX) {
-+              read_lock(&ext3_handler_lock);
-+              handler = ext3_xattr_handlers[name_index-1];
-+              read_unlock(&ext3_handler_lock);
-+      }
-+      return handler;
-+}
-+
-+/*
-+ * Inode operation getxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext3_getxattr(struct dentry *dentry, const char *name,
-+            void *buffer, size_t size)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->get(inode, name, buffer, size);
-+}
-+
-+/*
-+ * Inode operation listxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext3_listxattr(struct dentry *dentry, char *buffer, size_t size)
-+{
-+      return ext3_xattr_list(dentry->d_inode, buffer, size);
-+}
-+
-+/*
-+ * Inode operation setxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext3_setxattr(struct dentry *dentry, const char *name,
-+            const void *value, size_t size, int flags)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      if (size == 0)
-+              value = "";  /* empty EA, do not remove */
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, value, size, flags);
-+}
-+
-+/*
-+ * Inode operation removexattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext3_removexattr(struct dentry *dentry, const char *name)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, NULL, 0, XATTR_REPLACE);
-+}
-+
-+/*
-+ * ext3_xattr_get()
-+ *
-+ * Copy an extended attribute into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext3_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_entry *entry;
-+      unsigned int block, size;
-+      char *end;
-+      int name_len, error;
-+
-+      ea_idebug(inode, "name=%d.%s, buffer=%p, buffer_size=%ld",
-+                name_index, name, buffer, (long)buffer_size);
-+
-+      if (name == NULL)
-+              return -EINVAL;
-+      if (!EXT3_I(inode)->i_file_acl)
-+              return -ENOATTR;
-+      block = EXT3_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext3_error(inode->i_sb, "ext3_xattr_get",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* find named attribute */
-+      name_len = strlen(name);
-+
-+      error = -ERANGE;
-+      if (name_len > 255)
-+              goto cleanup;
-+      entry = FIRST_ENTRY(bh);
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              if (name_index == entry->e_name_index &&
-+                  name_len == entry->e_name_len &&
-+                  memcmp(name, entry->e_name, name_len) == 0)
-+                      goto found;
-+              entry = next;
-+      }
-+      /* Check the remaining name entries */
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              entry = next;
-+      }
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      error = -ENOATTR;
-+      goto cleanup;
-+found:
-+      /* check the buffer size */
-+      if (entry->e_value_block != 0)
-+              goto bad_block;
-+      size = le32_to_cpu(entry->e_value_size);
-+      if (size > inode->i_sb->s_blocksize ||
-+          le16_to_cpu(entry->e_value_offs) + size > inode->i_sb->s_blocksize)
-+              goto bad_block;
-+
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (buffer) {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+              /* return value of attribute */
-+              memcpy(buffer, bh->b_data + le16_to_cpu(entry->e_value_offs),
-+                      size);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_list()
-+ *
-+ * Copy a list of attribute names into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext3_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_entry *entry;
-+      unsigned int block, size = 0;
-+      char *buf, *end;
-+      int error;
-+
-+      ea_idebug(inode, "buffer=%p, buffer_size=%ld",
-+                buffer, (long)buffer_size);
-+
-+      if (!EXT3_I(inode)->i_file_acl)
-+              return 0;
-+      block = EXT3_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext3_error(inode->i_sb, "ext3_xattr_list",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* compute the size required for the list of attribute names */
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT3_XATTR_NEXT(entry)) {
-+              struct ext3_xattr_handler *handler;
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+
-+              handler = ext3_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      size += handler->list(NULL, inode, entry->e_name,
-+                                            entry->e_name_len);
-+      }
-+
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (!buffer) {
-+              error = size;
-+              goto cleanup;
-+      } else {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+      }
-+
-+      /* list the attribute names */
-+      buf = buffer;
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT3_XATTR_NEXT(entry)) {
-+              struct ext3_xattr_handler *handler;
-+
-+              handler = ext3_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      buf += handler->list(buf, inode, entry->e_name,
-+                                           entry->e_name_len);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * If the EXT3_FEATURE_COMPAT_EXT_ATTR feature of this file system is
-+ * not set, set it.
-+ */
-+static void ext3_xattr_update_super_block(handle_t *handle,
-+                                        struct super_block *sb)
-+{
-+      if (EXT3_HAS_COMPAT_FEATURE(sb, EXT3_FEATURE_COMPAT_EXT_ATTR))
-+              return;
-+
-+      lock_super(sb);
-+      ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+      EXT3_SB(sb)->s_feature_compat |= EXT3_FEATURE_COMPAT_EXT_ATTR;
-+#endif
-+      EXT3_SB(sb)->s_es->s_feature_compat |=
-+              cpu_to_le32(EXT3_FEATURE_COMPAT_EXT_ATTR);
-+      sb->s_dirt = 1;
-+      ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
-+      unlock_super(sb);
-+}
-+
-+/*
-+ * ext3_xattr_set()
-+ *
-+ * Create, replace or remove an extended attribute for this inode. Buffer
-+ * is NULL to remove an existing extended attribute, and non-NULL to
-+ * either replace an existing extended attribute, or create a new extended
-+ * attribute. The flags XATTR_REPLACE and XATTR_CREATE
-+ * specify that an extended attribute must exist and must not exist
-+ * previous to the call, respectively.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+int
-+ext3_xattr_set(handle_t *handle, struct inode *inode, int name_index,
-+             const char *name, const void *value, size_t value_len, int flags)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_header *header = NULL;
-+      struct ext3_xattr_entry *here, *last;
-+      unsigned int name_len;
-+      int block = EXT3_I(inode)->i_file_acl;
-+      int min_offs = sb->s_blocksize, not_found = 1, free, error;
-+      char *end;
-+      
-+      /*
-+       * header -- Points either into bh, or to a temporarily
-+       *           allocated buffer.
-+       * here -- The named entry found, or the place for inserting, within
-+       *         the block pointed to by header.
-+       * last -- Points right after the last named entry within the block
-+       *         pointed to by header.
-+       * min_offs -- The offset of the first value (values are aligned
-+       *             towards the end of the block).
-+       * end -- Points right after the block pointed to by header.
-+       */
-+      
-+      ea_idebug(inode, "name=%d.%s, value=%p, value_len=%ld",
-+                name_index, name, value, (long)value_len);
-+
-+      if (IS_RDONLY(inode))
-+              return -EROFS;
-+      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-+              return -EPERM;
-+      if (value == NULL)
-+              value_len = 0;
-+      if (name == NULL)
-+              return -EINVAL;
-+      name_len = strlen(name);
-+      if (name_len > 255 || value_len > sb->s_blocksize)
-+              return -ERANGE;
-+      down(&ext3_xattr_sem);
-+
-+      if (block) {
-+              /* The inode already has an extended attribute block. */
-+              bh = sb_bread(sb, block);
-+              error = -EIO;
-+              if (!bh)
-+                      goto cleanup;
-+              ea_bdebug(bh, "b_count=%d, refcount=%d",
-+                      atomic_read(&(bh->b_count)),
-+                      le32_to_cpu(HDR(bh)->h_refcount));
-+              header = HDR(bh);
-+              end = bh->b_data + bh->b_size;
-+              if (header->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+                  header->h_blocks != cpu_to_le32(1)) {
-+bad_block:            ext3_error(sb, "ext3_xattr_set",
-+                              "inode %ld: bad block %d", inode->i_ino, block);
-+                      error = -EIO;
-+                      goto cleanup;
-+              }
-+              /* Find the named attribute. */
-+              here = FIRST_ENTRY(bh);
-+              while (!IS_LAST_ENTRY(here)) {
-+                      struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(here);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!here->e_value_block && here->e_value_size) {
-+                              int offs = le16_to_cpu(here->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      not_found = name_index - here->e_name_index;
-+                      if (!not_found)
-+                              not_found = name_len - here->e_name_len;
-+                      if (!not_found)
-+                              not_found = memcmp(name, here->e_name,name_len);
-+                      if (not_found <= 0)
-+                              break;
-+                      here = next;
-+              }
-+              last = here;
-+              /* We still need to compute min_offs and last. */
-+              while (!IS_LAST_ENTRY(last)) {
-+                      struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(last);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!last->e_value_block && last->e_value_size) {
-+                              int offs = le16_to_cpu(last->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      last = next;
-+              }
-+
-+              /* Check whether we have enough space left. */
-+              free = min_offs - ((char*)last - (char*)header) - sizeof(__u32);
-+      } else {
-+              /* We will use a new extended attribute block. */
-+              free = sb->s_blocksize -
-+                      sizeof(struct ext3_xattr_header) - sizeof(__u32);
-+              here = last = NULL;  /* avoid gcc uninitialized warning. */
-+      }
-+
-+      if (not_found) {
-+              /* Request to remove a nonexistent attribute? */
-+              error = -ENOATTR;
-+              if (flags & XATTR_REPLACE)
-+                      goto cleanup;
-+              error = 0;
-+              if (value == NULL)
-+                      goto cleanup;
-+              else
-+                      free -= EXT3_XATTR_LEN(name_len);
-+      } else {
-+              /* Request to create an existing attribute? */
-+              error = -EEXIST;
-+              if (flags & XATTR_CREATE)
-+                      goto cleanup;
-+              if (!here->e_value_block && here->e_value_size) {
-+                      unsigned int size = le32_to_cpu(here->e_value_size);
-+
-+                      if (le16_to_cpu(here->e_value_offs) + size > 
-+                          sb->s_blocksize || size > sb->s_blocksize)
-+                              goto bad_block;
-+                      free += EXT3_XATTR_SIZE(size);
-+              }
-+      }
-+      free -= EXT3_XATTR_SIZE(value_len);
-+      error = -ENOSPC;
-+      if (free < 0)
-+              goto cleanup;
-+
-+      /* Here we know that we can set the new attribute. */
-+
-+      if (header) {
-+              if (header->h_refcount == cpu_to_le32(1)) {
-+                      ea_bdebug(bh, "modifying in-place");
-+                      ext3_xattr_cache_remove(bh);
-+                      error = ext3_journal_get_write_access(handle, bh);
-+                      if (error)
-+                              goto cleanup;
-+              } else {
-+                      int offset;
-+
-+                      ea_bdebug(bh, "cloning");
-+                      header = kmalloc(bh->b_size, GFP_KERNEL);
-+                      error = -ENOMEM;
-+                      if (header == NULL)
-+                              goto cleanup;
-+                      memcpy(header, HDR(bh), bh->b_size);
-+                      header->h_refcount = cpu_to_le32(1);
-+                      offset = (char *)header - bh->b_data;
-+                      here = ENTRY((char *)here + offset);
-+                      last = ENTRY((char *)last + offset);
-+              }
-+      } else {
-+              /* Allocate a buffer where we construct the new block. */
-+              header = kmalloc(sb->s_blocksize, GFP_KERNEL);
-+              error = -ENOMEM;
-+              if (header == NULL)
-+                      goto cleanup;
-+              memset(header, 0, sb->s_blocksize);
-+              end = (char *)header + sb->s_blocksize;
-+              header->h_magic = cpu_to_le32(EXT3_XATTR_MAGIC);
-+              header->h_blocks = header->h_refcount = cpu_to_le32(1);
-+              last = here = ENTRY(header+1);
-+      }
-+
-+      if (not_found) {
-+              /* Insert the new name. */
-+              int size = EXT3_XATTR_LEN(name_len);
-+              int rest = (char *)last - (char *)here;
-+              memmove((char *)here + size, here, rest);
-+              memset(here, 0, size);
-+              here->e_name_index = name_index;
-+              here->e_name_len = name_len;
-+              memcpy(here->e_name, name, name_len);
-+      } else {
-+              /* Remove the old value. */
-+              if (!here->e_value_block && here->e_value_size) {
-+                      char *first_val = (char *)header + min_offs;
-+                      int offs = le16_to_cpu(here->e_value_offs);
-+                      char *val = (char *)header + offs;
-+                      size_t size = EXT3_XATTR_SIZE(
-+                              le32_to_cpu(here->e_value_size));
-+                      memmove(first_val + size, first_val, val - first_val);
-+                      memset(first_val, 0, size);
-+                      here->e_value_offs = 0;
-+                      min_offs += size;
-+
-+                      /* Adjust all value offsets. */
-+                      last = ENTRY(header+1);
-+                      while (!IS_LAST_ENTRY(last)) {
-+                              int o = le16_to_cpu(last->e_value_offs);
-+                              if (!last->e_value_block && o < offs)
-+                                      last->e_value_offs =
-+                                              cpu_to_le16(o + size);
-+                              last = EXT3_XATTR_NEXT(last);
-+                      }
-+              }
-+              if (value == NULL) {
-+                      /* Remove this attribute. */
-+                      if (EXT3_XATTR_NEXT(ENTRY(header+1)) == last) {
-+                              /* This block is now empty. */
-+                              error = ext3_xattr_set2(handle, inode, bh,NULL);
-+                              goto cleanup;
-+                      } else {
-+                              /* Remove the old name. */
-+                              int size = EXT3_XATTR_LEN(name_len);
-+                              last = ENTRY((char *)last - size);
-+                              memmove(here, (char*)here + size,
-+                                      (char*)last - (char*)here);
-+                              memset(last, 0, size);
-+                      }
-+              }
-+      }
-+
-+      if (value != NULL) {
-+              /* Insert the new value. */
-+              here->e_value_size = cpu_to_le32(value_len);
-+              if (value_len) {
-+                      size_t size = EXT3_XATTR_SIZE(value_len);
-+                      char *val = (char *)header + min_offs - size;
-+                      here->e_value_offs =
-+                              cpu_to_le16((char *)val - (char *)header);
-+                      memset(val + size - EXT3_XATTR_PAD, 0,
-+                             EXT3_XATTR_PAD); /* Clear the pad bytes. */
-+                      memcpy(val, value, value_len);
-+              }
-+      }
-+      ext3_xattr_rehash(header, here);
-+
-+      error = ext3_xattr_set2(handle, inode, bh, header);
-+
-+cleanup:
-+      brelse(bh);
-+      if (!(bh && header == HDR(bh)))
-+              kfree(header);
-+      up(&ext3_xattr_sem);
-+
-+      return error;
-+}
-+
-+/*
-+ * Second half of ext3_xattr_set(): Update the file system.
-+ */
-+static int
-+ext3_xattr_set2(handle_t *handle, struct inode *inode,
-+              struct buffer_head *old_bh, struct ext3_xattr_header *header)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *new_bh = NULL;
-+      int error;
-+
-+      if (header) {
-+              new_bh = ext3_xattr_cache_find(inode, header);
-+              if (new_bh) {
-+                      /*
-+                       * We found an identical block in the cache.
-+                       * The old block will be released after updating
-+                       * the inode.
-+                       */
-+                      ea_bdebug(old_bh, "reusing block %ld",
-+                              new_bh->b_blocknr);
-+                      
-+                      error = -EDQUOT;
-+                      if (ext3_xattr_quota_alloc(inode, 1))
-+                              goto cleanup;
-+                      
-+                      error = ext3_journal_get_write_access(handle, new_bh);
-+                      if (error)
-+                              goto cleanup;
-+                      HDR(new_bh)->h_refcount = cpu_to_le32(
-+                              le32_to_cpu(HDR(new_bh)->h_refcount) + 1);
-+                      ea_bdebug(new_bh, "refcount now=%d",
-+                              le32_to_cpu(HDR(new_bh)->h_refcount));
-+              } else if (old_bh && header == HDR(old_bh)) {
-+                      /* Keep this block. */
-+                      new_bh = old_bh;
-+                      (void)ext3_xattr_cache_insert(new_bh);
-+              } else {
-+                      /* We need to allocate a new block */
-+                      int force = EXT3_I(inode)->i_file_acl != 0;
-+                      int block = ext3_xattr_new_block(handle, inode,
-+                                                       &error, force);
-+                      if (error)
-+                              goto cleanup;
-+                      ea_idebug(inode, "creating block %d", block);
-+
-+                      new_bh = sb_getblk(sb, block);
-+                      if (!new_bh) {
-+getblk_failed:                        ext3_xattr_free_block(handle, inode, block);
-+                              error = -EIO;
-+                              goto cleanup;
-+                      }
-+                      lock_buffer(new_bh);
-+                      error = ext3_journal_get_create_access(handle, new_bh);
-+                      if (error) {
-+                              unlock_buffer(new_bh);
-+                              goto getblk_failed;
-+                      }
-+                      memcpy(new_bh->b_data, header, new_bh->b_size);
-+                      mark_buffer_uptodate(new_bh, 1);
-+                      unlock_buffer(new_bh);
-+                      (void)ext3_xattr_cache_insert(new_bh);
-+                      
-+                      ext3_xattr_update_super_block(handle, sb);
-+              }
-+              error = ext3_journal_dirty_metadata(handle, new_bh);
-+              if (error)
-+                      goto cleanup;
-+      }
-+
-+      /* Update the inode. */
-+      EXT3_I(inode)->i_file_acl = new_bh ? new_bh->b_blocknr : 0;
-+      inode->i_ctime = CURRENT_TIME;
-+      ext3_mark_inode_dirty(handle, inode);
-+      if (IS_SYNC(inode))
-+              handle->h_sync = 1;
-+
-+      error = 0;
-+      if (old_bh && old_bh != new_bh) {
-+              /*
-+               * If there was an old block, and we are not still using it,
-+               * we now release the old block.
-+              */
-+              unsigned int refcount = le32_to_cpu(HDR(old_bh)->h_refcount);
-+
-+              error = ext3_journal_get_write_access(handle, old_bh);
-+              if (error)
-+                      goto cleanup;
-+              if (refcount == 1) {
-+                      /* Free the old block. */
-+                      ea_bdebug(old_bh, "freeing");
-+                      ext3_xattr_free_block(handle, inode, old_bh->b_blocknr);
-+
-+                      /* ext3_forget() calls bforget() for us, but we
-+                         let our caller release old_bh, so we need to
-+                         duplicate the handle before. */
-+                      get_bh(old_bh);
-+                      ext3_forget(handle, 1, inode, old_bh,old_bh->b_blocknr);
-+              } else {
-+                      /* Decrement the refcount only. */
-+                      refcount--;
-+                      HDR(old_bh)->h_refcount = cpu_to_le32(refcount);
-+                      ext3_xattr_quota_free(inode);
-+                      ext3_journal_dirty_metadata(handle, old_bh);
-+                      ea_bdebug(old_bh, "refcount now=%d", refcount);
-+              }
-+      }
-+
-+cleanup:
-+      if (old_bh != new_bh)
-+              brelse(new_bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_delete_inode()
-+ *
-+ * Free extended attribute resources associated with this inode. This
-+ * is called immediately before an inode is freed.
-+ */
-+void
-+ext3_xattr_delete_inode(handle_t *handle, struct inode *inode)
-+{
-+      struct buffer_head *bh;
-+      unsigned int block = EXT3_I(inode)->i_file_acl;
-+
-+      if (!block)
-+              return;
-+      down(&ext3_xattr_sem);
-+
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh) {
-+              ext3_error(inode->i_sb, "ext3_xattr_delete_inode",
-+                      "inode %ld: block %d read error", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "b_count=%d", atomic_read(&(bh->b_count)));
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+              ext3_error(inode->i_sb, "ext3_xattr_delete_inode",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ext3_journal_get_write_access(handle, bh);
-+      ea_bdebug(bh, "refcount now=%d", le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+      if (HDR(bh)->h_refcount == cpu_to_le32(1)) {
-+              ext3_xattr_cache_remove(bh);
-+              ext3_xattr_free_block(handle, inode, block);
-+              ext3_forget(handle, 1, inode, bh, block);
-+              bh = NULL;
-+      } else {
-+              HDR(bh)->h_refcount = cpu_to_le32(
-+                      le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+              ext3_journal_dirty_metadata(handle, bh);
-+              if (IS_SYNC(inode))
-+                      handle->h_sync = 1;
-+              ext3_xattr_quota_free(inode);
-+      }
-+      EXT3_I(inode)->i_file_acl = 0;
-+
-+cleanup:
-+      brelse(bh);
-+      up(&ext3_xattr_sem);
-+}
-+
-+/*
-+ * ext3_xattr_put_super()
-+ *
-+ * This is called when a file system is unmounted.
-+ */
-+void
-+ext3_xattr_put_super(struct super_block *sb)
-+{
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+      mb_cache_shrink(ext3_xattr_cache, sb->s_dev);
-+#endif
-+}
-+
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+
-+/*
-+ * ext3_xattr_cache_insert()
-+ *
-+ * Create a new entry in the extended attribute cache, and insert
-+ * it unless such an entry is already in the cache.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+static int
-+ext3_xattr_cache_insert(struct buffer_head *bh)
-+{
-+      __u32 hash = le32_to_cpu(HDR(bh)->h_hash);
-+      struct mb_cache_entry *ce;
-+      int error;
-+
-+      ce = mb_cache_entry_alloc(ext3_xattr_cache);
-+      if (!ce)
-+              return -ENOMEM;
-+      error = mb_cache_entry_insert(ce, bh->b_dev, bh->b_blocknr, &hash);
-+      if (error) {
-+              mb_cache_entry_free(ce);
-+              if (error == -EBUSY) {
-+                      ea_bdebug(bh, "already in cache (%d cache entries)",
-+                              atomic_read(&ext3_xattr_cache->c_entry_count));
-+                      error = 0;
-+              }
-+      } else {
-+              ea_bdebug(bh, "inserting [%x] (%d cache entries)", (int)hash,
-+                        atomic_read(&ext3_xattr_cache->c_entry_count));
-+              mb_cache_entry_release(ce);
-+      }
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_cmp()
-+ *
-+ * Compare two extended attribute blocks for equality.
-+ *
-+ * Returns 0 if the blocks are equal, 1 if they differ, and
-+ * a negative error number on errors.
-+ */
-+static int
-+ext3_xattr_cmp(struct ext3_xattr_header *header1,
-+             struct ext3_xattr_header *header2)
-+{
-+      struct ext3_xattr_entry *entry1, *entry2;
-+
-+      entry1 = ENTRY(header1+1);
-+      entry2 = ENTRY(header2+1);
-+      while (!IS_LAST_ENTRY(entry1)) {
-+              if (IS_LAST_ENTRY(entry2))
-+                      return 1;
-+              if (entry1->e_hash != entry2->e_hash ||
-+                  entry1->e_name_len != entry2->e_name_len ||
-+                  entry1->e_value_size != entry2->e_value_size ||
-+                  memcmp(entry1->e_name, entry2->e_name, entry1->e_name_len))
-+                      return 1;
-+              if (entry1->e_value_block != 0 || entry2->e_value_block != 0)
-+                      return -EIO;
-+              if (memcmp((char *)header1 + le16_to_cpu(entry1->e_value_offs),
-+                         (char *)header2 + le16_to_cpu(entry2->e_value_offs),
-+                         le32_to_cpu(entry1->e_value_size)))
-+                      return 1;
-+
-+              entry1 = EXT3_XATTR_NEXT(entry1);
-+              entry2 = EXT3_XATTR_NEXT(entry2);
-+      }
-+      if (!IS_LAST_ENTRY(entry2))
-+              return 1;
-+      return 0;
-+}
-+
-+/*
-+ * ext3_xattr_cache_find()
-+ *
-+ * Find an identical extended attribute block.
-+ *
-+ * Returns a pointer to the block found, or NULL if such a block was
-+ * not found or an error occurred.
-+ */
-+static struct buffer_head *
-+ext3_xattr_cache_find(struct inode *inode, struct ext3_xattr_header *header)
-+{
-+      __u32 hash = le32_to_cpu(header->h_hash);
-+      struct mb_cache_entry *ce;
-+
-+      if (!header->h_hash)
-+              return NULL;  /* never share */
-+      ea_idebug(inode, "looking for cached blocks [%x]", (int)hash);
-+      ce = mb_cache_entry_find_first(ext3_xattr_cache, 0, inode->i_dev, hash);
-+      while (ce) {
-+              struct buffer_head *bh = sb_bread(inode->i_sb, ce->e_block);
-+
-+              if (!bh) {
-+                      ext3_error(inode->i_sb, "ext3_xattr_cache_find",
-+                              "inode %ld: block %ld read error",
-+                              inode->i_ino, ce->e_block);
-+              } else if (le32_to_cpu(HDR(bh)->h_refcount) >
-+                         EXT3_XATTR_REFCOUNT_MAX) {
-+                      ea_idebug(inode, "block %ld refcount %d>%d",ce->e_block,
-+                              le32_to_cpu(HDR(bh)->h_refcount),
-+                              EXT3_XATTR_REFCOUNT_MAX);
-+              } else if (!ext3_xattr_cmp(header, HDR(bh))) {
-+                      ea_bdebug(bh, "b_count=%d",atomic_read(&(bh->b_count)));
-+                      mb_cache_entry_release(ce);
-+                      return bh;
-+              }
-+              brelse(bh);
-+              ce = mb_cache_entry_find_next(ce, 0, inode->i_dev, hash);
-+      }
-+      return NULL;
-+}
-+
-+/*
-+ * ext3_xattr_cache_remove()
-+ *
-+ * Remove the cache entry of a block from the cache. Called when a
-+ * block becomes invalid.
-+ */
-+static void
-+ext3_xattr_cache_remove(struct buffer_head *bh)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      ce = mb_cache_entry_get(ext3_xattr_cache, bh->b_dev, bh->b_blocknr);
-+      if (ce) {
-+              ea_bdebug(bh, "removing (%d cache entries remaining)",
-+                        atomic_read(&ext3_xattr_cache->c_entry_count)-1);
-+              mb_cache_entry_free(ce);
-+      } else 
-+              ea_bdebug(bh, "no cache entry");
-+}
-+
-+#define NAME_HASH_SHIFT 5
-+#define VALUE_HASH_SHIFT 16
-+
-+/*
-+ * ext3_xattr_hash_entry()
-+ *
-+ * Compute the hash of an extended attribute.
-+ */
-+static inline void ext3_xattr_hash_entry(struct ext3_xattr_header *header,
-+                                       struct ext3_xattr_entry *entry)
-+{
-+      __u32 hash = 0;
-+      char *name = entry->e_name;
-+      int n;
-+
-+      for (n=0; n < entry->e_name_len; n++) {
-+              hash = (hash << NAME_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - NAME_HASH_SHIFT)) ^
-+                     *name++;
-+      }
-+
-+      if (entry->e_value_block == 0 && entry->e_value_size != 0) {
-+              __u32 *value = (__u32 *)((char *)header +
-+                      le16_to_cpu(entry->e_value_offs));
-+              for (n = (le32_to_cpu(entry->e_value_size) +
-+                   EXT3_XATTR_ROUND) >> EXT3_XATTR_PAD_BITS; n; n--) {
-+                      hash = (hash << VALUE_HASH_SHIFT) ^
-+                             (hash >> (8*sizeof(hash) - VALUE_HASH_SHIFT)) ^
-+                             le32_to_cpu(*value++);
-+              }
-+      }
-+      entry->e_hash = cpu_to_le32(hash);
-+}
-+
-+#undef NAME_HASH_SHIFT
-+#undef VALUE_HASH_SHIFT
-+
-+#define BLOCK_HASH_SHIFT 16
-+
-+/*
-+ * ext3_xattr_rehash()
-+ *
-+ * Re-compute the extended attribute hash value after an entry has changed.
-+ */
-+static void ext3_xattr_rehash(struct ext3_xattr_header *header,
-+                            struct ext3_xattr_entry *entry)
-+{
-+      struct ext3_xattr_entry *here;
-+      __u32 hash = 0;
-+      
-+      ext3_xattr_hash_entry(header, entry);
-+      here = ENTRY(header+1);
-+      while (!IS_LAST_ENTRY(here)) {
-+              if (!here->e_hash) {
-+                      /* Block is not shared if an entry's hash value == 0 */
-+                      hash = 0;
-+                      break;
-+              }
-+              hash = (hash << BLOCK_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - BLOCK_HASH_SHIFT)) ^
-+                     le32_to_cpu(here->e_hash);
-+              here = EXT3_XATTR_NEXT(here);
-+      }
-+      header->h_hash = cpu_to_le32(hash);
-+}
-+
-+#undef BLOCK_HASH_SHIFT
-+
-+int __init
-+init_ext3_xattr(void)
-+{
-+      ext3_xattr_cache = mb_cache_create("ext3_xattr", NULL,
-+              sizeof(struct mb_cache_entry) +
-+              sizeof(struct mb_cache_entry_index), 1, 61);
-+      if (!ext3_xattr_cache)
-+              return -ENOMEM;
-+
-+      return 0;
-+}
-+
-+void
-+exit_ext3_xattr(void)
-+{
-+      if (ext3_xattr_cache)
-+              mb_cache_destroy(ext3_xattr_cache);
-+      ext3_xattr_cache = NULL;
-+}
-+
-+#else  /* CONFIG_EXT3_FS_XATTR_SHARING */
-+
-+int __init
-+init_ext3_xattr(void)
-+{
-+      return 0;
-+}
-+
-+void
-+exit_ext3_xattr(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT3_FS_XATTR_SHARING */
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/fs/ext3/xattr_user.c     2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,111 @@
-+/*
-+ * linux/fs/ext3/xattr_user.c
-+ * Handler for extended user attributes.
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/string.h>
-+#include <linux/fs.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
-+
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+# include <linux/ext3_acl.h>
-+#endif
-+
-+#define XATTR_USER_PREFIX "user."
-+
-+static size_t
-+ext3_xattr_user_list(char *list, struct inode *inode,
-+                   const char *name, int name_len)
-+{
-+      const int prefix_len = sizeof(XATTR_USER_PREFIX)-1;
-+
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return 0;
-+
-+      if (list) {
-+              memcpy(list, XATTR_USER_PREFIX, prefix_len);
-+              memcpy(list+prefix_len, name, name_len);
-+              list[prefix_len + name_len] = '\0';
-+      }
-+      return prefix_len + name_len + 1;
-+}
-+
-+static int
-+ext3_xattr_user_get(struct inode *inode, const char *name,
-+                  void *buffer, size_t size)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+      error = ext3_permission_locked(inode, MAY_READ);
-+#else
-+      error = permission(inode, MAY_READ);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext3_xattr_get(inode, EXT3_XATTR_INDEX_USER, name,
-+                            buffer, size);
-+}
-+
-+static int
-+ext3_xattr_user_set(struct inode *inode, const char *name,
-+                  const void *value, size_t size, int flags)
-+{
-+      handle_t *handle;
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+      if ( !S_ISREG(inode->i_mode) &&
-+          (!S_ISDIR(inode->i_mode) || inode->i_mode & S_ISVTX))
-+              return -EPERM;
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+      error = ext3_permission_locked(inode, MAY_WRITE);
-+#else
-+      error = permission(inode, MAY_WRITE);
-+#endif
-+      if (error)
-+              return error;
-+
-+      handle = ext3_journal_start(inode, EXT3_XATTR_TRANS_BLOCKS);
-+      if (IS_ERR(handle))
-+              return PTR_ERR(handle);
-+      error = ext3_xattr_set(handle, inode, EXT3_XATTR_INDEX_USER, name,
-+                             value, size, flags);
-+      ext3_journal_stop(handle, inode);
-+
-+      return error;
-+}
-+
-+struct ext3_xattr_handler ext3_xattr_user_handler = {
-+      prefix: XATTR_USER_PREFIX,
-+      list:   ext3_xattr_user_list,
-+      get:    ext3_xattr_user_get,
-+      set:    ext3_xattr_user_set,
-+};
-+
-+int __init
-+init_ext3_xattr_user(void)
-+{
-+      return ext3_xattr_register(EXT3_XATTR_INDEX_USER,
-+                                 &ext3_xattr_user_handler);
-+}
-+
-+void
-+exit_ext3_xattr_user(void)
-+{
-+      ext3_xattr_unregister(EXT3_XATTR_INDEX_USER,
-+                            &ext3_xattr_user_handler);
-+}
---- linux-2.4.20/fs/jfs/jfs_xattr.h~linux-2.4.20-xattr-0.8.54  2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/jfs/jfs_xattr.h       2003-05-07 18:08:03.000000000 +0800
-@@ -52,8 +52,10 @@ struct jfs_ea_list {
- #define       END_EALIST(ealist) \
-       ((struct jfs_ea *) (((char *) (ealist)) + EALIST_SIZE(ealist)))
--extern int __jfs_setxattr(struct inode *, const char *, void *, size_t, int);
--extern int jfs_setxattr(struct dentry *, const char *, void *, size_t, int);
-+extern int __jfs_setxattr(struct inode *, const char *, const void *, size_t,
-+                        int);
-+extern int jfs_setxattr(struct dentry *, const char *, const void *, size_t,
-+                      int);
- extern ssize_t __jfs_getxattr(struct inode *, const char *, void *, size_t);
- extern ssize_t jfs_getxattr(struct dentry *, const char *, void *, size_t);
- extern ssize_t jfs_listxattr(struct dentry *, char *, size_t);
---- linux-2.4.20/fs/jfs/xattr.c~linux-2.4.20-xattr-0.8.54      2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/fs/jfs/xattr.c   2003-05-07 18:08:03.000000000 +0800
-@@ -641,7 +641,7 @@ static int ea_put(struct inode *inode, s
- }
- static int can_set_xattr(struct inode *inode, const char *name,
--                       void *value, size_t value_len)
-+                       const void *value, size_t value_len)
- {
-       if (IS_RDONLY(inode))
-               return -EROFS;
-@@ -660,7 +660,7 @@ static int can_set_xattr(struct inode *i
-       return permission(inode, MAY_WRITE);
- }
--int __jfs_setxattr(struct inode *inode, const char *name, void *value,
-+int __jfs_setxattr(struct inode *inode, const char *name, const void *value,
-                  size_t value_len, int flags)
- {
-       struct jfs_ea_list *ealist;
-@@ -799,7 +799,7 @@ int __jfs_setxattr(struct inode *inode, 
-       return rc;
- }
--int jfs_setxattr(struct dentry *dentry, const char *name, void *value,
-+int jfs_setxattr(struct dentry *dentry, const char *name, const void *value,
-                size_t value_len, int flags)
- {
-       if (value == NULL) {    /* empty EA, do not remove */
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/fs/mbcache.c     2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,648 @@
-+/*
-+ * linux/fs/mbcache.c
-+ * (C) 2001-2002 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+/*
-+ * Filesystem Meta Information Block Cache (mbcache)
-+ *
-+ * The mbcache caches blocks of block devices that need to be located
-+ * by their device/block number, as well as by other criteria (such
-+ * as the block's contents).
-+ *
-+ * There can only be one cache entry in a cache per device and block number.
-+ * Additional indexes need not be unique in this sense. The number of
-+ * additional indexes (=other criteria) can be hardwired at compile time
-+ * or specified at cache create time.
-+ *
-+ * Each cache entry is of fixed size. An entry may be `valid' or `invalid'
-+ * in the cache. A valid entry is in the main hash tables of the cache,
-+ * and may also be in the lru list. An invalid entry is not in any hashes
-+ * or lists.
-+ *
-+ * A valid cache entry is only in the lru list if no handles refer to it.
-+ * Invalid cache entries will be freed when the last handle to the cache
-+ * entry is released. Entries that cannot be freed immediately are put
-+ * back on the lru list.
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+
-+#include <linux/fs.h>
-+#include <linux/slab.h>
-+#include <linux/sched.h>
-+#include <linux/cache_def.h>
-+#include <linux/version.h>
-+#include <linux/init.h>
-+#include <linux/mbcache.h>
-+
-+
-+#ifdef MB_CACHE_DEBUG
-+# define mb_debug(f...) do { \
-+              printk(KERN_DEBUG f); \
-+              printk("\n"); \
-+      } while (0)
-+#define mb_assert(c) do { if (!(c)) \
-+              printk(KERN_ERR "assertion " #c " failed\n"); \
-+      } while(0)
-+#else
-+# define mb_debug(f...) do { } while(0)
-+# define mb_assert(c) do { } while(0)
-+#endif
-+#define mb_error(f...) do { \
-+              printk(KERN_ERR f); \
-+              printk("\n"); \
-+      } while(0)
-+              
-+MODULE_AUTHOR("Andreas Gruenbacher <a.gruenbacher@computer.org>");
-+MODULE_DESCRIPTION("Meta block cache (for extended attributes)");
-+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,0)
-+MODULE_LICENSE("GPL");
-+#endif
-+
-+EXPORT_SYMBOL(mb_cache_create);
-+EXPORT_SYMBOL(mb_cache_shrink);
-+EXPORT_SYMBOL(mb_cache_destroy);
-+EXPORT_SYMBOL(mb_cache_entry_alloc);
-+EXPORT_SYMBOL(mb_cache_entry_insert);
-+EXPORT_SYMBOL(mb_cache_entry_release);
-+EXPORT_SYMBOL(mb_cache_entry_takeout);
-+EXPORT_SYMBOL(mb_cache_entry_free);
-+EXPORT_SYMBOL(mb_cache_entry_dup);
-+EXPORT_SYMBOL(mb_cache_entry_get);
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+EXPORT_SYMBOL(mb_cache_entry_find_first);
-+EXPORT_SYMBOL(mb_cache_entry_find_next);
-+#endif
-+
-+
-+/*
-+ * Global data: list of all mbcache's, lru list, and a spinlock for
-+ * accessing cache data structures on SMP machines. The lru list is
-+ * global across all mbcaches.
-+ */
-+
-+static LIST_HEAD(mb_cache_list);
-+static LIST_HEAD(mb_cache_lru_list);
-+static spinlock_t mb_cache_spinlock = SPIN_LOCK_UNLOCKED;
-+
-+static inline int
-+mb_cache_indexes(struct mb_cache *cache)
-+{
-+#ifdef MB_CACHE_INDEXES_COUNT
-+      return MB_CACHE_INDEXES_COUNT;
-+#else
-+      return cache->c_indexes_count;
-+#endif
-+}
-+
-+/*
-+ * What the mbcache registers as to get shrunk dynamically.
-+ */
-+
-+static void
-+mb_cache_memory_pressure(int priority, unsigned int gfp_mask);
-+
-+static struct cache_definition mb_cache_definition = {
-+      "mb_cache",
-+      mb_cache_memory_pressure
-+};
-+
-+
-+static inline int
-+__mb_cache_entry_is_hashed(struct mb_cache_entry *ce)
-+{
-+      return !list_empty(&ce->e_block_list);
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_unhash(struct mb_cache_entry *ce)
-+{
-+      int n;
-+
-+      if (__mb_cache_entry_is_hashed(ce)) {
-+              list_del_init(&ce->e_block_list);
-+              for (n=0; n<mb_cache_indexes(ce->e_cache); n++)
-+                      list_del(&ce->e_indexes[n].o_list);
-+      }
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_forget(struct mb_cache_entry *ce, int gfp_mask)
-+{
-+      struct mb_cache *cache = ce->e_cache;
-+
-+      mb_assert(atomic_read(&ce->e_used) == 0);
-+      if (cache->c_op.free && cache->c_op.free(ce, gfp_mask)) {
-+              /* free failed -- put back on the lru list
-+                 for freeing later. */
-+              spin_lock(&mb_cache_spinlock);
-+              list_add(&ce->e_lru_list, &mb_cache_lru_list);
-+              spin_unlock(&mb_cache_spinlock);
-+      } else {
-+              kmem_cache_free(cache->c_entry_cache, ce);
-+              atomic_dec(&cache->c_entry_count);
-+      }
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_release_unlock(struct mb_cache_entry *ce)
-+{
-+      if (atomic_dec_and_test(&ce->e_used)) {
-+              if (__mb_cache_entry_is_hashed(ce))
-+                      list_add_tail(&ce->e_lru_list, &mb_cache_lru_list);
-+              else {
-+                      spin_unlock(&mb_cache_spinlock);
-+                      __mb_cache_entry_forget(ce, GFP_KERNEL);
-+                      return;
-+              }
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+}
-+
-+
-+/*
-+ * mb_cache_memory_pressure()  memory pressure callback
-+ *
-+ * This function is called by the kernel memory management when memory
-+ * gets low.
-+ *
-+ * @priority: Amount by which to shrink the cache (0 = highes priority)
-+ * @gfp_mask: (ignored)
-+ */
-+static void
-+mb_cache_memory_pressure(int priority, unsigned int gfp_mask)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+      int count = 0;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &mb_cache_list) {
-+              struct mb_cache *cache =
-+                      list_entry(l, struct mb_cache, c_cache_list);
-+              mb_debug("cache %s (%d)", cache->c_name,
-+                        atomic_read(&cache->c_entry_count));
-+              count += atomic_read(&cache->c_entry_count);
-+      }
-+      mb_debug("trying to free %d of %d entries",
-+                count / (priority ? priority : 1), count);
-+      if (priority)
-+              count /= priority;
-+      while (count-- && !list_empty(&mb_cache_lru_list)) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(mb_cache_lru_list.next,
-+                                 struct mb_cache_entry, e_lru_list);
-+              list_del(&ce->e_lru_list);
-+              __mb_cache_entry_unhash(ce);
-+              list_add_tail(&ce->e_lru_list, &free_list);
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), gfp_mask);
-+      }
-+}
-+
-+
-+/*
-+ * mb_cache_create()  create a new cache
-+ *
-+ * All entries in one cache are equal size. Cache entries may be from
-+ * multiple devices. If this is the first mbcache created, registers
-+ * the cache with kernel memory management. Returns NULL if no more
-+ * memory was available.
-+ *
-+ * @name: name of the cache (informal)
-+ * @cache_op: contains the callback called when freeing a cache entry
-+ * @entry_size: The size of a cache entry, including
-+ *              struct mb_cache_entry
-+ * @indexes_count: number of additional indexes in the cache. Must equal
-+ *                 MB_CACHE_INDEXES_COUNT if the number of indexes is
-+ *                 hardwired.
-+ * @bucket_count: number of hash buckets
-+ */
-+struct mb_cache *
-+mb_cache_create(const char *name, struct mb_cache_op *cache_op,
-+              size_t entry_size, int indexes_count, int bucket_count)
-+{
-+      int m=0, n;
-+      struct mb_cache *cache = NULL;
-+
-+      if(entry_size < sizeof(struct mb_cache_entry) +
-+         indexes_count * sizeof(struct mb_cache_entry_index))
-+              return NULL;
-+
-+      MOD_INC_USE_COUNT;
-+      cache = kmalloc(sizeof(struct mb_cache) +
-+                      indexes_count * sizeof(struct list_head), GFP_KERNEL);
-+      if (!cache)
-+              goto fail;
-+      cache->c_name = name;
-+      cache->c_op.free = NULL;
-+      if (cache_op)
-+              cache->c_op.free = cache_op->free;
-+      atomic_set(&cache->c_entry_count, 0);
-+      cache->c_bucket_count = bucket_count;
-+#ifdef MB_CACHE_INDEXES_COUNT
-+      mb_assert(indexes_count == MB_CACHE_INDEXES_COUNT);
-+#else
-+      cache->c_indexes_count = indexes_count;
-+#endif
-+      cache->c_block_hash = kmalloc(bucket_count * sizeof(struct list_head),
-+                                    GFP_KERNEL);
-+      if (!cache->c_block_hash)
-+              goto fail;
-+      for (n=0; n<bucket_count; n++)
-+              INIT_LIST_HEAD(&cache->c_block_hash[n]);
-+      for (m=0; m<indexes_count; m++) {
-+              cache->c_indexes_hash[m] = kmalloc(bucket_count *
-+                                               sizeof(struct list_head),
-+                                               GFP_KERNEL);
-+              if (!cache->c_indexes_hash[m])
-+                      goto fail;
-+              for (n=0; n<bucket_count; n++)
-+                      INIT_LIST_HEAD(&cache->c_indexes_hash[m][n]);
-+      }
-+      cache->c_entry_cache = kmem_cache_create(name, entry_size, 0,
-+              0 /*SLAB_POISON | SLAB_RED_ZONE*/, NULL, NULL);
-+      if (!cache->c_entry_cache)
-+              goto fail;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_add(&cache->c_cache_list, &mb_cache_list);
-+      spin_unlock(&mb_cache_spinlock);
-+      return cache;
-+
-+fail:
-+      if (cache) {
-+              while (--m >= 0)
-+                      kfree(cache->c_indexes_hash[m]);
-+              if (cache->c_block_hash)
-+                      kfree(cache->c_block_hash);
-+              kfree(cache);
-+      }
-+      MOD_DEC_USE_COUNT;
-+      return NULL;
-+}
-+
-+
-+/*
-+ * mb_cache_shrink()
-+ *
-+ * Removes all cache entires of a device from the cache. All cache entries
-+ * currently in use cannot be freed, and thus remain in the cache.
-+ *
-+ * @cache: which cache to shrink
-+ * @dev: which device's cache entries to shrink
-+ */
-+void
-+mb_cache_shrink(struct mb_cache *cache, kdev_t dev)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &mb_cache_lru_list) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_lru_list);
-+              if (ce->e_dev == dev) {
-+                      list_del(&ce->e_lru_list);
-+                      list_add_tail(&ce->e_lru_list, &free_list);
-+                      __mb_cache_entry_unhash(ce);
-+              }
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), GFP_KERNEL);
-+      }
-+}
-+
-+
-+/*
-+ * mb_cache_destroy()
-+ *
-+ * Shrinks the cache to its minimum possible size (hopefully 0 entries),
-+ * and then destroys it. If this was the last mbcache, un-registers the
-+ * mbcache from kernel memory management.
-+ */
-+void
-+mb_cache_destroy(struct mb_cache *cache)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+      int n;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &mb_cache_lru_list) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_lru_list);
-+              if (ce->e_cache == cache) {
-+                      list_del(&ce->e_lru_list);
-+                      list_add_tail(&ce->e_lru_list, &free_list);
-+                      __mb_cache_entry_unhash(ce);
-+              }
-+      }
-+      list_del(&cache->c_cache_list);
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), GFP_KERNEL);
-+      }
-+
-+      if (atomic_read(&cache->c_entry_count) > 0) {
-+              mb_error("cache %s: %d orphaned entries",
-+                        cache->c_name,
-+                        atomic_read(&cache->c_entry_count));
-+      }
-+
-+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,3,0))
-+      /* We don't have kmem_cache_destroy() in 2.2.x */
-+      kmem_cache_shrink(cache->c_entry_cache);
-+#else
-+      kmem_cache_destroy(cache->c_entry_cache);
-+#endif
-+      for (n=0; n < mb_cache_indexes(cache); n++)
-+              kfree(cache->c_indexes_hash[n]);
-+      kfree(cache->c_block_hash);
-+      kfree(cache);
-+
-+      MOD_DEC_USE_COUNT;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_alloc()
-+ *
-+ * Allocates a new cache entry. The new entry will not be valid initially,
-+ * and thus cannot be looked up yet. It should be filled with data, and
-+ * then inserted into the cache using mb_cache_entry_insert(). Returns NULL
-+ * if no more memory was available.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_alloc(struct mb_cache *cache)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      atomic_inc(&cache->c_entry_count);
-+      ce = kmem_cache_alloc(cache->c_entry_cache, GFP_KERNEL);
-+      if (ce) {
-+              INIT_LIST_HEAD(&ce->e_lru_list);
-+              INIT_LIST_HEAD(&ce->e_block_list);
-+              ce->e_cache = cache;
-+              atomic_set(&ce->e_used, 1);
-+      }
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_insert()
-+ *
-+ * Inserts an entry that was allocated using mb_cache_entry_alloc() into
-+ * the cache. After this, the cache entry can be looked up, but is not yet
-+ * in the lru list as the caller still holds a handle to it. Returns 0 on
-+ * success, or -EBUSY if a cache entry for that device + inode exists
-+ * already (this may happen after a failed lookup, if another process has
-+ * inserted the same cache entry in the meantime).
-+ *
-+ * @dev: device the cache entry belongs to
-+ * @block: block number
-+ * @keys: array of additional keys. There must be indexes_count entries
-+ *        in the array (as specified when creating the cache).
-+ */
-+int
-+mb_cache_entry_insert(struct mb_cache_entry *ce, kdev_t dev,
-+                    unsigned long block, unsigned int keys[])
-+{
-+      struct mb_cache *cache = ce->e_cache;
-+      unsigned int bucket = (HASHDEV(dev) + block) % cache->c_bucket_count;
-+      struct list_head *l;
-+      int error = -EBUSY, n;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &cache->c_block_hash[bucket]) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_block_list);
-+              if (ce->e_dev == dev && ce->e_block == block)
-+                      goto out;
-+      }
-+      __mb_cache_entry_unhash(ce);
-+      ce->e_dev = dev;
-+      ce->e_block = block;
-+      list_add(&ce->e_block_list, &cache->c_block_hash[bucket]);
-+      for (n=0; n<mb_cache_indexes(cache); n++) {
-+              ce->e_indexes[n].o_key = keys[n];
-+              bucket = keys[n] % cache->c_bucket_count;
-+              list_add(&ce->e_indexes[n].o_list,
-+                       &cache->c_indexes_hash[n][bucket]);
-+      }
-+out:
-+      spin_unlock(&mb_cache_spinlock);
-+      return error;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_release()
-+ *
-+ * Release a handle to a cache entry. When the last handle to a cache entry
-+ * is released it is either freed (if it is invalid) or otherwise inserted
-+ * in to the lru list.
-+ */
-+void
-+mb_cache_entry_release(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      __mb_cache_entry_release_unlock(ce);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_takeout()
-+ *
-+ * Take a cache entry out of the cache, making it invalid. The entry can later
-+ * be re-inserted using mb_cache_entry_insert(), or released using
-+ * mb_cache_entry_release().
-+ */
-+void
-+mb_cache_entry_takeout(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      mb_assert(list_empty(&ce->e_lru_list));
-+      __mb_cache_entry_unhash(ce);
-+      spin_unlock(&mb_cache_spinlock);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_free()
-+ *
-+ * This is equivalent to the sequence mb_cache_entry_takeout() --
-+ * mb_cache_entry_release().
-+ */
-+void
-+mb_cache_entry_free(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      mb_assert(list_empty(&ce->e_lru_list));
-+      __mb_cache_entry_unhash(ce);
-+      __mb_cache_entry_release_unlock(ce);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_dup()
-+ *
-+ * Duplicate a handle to a cache entry (does not duplicate the cache entry
-+ * itself). After the call, both the old and the new handle must be released.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_dup(struct mb_cache_entry *ce)
-+{
-+      atomic_inc(&ce->e_used);
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_get()
-+ *
-+ * Get a cache entry  by device / block number. (There can only be one entry
-+ * in the cache per device and block.) Returns NULL if no such cache entry
-+ * exists.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_get(struct mb_cache *cache, kdev_t dev, unsigned long block)
-+{
-+      unsigned int bucket = (HASHDEV(dev) + block) % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &cache->c_block_hash[bucket]) {
-+              ce = list_entry(l, struct mb_cache_entry, e_block_list);
-+              if (ce->e_dev == dev && ce->e_block == block) {
-+                      if (!list_empty(&ce->e_lru_list))
-+                              list_del_init(&ce->e_lru_list);
-+                      atomic_inc(&ce->e_used);
-+                      goto cleanup;
-+              }
-+      }
-+      ce = NULL;
-+
-+cleanup:
-+      spin_unlock(&mb_cache_spinlock);
-+      return ce;
-+}
-+
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+
-+static struct mb_cache_entry *
-+__mb_cache_entry_find(struct list_head *l, struct list_head *head,
-+                    int index, kdev_t dev, unsigned int key)
-+{
-+      while (l != head) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry,
-+                                 e_indexes[index].o_list);
-+              if (ce->e_dev == dev && ce->e_indexes[index].o_key == key) {
-+                      if (!list_empty(&ce->e_lru_list))
-+                              list_del_init(&ce->e_lru_list);
-+                      atomic_inc(&ce->e_used);
-+                      return ce;
-+              }
-+              l = l->next;
-+      }
-+      return NULL;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_find_first()
-+ *
-+ * Find the first cache entry on a given device with a certain key in
-+ * an additional index. Additonal matches can be found with
-+ * mb_cache_entry_find_next(). Returns NULL if no match was found.
-+ *
-+ * @cache: the cache to search
-+ * @index: the number of the additonal index to search (0<=index<indexes_count)
-+ * @dev: the device the cache entry should belong to
-+ * @key: the key in the index
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_find_first(struct mb_cache *cache, int index, kdev_t dev,
-+                        unsigned int key)
-+{
-+      unsigned int bucket = key % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      mb_assert(index < mb_cache_indexes(cache));
-+      spin_lock(&mb_cache_spinlock);
-+      l = cache->c_indexes_hash[index][bucket].next;
-+      ce = __mb_cache_entry_find(l, &cache->c_indexes_hash[index][bucket],
-+                                 index, dev, key);
-+      spin_unlock(&mb_cache_spinlock);
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_find_next()
-+ *
-+ * Find the next cache entry on a given device with a certain key in an
-+ * additional index. Returns NULL if no match could be found. The previous
-+ * entry is atomatically released, so that mb_cache_entry_find_next() can
-+ * be called like this:
-+ *
-+ * entry = mb_cache_entry_find_first();
-+ * while (entry) {
-+ *    ...
-+ *    entry = mb_cache_entry_find_next(entry, ...);
-+ * }
-+ *
-+ * @prev: The previous match
-+ * @index: the number of the additonal index to search (0<=index<indexes_count)
-+ * @dev: the device the cache entry should belong to
-+ * @key: the key in the index
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_find_next(struct mb_cache_entry *prev, int index, kdev_t dev,
-+                       unsigned int key)
-+{
-+      struct mb_cache *cache = prev->e_cache;
-+      unsigned int bucket = key % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      mb_assert(index < mb_cache_indexes(cache));
-+      spin_lock(&mb_cache_spinlock);
-+      l = prev->e_indexes[index].o_list.next;
-+      ce = __mb_cache_entry_find(l, &cache->c_indexes_hash[index][bucket],
-+                                 index, dev, key);
-+      __mb_cache_entry_release_unlock(prev);
-+      return ce;
-+}
-+
-+#endif  /* !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0) */
-+
-+static int __init init_mbcache(void)
-+{
-+      register_cache(&mb_cache_definition);
-+      return 0;
-+}
-+
-+static void __exit exit_mbcache(void)
-+{
-+      unregister_cache(&mb_cache_definition);
-+}
-+
-+module_init(init_mbcache)
-+module_exit(exit_mbcache)
-+
---- linux-2.4.20/include/asm-arm/unistd.h~linux-2.4.20-xattr-0.8.54    2002-08-03 08:39:45.000000000 +0800
-+++ linux-2.4.20-root/include/asm-arm/unistd.h 2003-05-07 18:08:03.000000000 +0800
-@@ -244,7 +244,6 @@
- #define __NR_security                 (__NR_SYSCALL_BASE+223)
- #define __NR_gettid                   (__NR_SYSCALL_BASE+224)
- #define __NR_readahead                        (__NR_SYSCALL_BASE+225)
--#if 0 /* allocated in 2.5 */
- #define __NR_setxattr                 (__NR_SYSCALL_BASE+226)
- #define __NR_lsetxattr                        (__NR_SYSCALL_BASE+227)
- #define __NR_fsetxattr                        (__NR_SYSCALL_BASE+228)
-@@ -257,7 +256,6 @@
- #define __NR_removexattr              (__NR_SYSCALL_BASE+235)
- #define __NR_lremovexattr             (__NR_SYSCALL_BASE+236)
- #define __NR_fremovexattr             (__NR_SYSCALL_BASE+237)
--#endif
- #define __NR_tkill                    (__NR_SYSCALL_BASE+238)
- /*
-  * Please check 2.5 _before_ adding calls here,
---- linux-2.4.20/include/asm-ppc64/unistd.h~linux-2.4.20-xattr-0.8.54  2002-08-03 08:39:45.000000000 +0800
-+++ linux-2.4.20-root/include/asm-ppc64/unistd.h       2003-05-07 18:08:03.000000000 +0800
-@@ -218,6 +218,7 @@
- #define __NR_gettid           207
- #if 0 /* Reserved syscalls */
- #define __NR_tkill            208
-+#endif
- #define __NR_setxattr         209
- #define __NR_lsetxattr                210
- #define __NR_fsetxattr                211
-@@ -230,6 +231,7 @@
- #define __NR_removexattr      218
- #define __NR_lremovexattr     219
- #define __NR_fremovexattr     220
-+#if 0 /* Reserved syscalls */
- #define __NR_futex            221
- #endif
---- linux-2.4.20/include/asm-s390/unistd.h~linux-2.4.20-xattr-0.8.54   2002-08-03 08:39:45.000000000 +0800
-+++ linux-2.4.20-root/include/asm-s390/unistd.h        2003-05-07 18:08:03.000000000 +0800
-@@ -212,9 +212,18 @@
- #define __NR_getdents64               220
- #define __NR_fcntl64          221
- #define __NR_readahead                222
--/*
-- * Numbers 224-235 are reserved for posix acl
-- */
-+#define __NR_setxattr         224
-+#define __NR_lsetxattr                225
-+#define __NR_fsetxattr                226
-+#define __NR_getxattr         227
-+#define __NR_lgetxattr                228
-+#define __NR_fgetxattr                229
-+#define __NR_listxattr                230
-+#define __NR_llistxattr               231
-+#define __NR_flistxattr               232
-+#define __NR_removexattr      233
-+#define __NR_lremovexattr     234
-+#define __NR_fremovexattr     235
- #define __NR_gettid           236
- #define __NR_tkill            237
---- linux-2.4.20/include/asm-s390x/unistd.h~linux-2.4.20-xattr-0.8.54  2002-08-03 08:39:45.000000000 +0800
-+++ linux-2.4.20-root/include/asm-s390x/unistd.h       2003-05-07 18:08:03.000000000 +0800
-@@ -180,9 +180,18 @@
- #define __NR_mincore            218
- #define __NR_madvise            219
- #define __NR_readahead                222
--/*
-- * Numbers 224-235 are reserved for posix acl
-- */
-+#define __NR_setxattr         224
-+#define __NR_lsetxattr                225
-+#define __NR_fsetxattr                226
-+#define __NR_getxattr         227
-+#define __NR_lgetxattr                228
-+#define __NR_fgetxattr                229
-+#define __NR_listxattr                230
-+#define __NR_llistxattr               231
-+#define __NR_flistxattr               232
-+#define __NR_removexattr      233
-+#define __NR_lremovexattr     234
-+#define __NR_fremovexattr     235
- #define __NR_gettid           236
- #define __NR_tkill            237
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/include/linux/cache_def.h        2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,15 @@
-+/*
-+ * linux/cache_def.h
-+ * Handling of caches defined in drivers, filesystems, ...
-+ *
-+ * Copyright (C) 2002 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+struct cache_definition {
-+      const char *name;
-+      void (*shrink)(int, unsigned int);
-+      struct list_head link;
-+};
-+
-+extern void register_cache(struct cache_definition *);
-+extern void unregister_cache(struct cache_definition *);
---- linux-2.4.20/include/linux/errno.h~linux-2.4.20-xattr-0.8.54       2003-04-14 16:39:03.000000000 +0800
-+++ linux-2.4.20-root/include/linux/errno.h    2003-05-07 18:08:03.000000000 +0800
-@@ -23,4 +23,8 @@
- #endif
-+/* Defined for extended attributes */
-+#define ENOATTR ENODATA               /* No such attribute */
-+#define ENOTSUP EOPNOTSUPP    /* Operation not supported */
-+
- #endif
---- linux-2.4.20/include/linux/ext2_fs.h~linux-2.4.20-xattr-0.8.54     2003-04-14 16:39:08.000000000 +0800
-+++ linux-2.4.20-root/include/linux/ext2_fs.h  2003-05-07 18:08:03.000000000 +0800
-@@ -57,8 +57,6 @@
-  */
- #define       EXT2_BAD_INO             1      /* Bad blocks inode */
- #define EXT2_ROOT_INO          2      /* Root inode */
--#define EXT2_ACL_IDX_INO       3      /* ACL inode */
--#define EXT2_ACL_DATA_INO      4      /* ACL inode */
- #define EXT2_BOOT_LOADER_INO   5      /* Boot loader inode */
- #define EXT2_UNDEL_DIR_INO     6      /* Undelete directory inode */
-@@ -86,7 +84,6 @@
- #else
- # define EXT2_BLOCK_SIZE(s)           (EXT2_MIN_BLOCK_SIZE << (s)->s_log_block_size)
- #endif
--#define EXT2_ACLE_PER_BLOCK(s)                (EXT2_BLOCK_SIZE(s) / sizeof (struct ext2_acl_entry))
- #define       EXT2_ADDR_PER_BLOCK(s)          (EXT2_BLOCK_SIZE(s) / sizeof (__u32))
- #ifdef __KERNEL__
- # define EXT2_BLOCK_SIZE_BITS(s)      ((s)->s_blocksize_bits)
-@@ -121,28 +118,6 @@
- #endif
- /*
-- * ACL structures
-- */
--struct ext2_acl_header        /* Header of Access Control Lists */
--{
--      __u32   aclh_size;
--      __u32   aclh_file_count;
--      __u32   aclh_acle_count;
--      __u32   aclh_first_acle;
--};
--
--struct ext2_acl_entry /* Access Control List Entry */
--{
--      __u32   acle_size;
--      __u16   acle_perms;     /* Access permissions */
--      __u16   acle_type;      /* Type of entry */
--      __u16   acle_tag;       /* User or group identity */
--      __u16   acle_pad1;
--      __u32   acle_next;      /* Pointer on next entry for the */
--                                      /* same inode or on next free entry */
--};
--
--/*
-  * Structure of a blocks group descriptor
-  */
- struct ext2_group_desc
-@@ -314,6 +289,7 @@ struct ext2_inode {
- #define EXT2_MOUNT_ERRORS_PANIC               0x0040  /* Panic on errors */
- #define EXT2_MOUNT_MINIX_DF           0x0080  /* Mimics the Minix statfs */
- #define EXT2_MOUNT_NO_UID32           0x0200  /* Disable 32-bit UIDs */
-+#define EXT2_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
- #define clear_opt(o, opt)             o &= ~EXT2_MOUNT_##opt
- #define set_opt(o, opt)                       o |= EXT2_MOUNT_##opt
-@@ -397,6 +373,7 @@ struct ext2_super_block {
- #ifdef __KERNEL__
- #define EXT2_SB(sb)   (&((sb)->u.ext2_sb))
-+#define EXT2_I(inode) (&((inode)->u.ext2_i))
- #else
- /* Assume that user mode programs are passing in an ext2fs superblock, not
-  * a kernel struct super_block.  This will allow us to call the feature-test
-@@ -466,7 +443,7 @@ struct ext2_super_block {
- #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008
- #define EXT2_FEATURE_INCOMPAT_ANY             0xffffffff
--#define EXT2_FEATURE_COMPAT_SUPP      0
-+#define EXT2_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
- #define EXT2_FEATURE_INCOMPAT_SUPP    EXT2_FEATURE_INCOMPAT_FILETYPE
- #define EXT2_FEATURE_RO_COMPAT_SUPP   (EXT2_FEATURE_RO_COMPAT_SPARSE_SUPER| \
-                                        EXT2_FEATURE_RO_COMPAT_LARGE_FILE| \
-@@ -623,8 +600,10 @@ extern struct address_space_operations e
- /* namei.c */
- extern struct inode_operations ext2_dir_inode_operations;
-+extern struct inode_operations ext2_special_inode_operations;
- /* symlink.c */
-+extern struct inode_operations ext2_symlink_inode_operations;
- extern struct inode_operations ext2_fast_symlink_inode_operations;
- #endif        /* __KERNEL__ */
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/include/linux/ext2_xattr.h       2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,157 @@
-+/*
-+  File: linux/ext2_xattr.h
-+
-+  On-disk format of extended attributes for the ext2 filesystem.
-+
-+  (C) 2001 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+#include <linux/config.h>
-+#include <linux/init.h>
-+#include <linux/xattr.h>
-+
-+/* Magic value in attribute blocks */
-+#define EXT2_XATTR_MAGIC              0xEA020000
-+
-+/* Maximum number of references to one attribute block */
-+#define EXT2_XATTR_REFCOUNT_MAX               1024
-+
-+/* Name indexes */
-+#define EXT2_XATTR_INDEX_MAX                  10
-+#define EXT2_XATTR_INDEX_USER                 1
-+#define EXT2_XATTR_INDEX_POSIX_ACL_ACCESS     2
-+#define EXT2_XATTR_INDEX_POSIX_ACL_DEFAULT    3
-+
-+struct ext2_xattr_header {
-+      __u32   h_magic;        /* magic number for identification */
-+      __u32   h_refcount;     /* reference count */
-+      __u32   h_blocks;       /* number of disk blocks used */
-+      __u32   h_hash;         /* hash value of all attributes */
-+      __u32   h_reserved[4];  /* zero right now */
-+};
-+
-+struct ext2_xattr_entry {
-+      __u8    e_name_len;     /* length of name */
-+      __u8    e_name_index;   /* attribute name index */
-+      __u16   e_value_offs;   /* offset in disk block of value */
-+      __u32   e_value_block;  /* disk block attribute is stored on (n/i) */
-+      __u32   e_value_size;   /* size of attribute value */
-+      __u32   e_hash;         /* hash value of name and value */
-+      char    e_name[0];      /* attribute name */
-+};
-+
-+#define EXT2_XATTR_PAD_BITS           2
-+#define EXT2_XATTR_PAD                (1<<EXT2_XATTR_PAD_BITS)
-+#define EXT2_XATTR_ROUND              (EXT2_XATTR_PAD-1)
-+#define EXT2_XATTR_LEN(name_len) \
-+      (((name_len) + EXT2_XATTR_ROUND + \
-+      sizeof(struct ext2_xattr_entry)) & ~EXT2_XATTR_ROUND)
-+#define EXT2_XATTR_NEXT(entry) \
-+      ( (struct ext2_xattr_entry *)( \
-+        (char *)(entry) + EXT2_XATTR_LEN((entry)->e_name_len)) )
-+#define EXT2_XATTR_SIZE(size) \
-+      (((size) + EXT2_XATTR_ROUND) & ~EXT2_XATTR_ROUND)
-+
-+#ifdef __KERNEL__
-+
-+# ifdef CONFIG_EXT2_FS_XATTR
-+
-+struct ext2_xattr_handler {
-+      char *prefix;
-+      size_t (*list)(char *list, struct inode *inode, const char *name,
-+                     int name_len);
-+      int (*get)(struct inode *inode, const char *name, void *buffer,
-+                 size_t size);
-+      int (*set)(struct inode *inode, const char *name, const void *buffer,
-+                 size_t size, int flags);
-+};
-+
-+extern int ext2_xattr_register(int, struct ext2_xattr_handler *);
-+extern void ext2_xattr_unregister(int, struct ext2_xattr_handler *);
-+
-+extern int ext2_setxattr(struct dentry *, const char *, const void *, size_t, int);
-+extern ssize_t ext2_getxattr(struct dentry *, const char *, void *, size_t);
-+extern ssize_t ext2_listxattr(struct dentry *, char *, size_t);
-+extern int ext2_removexattr(struct dentry *, const char *);
-+
-+extern int ext2_xattr_get(struct inode *, int, const char *, void *, size_t);
-+extern int ext2_xattr_list(struct inode *, char *, size_t);
-+extern int ext2_xattr_set(struct inode *, int, const char *, const void *, size_t, int);
-+
-+extern void ext2_xattr_delete_inode(struct inode *);
-+extern void ext2_xattr_put_super(struct super_block *);
-+
-+extern int init_ext2_xattr(void) __init;
-+extern void exit_ext2_xattr(void);
-+
-+# else  /* CONFIG_EXT2_FS_XATTR */
-+#  define ext2_setxattr               NULL
-+#  define ext2_getxattr               NULL
-+#  define ext2_listxattr      NULL
-+#  define ext2_removexattr    NULL
-+
-+static inline int
-+ext2_xattr_get(struct inode *inode, int name_index,
-+             const char *name, void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext2_xattr_list(struct inode *inode, char *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext2_xattr_set(struct inode *inode, int name_index, const char *name,
-+             const void *value, size_t size, int flags)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline void
-+ext2_xattr_delete_inode(struct inode *inode)
-+{
-+}
-+
-+static inline void
-+ext2_xattr_put_super(struct super_block *sb)
-+{
-+}
-+
-+static inline int
-+init_ext2_xattr(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext2_xattr(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT2_FS_XATTR */
-+
-+# ifdef CONFIG_EXT2_FS_XATTR_USER
-+
-+extern int init_ext2_xattr_user(void) __init;
-+extern void exit_ext2_xattr_user(void);
-+
-+# else  /* CONFIG_EXT2_FS_XATTR_USER */
-+
-+static inline int
-+init_ext2_xattr_user(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext2_xattr_user(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT2_FS_XATTR_USER */
-+
-+#endif  /* __KERNEL__ */
-+
---- linux-2.4.20/include/linux/ext3_fs.h~linux-2.4.20-xattr-0.8.54     2003-05-05 19:01:04.000000000 +0800
-+++ linux-2.4.20-root/include/linux/ext3_fs.h  2003-05-07 18:08:03.000000000 +0800
-@@ -63,8 +63,6 @@
-  */
- #define       EXT3_BAD_INO             1      /* Bad blocks inode */
- #define EXT3_ROOT_INO          2      /* Root inode */
--#define EXT3_ACL_IDX_INO       3      /* ACL inode */
--#define EXT3_ACL_DATA_INO      4      /* ACL inode */
- #define EXT3_BOOT_LOADER_INO   5      /* Boot loader inode */
- #define EXT3_UNDEL_DIR_INO     6      /* Undelete directory inode */
- #define EXT3_RESIZE_INO                7      /* Reserved group descriptors inode */
-@@ -94,7 +92,6 @@
- #else
- # define EXT3_BLOCK_SIZE(s)           (EXT3_MIN_BLOCK_SIZE << (s)->s_log_block_size)
- #endif
--#define EXT3_ACLE_PER_BLOCK(s)                (EXT3_BLOCK_SIZE(s) / sizeof (struct ext3_acl_entry))
- #define       EXT3_ADDR_PER_BLOCK(s)          (EXT3_BLOCK_SIZE(s) / sizeof (__u32))
- #ifdef __KERNEL__
- # define EXT3_BLOCK_SIZE_BITS(s)      ((s)->s_blocksize_bits)
-@@ -129,28 +126,6 @@
- #endif
- /*
-- * ACL structures
-- */
--struct ext3_acl_header        /* Header of Access Control Lists */
--{
--      __u32   aclh_size;
--      __u32   aclh_file_count;
--      __u32   aclh_acle_count;
--      __u32   aclh_first_acle;
--};
--
--struct ext3_acl_entry /* Access Control List Entry */
--{
--      __u32   acle_size;
--      __u16   acle_perms;     /* Access permissions */
--      __u16   acle_type;      /* Type of entry */
--      __u16   acle_tag;       /* User or group identity */
--      __u16   acle_pad1;
--      __u32   acle_next;      /* Pointer on next entry for the */
--                                      /* same inode or on next free entry */
--};
--
--/*
-  * Structure of a blocks group descriptor
-  */
- struct ext3_group_desc
-@@ -344,6 +319,7 @@ struct ext3_inode {
-   #define EXT3_MOUNT_WRITEBACK_DATA   0x0C00  /* No data ordering */
- #define EXT3_MOUNT_UPDATE_JOURNAL     0x1000  /* Update the journal format */
- #define EXT3_MOUNT_NO_UID32           0x2000  /* Disable 32-bit UIDs */
-+#define EXT3_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
- /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
- #ifndef _LINUX_EXT2_FS_H
-@@ -520,7 +496,7 @@ struct ext3_super_block {
- #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
- #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
--#define EXT3_FEATURE_COMPAT_SUPP      0
-+#define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
- #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
-                                        EXT3_FEATURE_INCOMPAT_RECOVER)
- #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
-@@ -703,6 +679,7 @@ extern void ext3_check_inodes_bitmap (st
- extern unsigned long ext3_count_free (struct buffer_head *, unsigned);
- /* inode.c */
-+extern int ext3_forget(handle_t *, int, struct inode *, struct buffer_head *, int);
- extern struct buffer_head * ext3_getblk (handle_t *, struct inode *, long, int, int *);
- extern struct buffer_head * ext3_bread (handle_t *, struct inode *, int, int, int *);
-@@ -771,8 +748,10 @@ extern struct address_space_operations e
- /* namei.c */
- extern struct inode_operations ext3_dir_inode_operations;
-+extern struct inode_operations ext3_special_inode_operations;
- /* symlink.c */
-+extern struct inode_operations ext3_symlink_inode_operations;
- extern struct inode_operations ext3_fast_symlink_inode_operations;
---- linux-2.4.20/include/linux/ext3_jbd.h~linux-2.4.20-xattr-0.8.54    2003-05-05 19:01:02.000000000 +0800
-+++ linux-2.4.20-root/include/linux/ext3_jbd.h 2003-05-07 18:08:03.000000000 +0800
-@@ -30,13 +30,19 @@
- #define EXT3_SINGLEDATA_TRANS_BLOCKS  8
-+/* Extended attributes may touch two data buffers, two bitmap buffers,
-+ * and two group and summaries. */
-+
-+#define EXT3_XATTR_TRANS_BLOCKS               8
-+
- /* Define the minimum size for a transaction which modifies data.  This
-  * needs to take into account the fact that we may end up modifying two
-  * quota files too (one for the group, one for the user quota).  The
-  * superblock only gets updated once, of course, so don't bother
-  * counting that again for the quota updates. */
--#define EXT3_DATA_TRANS_BLOCKS                (3 * EXT3_SINGLEDATA_TRANS_BLOCKS - 2)
-+#define EXT3_DATA_TRANS_BLOCKS                (3 * EXT3_SINGLEDATA_TRANS_BLOCKS + \
-+                                       EXT3_XATTR_TRANS_BLOCKS - 2)
- extern int ext3_writepage_trans_blocks(struct inode *inode);
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/include/linux/ext3_xattr.h       2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,157 @@
-+/*
-+  File: linux/ext3_xattr.h
-+
-+  On-disk format of extended attributes for the ext3 filesystem.
-+
-+  (C) 2001 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+#include <linux/config.h>
-+#include <linux/init.h>
-+#include <linux/xattr.h>
-+
-+/* Magic value in attribute blocks */
-+#define EXT3_XATTR_MAGIC              0xEA020000
-+
-+/* Maximum number of references to one attribute block */
-+#define EXT3_XATTR_REFCOUNT_MAX               1024
-+
-+/* Name indexes */
-+#define EXT3_XATTR_INDEX_MAX                  10
-+#define EXT3_XATTR_INDEX_USER                 1
-+#define EXT3_XATTR_INDEX_POSIX_ACL_ACCESS     2
-+#define EXT3_XATTR_INDEX_POSIX_ACL_DEFAULT    3
-+
-+struct ext3_xattr_header {
-+      __u32   h_magic;        /* magic number for identification */
-+      __u32   h_refcount;     /* reference count */
-+      __u32   h_blocks;       /* number of disk blocks used */
-+      __u32   h_hash;         /* hash value of all attributes */
-+      __u32   h_reserved[4];  /* zero right now */
-+};
-+
-+struct ext3_xattr_entry {
-+      __u8    e_name_len;     /* length of name */
-+      __u8    e_name_index;   /* attribute name index */
-+      __u16   e_value_offs;   /* offset in disk block of value */
-+      __u32   e_value_block;  /* disk block attribute is stored on (n/i) */
-+      __u32   e_value_size;   /* size of attribute value */
-+      __u32   e_hash;         /* hash value of name and value */
-+      char    e_name[0];      /* attribute name */
-+};
-+
-+#define EXT3_XATTR_PAD_BITS           2
-+#define EXT3_XATTR_PAD                (1<<EXT3_XATTR_PAD_BITS)
-+#define EXT3_XATTR_ROUND              (EXT3_XATTR_PAD-1)
-+#define EXT3_XATTR_LEN(name_len) \
-+      (((name_len) + EXT3_XATTR_ROUND + \
-+      sizeof(struct ext3_xattr_entry)) & ~EXT3_XATTR_ROUND)
-+#define EXT3_XATTR_NEXT(entry) \
-+      ( (struct ext3_xattr_entry *)( \
-+        (char *)(entry) + EXT3_XATTR_LEN((entry)->e_name_len)) )
-+#define EXT3_XATTR_SIZE(size) \
-+      (((size) + EXT3_XATTR_ROUND) & ~EXT3_XATTR_ROUND)
-+
-+#ifdef __KERNEL__
-+
-+# ifdef CONFIG_EXT3_FS_XATTR
-+
-+struct ext3_xattr_handler {
-+      char *prefix;
-+      size_t (*list)(char *list, struct inode *inode, const char *name,
-+                     int name_len);
-+      int (*get)(struct inode *inode, const char *name, void *buffer,
-+                 size_t size);
-+      int (*set)(struct inode *inode, const char *name, const void *buffer,
-+                 size_t size, int flags);
-+};
-+
-+extern int ext3_xattr_register(int, struct ext3_xattr_handler *);
-+extern void ext3_xattr_unregister(int, struct ext3_xattr_handler *);
-+
-+extern int ext3_setxattr(struct dentry *, const char *, const void *, size_t, int);
-+extern ssize_t ext3_getxattr(struct dentry *, const char *, void *, size_t);
-+extern ssize_t ext3_listxattr(struct dentry *, char *, size_t);
-+extern int ext3_removexattr(struct dentry *, const char *);
-+
-+extern int ext3_xattr_get(struct inode *, int, const char *, void *, size_t);
-+extern int ext3_xattr_list(struct inode *, char *, size_t);
-+extern int ext3_xattr_set(handle_t *handle, struct inode *, int, const char *, const void *, size_t, int);
-+
-+extern void ext3_xattr_delete_inode(handle_t *, struct inode *);
-+extern void ext3_xattr_put_super(struct super_block *);
-+
-+extern int init_ext3_xattr(void) __init;
-+extern void exit_ext3_xattr(void);
-+
-+# else  /* CONFIG_EXT3_FS_XATTR */
-+#  define ext3_setxattr               NULL
-+#  define ext3_getxattr               NULL
-+#  define ext3_listxattr      NULL
-+#  define ext3_removexattr    NULL
-+
-+static inline int
-+ext3_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext3_xattr_list(struct inode *inode, void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext3_xattr_set(handle_t *handle, struct inode *inode, int name_index,
-+             const char *name, const void *value, size_t size, int flags)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline void
-+ext3_xattr_delete_inode(handle_t *handle, struct inode *inode)
-+{
-+}
-+
-+static inline void
-+ext3_xattr_put_super(struct super_block *sb)
-+{
-+}
-+
-+static inline int
-+init_ext3_xattr(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext3_xattr(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT3_FS_XATTR */
-+
-+# ifdef CONFIG_EXT3_FS_XATTR_USER
-+
-+extern int init_ext3_xattr_user(void) __init;
-+extern void exit_ext3_xattr_user(void);
-+
-+# else  /* CONFIG_EXT3_FS_XATTR_USER */
-+
-+static inline int
-+init_ext3_xattr_user(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext3_xattr_user(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT3_FS_XATTR_USER */
-+
-+#endif  /* __KERNEL__ */
-+
---- linux-2.4.20/include/linux/fs.h~linux-2.4.20-xattr-0.8.54  2003-05-05 19:00:55.000000000 +0800
-+++ linux-2.4.20-root/include/linux/fs.h       2003-05-07 18:08:03.000000000 +0800
-@@ -888,7 +888,7 @@ struct inode_operations {
-       int (*setattr) (struct dentry *, struct iattr *);
-       int (*setattr_raw) (struct inode *, struct iattr *);
-       int (*getattr) (struct dentry *, struct iattr *);
--      int (*setxattr) (struct dentry *, const char *, void *, size_t, int);
-+      int (*setxattr) (struct dentry *, const char *, const void *, size_t, int);
-       ssize_t (*getxattr) (struct dentry *, const char *, void *, size_t);
-       ssize_t (*listxattr) (struct dentry *, char *, size_t);
-       int (*removexattr) (struct dentry *, const char *);
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-root/include/linux/mbcache.h  2003-05-07 18:08:03.000000000 +0800
-@@ -0,0 +1,69 @@
-+/*
-+  File: linux/mbcache.h
-+
-+  (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+/* Hardwire the number of additional indexes */
-+#define MB_CACHE_INDEXES_COUNT 1
-+
-+struct mb_cache_entry;
-+
-+struct mb_cache_op {
-+      int (*free)(struct mb_cache_entry *, int);
-+};
-+
-+struct mb_cache {
-+      struct list_head                c_cache_list;
-+      const char                      *c_name;
-+      struct mb_cache_op              c_op;
-+      atomic_t                        c_entry_count;
-+      int                             c_bucket_count;
-+#ifndef MB_CACHE_INDEXES_COUNT
-+      int                             c_indexes_count;
-+#endif
-+      kmem_cache_t                    *c_entry_cache;
-+      struct list_head                *c_block_hash;
-+      struct list_head                *c_indexes_hash[0];
-+};
-+
-+struct mb_cache_entry_index {
-+      struct list_head                o_list;
-+      unsigned int                    o_key;
-+};
-+
-+struct mb_cache_entry {
-+      struct list_head                e_lru_list;
-+      struct mb_cache                 *e_cache;
-+      atomic_t                        e_used;
-+      kdev_t                          e_dev;
-+      unsigned long                   e_block;
-+      struct list_head                e_block_list;
-+      struct mb_cache_entry_index     e_indexes[0];
-+};
-+
-+/* Functions on caches */
-+
-+struct mb_cache * mb_cache_create(const char *, struct mb_cache_op *, size_t,
-+                                int, int);
-+void mb_cache_shrink(struct mb_cache *, kdev_t);
-+void mb_cache_destroy(struct mb_cache *);
-+
-+/* Functions on cache entries */
-+
-+struct mb_cache_entry *mb_cache_entry_alloc(struct mb_cache *);
-+int mb_cache_entry_insert(struct mb_cache_entry *, kdev_t, unsigned long,
-+                        unsigned int[]);
-+void mb_cache_entry_rehash(struct mb_cache_entry *, unsigned int[]);
-+void mb_cache_entry_release(struct mb_cache_entry *);
-+void mb_cache_entry_takeout(struct mb_cache_entry *);
-+void mb_cache_entry_free(struct mb_cache_entry *);
-+struct mb_cache_entry *mb_cache_entry_dup(struct mb_cache_entry *);
-+struct mb_cache_entry *mb_cache_entry_get(struct mb_cache *, kdev_t,
-+                                        unsigned long);
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+struct mb_cache_entry *mb_cache_entry_find_first(struct mb_cache *cache, int,
-+                                               kdev_t, unsigned int);
-+struct mb_cache_entry *mb_cache_entry_find_next(struct mb_cache_entry *, int,
-+                                              kdev_t, unsigned int);
-+#endif
---- linux-2.4.20/kernel/ksyms.c~linux-2.4.20-xattr-0.8.54      2003-05-05 17:43:15.000000000 +0800
-+++ linux-2.4.20-root/kernel/ksyms.c   2003-05-07 18:08:03.000000000 +0800
-@@ -11,6 +11,7 @@
- #include <linux/config.h>
- #include <linux/slab.h>
-+#include <linux/cache_def.h>
- #include <linux/module.h>
- #include <linux/blkdev.h>
- #include <linux/cdrom.h>
-@@ -89,6 +90,7 @@ EXPORT_SYMBOL(exit_mm);
- EXPORT_SYMBOL(exit_files);
- EXPORT_SYMBOL(exit_fs);
- EXPORT_SYMBOL(exit_sighand);
-+EXPORT_SYMBOL(copy_fs_struct);
- /* internal kernel memory management */
- EXPORT_SYMBOL(_alloc_pages);
-@@ -107,6 +109,8 @@ EXPORT_SYMBOL(kmem_cache_validate);
- EXPORT_SYMBOL(kmem_cache_alloc);
- EXPORT_SYMBOL(kmem_cache_free);
- EXPORT_SYMBOL(kmem_cache_size);
-+EXPORT_SYMBOL(register_cache);
-+EXPORT_SYMBOL(unregister_cache);
- EXPORT_SYMBOL(kmalloc);
- EXPORT_SYMBOL(kfree);
- EXPORT_SYMBOL(vfree);
---- linux-2.4.20/mm/vmscan.c~linux-2.4.20-xattr-0.8.54 2002-11-29 07:53:15.000000000 +0800
-+++ linux-2.4.20-root/mm/vmscan.c      2003-05-07 18:08:03.000000000 +0800
-@@ -18,6 +18,7 @@
- #include <linux/kernel_stat.h>
- #include <linux/swap.h>
- #include <linux/swapctl.h>
-+#include <linux/cache_def.h>
- #include <linux/smp_lock.h>
- #include <linux/pagemap.h>
- #include <linux/init.h>
-@@ -34,6 +35,39 @@
-  */
- #define DEF_PRIORITY (6)
-+static DECLARE_MUTEX(other_caches_sem);
-+static LIST_HEAD(cache_definitions);
-+
-+void register_cache(struct cache_definition *cache)
-+{
-+      down(&other_caches_sem);
-+      list_add(&cache->link, &cache_definitions);
-+      up(&other_caches_sem);
-+}
-+
-+void unregister_cache(struct cache_definition *cache)
-+{
-+      down(&other_caches_sem);
-+      list_del(&cache->link);
-+      up(&other_caches_sem);
-+}
-+
-+static void shrink_other_caches(unsigned int priority, int gfp_mask)
-+{
-+      struct list_head *p;
-+
-+      if (down_trylock(&other_caches_sem))
-+              return;
-+
-+      list_for_each_prev(p, &cache_definitions) {
-+              struct cache_definition *cache =
-+                      list_entry(p, struct cache_definition, link);
-+
-+              cache->shrink(priority, gfp_mask);
-+      }
-+      up(&other_caches_sem);
-+}
-+
- /*
-  * The swap-out function returns 1 if it successfully
-  * scanned all the pages it was asked to (`count').
-@@ -577,6 +611,7 @@ static int shrink_caches(zone_t * classz
-       shrink_dcache_memory(priority, gfp_mask);
-       shrink_icache_memory(priority, gfp_mask);
-+      shrink_other_caches(priority, gfp_mask);
- #ifdef CONFIG_QUOTA
-       shrink_dqcache_memory(DEF_PRIORITY, gfp_mask);
- #endif
---- /dev/null  2003-01-30 18:24:37.000000000 +0800
-+++ linux-root/fs/ext3/ext3-exports.c  2003-05-05 18:19:11.000000000 +0800
-@@ -0,0 +1,13 @@
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
-+
-+EXPORT_SYMBOL(ext3_force_commit);
-+EXPORT_SYMBOL(ext3_bread);
-+EXPORT_SYMBOL(ext3_xattr_register);
-+EXPORT_SYMBOL(ext3_xattr_unregister);
-+EXPORT_SYMBOL(ext3_xattr_get);
-+EXPORT_SYMBOL(ext3_xattr_list);
-+EXPORT_SYMBOL(ext3_xattr_set);
-
-_
index 121c27f..aa8c735 100644 (file)
@@ -1,3 +1,4 @@
+Version 45: more robust and general dev_read_only for failover (b=4834)  
 Version 44: fix link_path_walk_it() oops creating .foo in deleted "." (b=5548)
 Version 43: fix remove_suid to not crash 2.6, and do anything on 2.4 (b=5695)
 Version 42: export show_task()
@@ -18,6 +19,6 @@ Version 34: ext3 iopen assertion (b=2517), operations on deleted "." (b=2399)
 --- /dev/null  Fri Aug 30 17:31:37 2002
 +++ linux-2.4.18-18.8.0-l12-braam/include/linux/lustre_version.h       Thu Feb 13 07:58:33 2003
 @@ -0,0 +1 @@
-+#define LUSTRE_KERNEL_VERSION 44
++#define LUSTRE_KERNEL_VERSION 45
 
 _
diff --git a/lustre/kernel_patches/patches/netconsole-2.4.20-rh.patch b/lustre/kernel_patches/patches/netconsole-2.4.20-rh.patch
deleted file mode 100644 (file)
index c5f1ed0..0000000
+++ /dev/null
@@ -1,469 +0,0 @@
-Index: linux-2.4.20-rh/drivers/net/netconsole.c
-===================================================================
---- linux-2.4.20-rh.orig/drivers/net/netconsole.c      2003-07-22 16:02:23.000000000 +0800
-+++ linux-2.4.20-rh/drivers/net/netconsole.c   2003-11-11 07:42:33.000000000 +0800
-@@ -12,6 +12,8 @@
-  *
-  * 2001-09-17    started by Ingo Molnar.
-  * 2002-03-14    simultaneous syslog packet option by Michael K. Johnson
-+ * 2003-10-30    Add sysrq command processing by Wangdi <wangdi@clusterfs.com>
-+ * 
-  */
- /****************************************************************
-@@ -51,6 +53,7 @@
- #include <linux/tty_driver.h>
- #include <linux/etherdevice.h>
- #include <linux/elf.h>
-+#include "netconsole.h"
- static struct net_device *netconsole_dev;
- static u16 source_port, netdump_target_port, netlog_target_port, syslog_target_port;
-@@ -62,12 +65,11 @@
- static unsigned int mhz = 500, idle_timeout;
- static unsigned long long mhz_cycles, jiffy_cycles;
--#include "netconsole.h"
- #define MAX_UDP_CHUNK 1460
- #define MAX_PRINT_CHUNK (MAX_UDP_CHUNK-HEADER_LEN)
--#define DEBUG 0
-+#define DEBUG 0 
- #if DEBUG
- # define Dprintk(x...) printk(KERN_INFO x)
- #else
-@@ -187,6 +189,22 @@
-               }
-       }
- }
-+void (*irqfunc)(int, void *, struct pt_regs *);
-+
-+static void netdump_poll(struct net_device *dev)
-+{
-+      int budget = 1;
-+
-+      disable_irq(dev->irq);
-+      
-+      irqfunc(dev->irq, dev, 0);
-+      
-+      if(dev->poll && test_bit(__LINK_STATE_RX_SCHED, &dev->state))
-+              dev->poll(dev, &budget);
-+
-+      enable_irq(dev->irq);
-+
-+}
- static struct sk_buff * alloc_netconsole_skb(struct net_device *dev, int len, int reserve)
- {
-@@ -209,7 +227,7 @@
-                               once = 0;
-                       }
-                       Dprintk("alloc skb: polling controller ...\n");
--                      dev->poll_controller(dev);
-+                      netdump_poll(dev);
-                       goto repeat;
-               }
-       }
-@@ -231,7 +249,7 @@
-               spin_unlock(&dev->xmit_lock);
-               Dprintk("xmit skb: polling controller ...\n");
--              dev->poll_controller(dev);
-+              netdump_poll(dev);
-               zap_completion_queue();
-               goto repeat_poll;
-       }
-@@ -426,18 +444,79 @@
- static spinlock_t sequence_lock = SPIN_LOCK_UNLOCKED;
- static unsigned int log_offset;
-+static int thread_stopped = 0;
-+/*Interrupt function for netdump */
-+static int sysrq_mode = 0;
-+static int stop_sysrq_thread = 0;
-+#define Set_Sysrq_mode()       (sysrq_mode = 1)
-+#define Clear_Sysrq_mode()     (sysrq_mode = 0)
-+static char send_cache[MAX_PRINT_CHUNK];
-+static unsigned int send_cache_pos = 0;
-+wait_queue_head_t sysrq_thread_queue;
-+wait_queue_head_t sysrq_thread_waiter_queue;
-+
-+#define SEND_MSG_BUFFER(buf, len)                     \
-+do                                                    \
-+{                                                     \
-+      reply_t reply;                                  \
-+      unsigned int flags;                             \
-+      __save_flags(flags);                            \
-+      __cli();                                        \
-+      reply.code = REPLY_LOG;                         \
-+      reply.nr = 0;                                   \
-+      reply.info = 0;                                 \
-+      spin_lock(&sequence_lock);                      \
-+      send_netlog_skb(dev, buf, len, &reply); \
-+      spin_unlock(&sequence_lock);                    \
-+      __restore_flags(flags);                         \
-+}while(0);
-+
-+void netconsole_do_sysrq(req_t *req)
-+{
-+        struct pt_regs regs;
-+      struct net_device *dev = netconsole_dev;
-+
-+      if (!dev)
-+              return;
-+      Set_Sysrq_mode();
-+      get_current_regs(&regs);
-+      handle_sysrq((int)req->from, &regs, NULL);
-+      
-+      if (send_cache_pos != 0){
-+              SEND_MSG_BUFFER(send_cache, send_cache_pos);
-+              memset(send_cache, 0, MAX_PRINT_CHUNK);
-+              send_cache_pos = 0;
-+      } 
-+
-+      Clear_Sysrq_mode();
-+}
- static void write_netconsole_msg(struct console *con, const char *msg0, unsigned int msg_len)
- {
-       int len, left, i;
-       struct net_device *dev;
-       const char *msg = msg0;
-       reply_t reply;
--
-+      
-       dev = netconsole_dev;
-       if (!dev || netdump_mode)
-               return;
--
--      if (dev->poll_controller && netif_running(dev)) {
-+      if (sysrq_mode){
-+              unsigned long total_len = send_cache_pos + msg_len;
-+              unsigned long left_len = msg_len;
-+              while (total_len >=  MAX_PRINT_CHUNK){
-+                      unsigned long send_len = MAX_PRINT_CHUNK - send_cache_pos; 
-+                      memcpy(send_cache + send_cache_pos, msg, send_len);
-+                      SEND_MSG_BUFFER(send_cache, MAX_PRINT_CHUNK);
-+                      send_cache_pos = 0;
-+                      total_len -= MAX_PRINT_CHUNK;
-+                      left_len -= send_len; 
-+              }
-+              if (left_len > 0){
-+                      memcpy(send_cache + send_cache_pos, msg + (msg_len -left_len), left_len);
-+                      send_cache_pos += left_len;
-+              }
-+              return; 
-+      }else if (netif_running(dev)) {
-               unsigned long flags;
-               __save_flags(flags);
-@@ -567,8 +646,6 @@
-       req_t *req;
-       struct net_device *dev;
--      if (!netdump_mode)
--              return NET_RX_SUCCESS;
- #if DEBUG
-       {
-               static int packet_count;
-@@ -722,8 +799,16 @@
-       Dprintk("... netdump from:    %08x.\n", req->from);
-       Dprintk("... netdump to:      %08x.\n", req->to);
--      add_new_req(req);
-+      if (netdump_mode) 
-+              add_new_req(req);
-+      else if (req->command == COMM_SYSRQ){
-+              add_new_req(req);
-+              wake_up(&sysrq_thread_queue);   
-+              return NET_RX_DROP;
-+      }
- out:
-+      if (!netdump_mode)
-+              return NET_RX_SUCCESS;
-       return NET_RX_DROP;
- }
-@@ -763,6 +848,7 @@
-       kunmap_atomic(kaddr, KM_NETDUMP);
- }
-+
- /*
-  * This function waits for the client to acknowledge the receipt
-  * of the netdump startup reply, with the possibility of packets
-@@ -792,7 +878,7 @@
-               // wait 1 sec.
-               udelay(100);
-               Dprintk("handshake: polling controller ...\n");
--              dev->poll_controller(dev);
-+              netdump_poll(dev);              
-               zap_completion_queue();
-               req = get_new_req();
-               if (req)
-@@ -904,7 +990,7 @@
-       while (netdump_mode) {
-               __cli();
-               Dprintk("main netdump loop: polling controller ...\n");
--              dev->poll_controller(dev);
-+              netdump_poll(dev);
-               zap_completion_queue();
- #if !CLI
-               __sti();
-@@ -1009,6 +1095,32 @@
-       printk("NETDUMP END!\n");
-       __restore_flags(flags);
- }
-+static int netconsole_sysrq_schedule(void *arg) 
-+{
-+      struct task_struct *tsk = current;
-+
-+      sprintf(tsk->comm, "sysrq_schedule");
-+      sigfillset(&tsk->blocked);
-+
-+      /* main loop */
-+      thread_stopped = 0;     
-+      for (;;) {
-+              wait_event_interruptible(sysrq_thread_queue,
-+                                       !list_empty(&request_list) || stop_sysrq_thread);
-+              while (!list_empty(&request_list)) {
-+                      req_t *req = get_new_req();
-+                      if (req->command == COMM_SYSRQ)
-+                              netconsole_do_sysrq(req);       
-+              }
-+              if (stop_sysrq_thread)
-+                      break;
-+              wake_up(&sysrq_thread_waiter_queue);
-+      }
-+      thread_stopped = 1;     
-+      wake_up(&sysrq_thread_waiter_queue);
-+      return 0;
-+}
-+
- static char *dev;
- static int netdump_target_eth_byte0 = 255;
-@@ -1087,11 +1199,12 @@
- static struct console netconsole =
-        { flags: CON_ENABLED, write: write_netconsole_msg };
--
- static int init_netconsole(void)
- {
-       struct net_device *ndev = NULL;
-       struct in_device *in_dev;
-+      struct irqaction *action;
-+      int rc = 0;
-       printk(KERN_INFO "netlog: using network device <%s>\n", dev);
-       // this will be valid once the device goes up.
-@@ -1101,10 +1214,6 @@
-               printk(KERN_ERR "netlog: network device %s does not exist, aborting.\n", dev);
-               return -1;
-       }
--      if (!ndev->poll_controller) {
--              printk(KERN_ERR "netlog: %s's network driver does not implement netlogging yet, aborting.\n", dev);
--              return -1;
--      }
-       in_dev = in_dev_get(ndev);
-       if (!in_dev) {
-               printk(KERN_ERR "netlog: network device %s is not an IP protocol device, aborting.\n", dev);
-@@ -1137,8 +1246,6 @@
-       if (!netdump_target_ip && !netlog_target_ip && !syslog_target_ip) {
-               printk(KERN_ERR "netlog: target_ip parameter not specified, aborting.\n");
-               return -1;
--      }
--      if (netdump_target_ip) {
- #define IP(x) ((unsigned char *)&netdump_target_ip)[x]
-               printk(KERN_INFO "netlog: using netdump target IP %u.%u.%u.%u\n",
-                       IP(3), IP(2), IP(1), IP(0));
-@@ -1214,12 +1321,27 @@
-       mhz_cycles = (unsigned long long)mhz * 1000000ULL;
-       jiffy_cycles = (unsigned long long)mhz * (1000000/HZ);
--
--      INIT_LIST_HEAD(&request_list);
--
-+      
-       ndev->rx_hook = netconsole_rx_hook;
-       netdump_func = netconsole_netdump;
-       netconsole_dev = ndev;
-+      /* find irq function of the ndev*/
-+      action=find_irq_action(ndev->irq, ndev);
-+        if (!action) {
-+              printk(KERN_ERR "couldn't find irq handler for <%s>", dev);
-+              return -1;
-+      }
-+      irqfunc = action->handler;
-+
-+      stop_sysrq_thread = 0;
-+      INIT_LIST_HEAD(&request_list);
-+      init_waitqueue_head(&sysrq_thread_queue);
-+      init_waitqueue_head(&sysrq_thread_waiter_queue);
-+      if ((rc = kernel_thread(netconsole_sysrq_schedule, NULL, 0)) < 0 ){
-+              printk(KERN_ERR "Can not start netconsole sysrq thread: rc %d\n", rc); 
-+            return -1; 
-+      }
-+
- #define STARTUP_MSG "[...network console startup...]\n"
-       write_netconsole_msg(NULL, STARTUP_MSG, strlen(STARTUP_MSG));
-@@ -1230,7 +1352,11 @@
- static void cleanup_netconsole(void)
- {
--      printk(KERN_INFO "netlog: network logging shut down.\n");
-+      stop_sysrq_thread = 1;
-+      
-+      wake_up(&sysrq_thread_queue);
-+      wait_event(sysrq_thread_waiter_queue, thread_stopped); 
-+      printk(KERN_INFO"netlog: network logging shut down.\n");
-       unregister_console(&netconsole);
- #define SHUTDOWN_MSG "[...network console shutdown...]\n"
-Index: linux-2.4.20-rh/drivers/net/netconsole.h
-===================================================================
---- linux-2.4.20-rh.orig/drivers/net/netconsole.h      2003-07-22 16:02:23.000000000 +0800
-+++ linux-2.4.20-rh/drivers/net/netconsole.h   2003-10-30 01:48:45.000000000 +0800
-@@ -29,7 +29,7 @@
-  *
-  ****************************************************************/
--#define NETCONSOLE_VERSION 0x04
-+#define NETCONSOLE_VERSION 0x03
- enum netdump_commands {
-       COMM_NONE = 0,
-@@ -42,6 +42,8 @@
-       COMM_START_NETDUMP_ACK = 7,
-       COMM_GET_REGS = 8,
-       COMM_SHOW_STATE = 9,
-+      COMM_START_WRITE_NETDUMP_ACK = 10,
-+        COMM_SYSRQ = 11,
- };
- #define NETDUMP_REQ_SIZE (8+4*4)
-@@ -69,6 +71,7 @@
-       REPLY_REGS = 10,
-       REPLY_MAGIC = 11,
-       REPLY_SHOW_STATE = 12,
-+      REPLY_SYSRQ = 13,
- };
- typedef struct netdump_reply_s {
-@@ -78,4 +81,22 @@
- } reply_t;
- #define HEADER_LEN (1 + sizeof(reply_t))
--
-+/* for netconsole */
-+static inline void get_current_regs(struct pt_regs *regs)
-+{
-+       __asm__ __volatile__("movl %%ebx,%0" : "=m"(regs->ebx));
-+       __asm__ __volatile__("movl %%ecx,%0" : "=m"(regs->ecx));
-+       __asm__ __volatile__("movl %%edx,%0" : "=m"(regs->edx));
-+       __asm__ __volatile__("movl %%esi,%0" : "=m"(regs->esi));
-+       __asm__ __volatile__("movl %%edi,%0" : "=m"(regs->edi));
-+       __asm__ __volatile__("movl %%ebp,%0" : "=m"(regs->ebp));
-+       __asm__ __volatile__("movl %%eax,%0" : "=m"(regs->eax));
-+       __asm__ __volatile__("movl %%esp,%0" : "=m"(regs->esp));
-+       __asm__ __volatile__("movw %%ss, %%ax;" :"=a"(regs->xss));
-+       __asm__ __volatile__("movw %%cs, %%ax;" :"=a"(regs->xcs));
-+       __asm__ __volatile__("movw %%ds, %%ax;" :"=a"(regs->xds));
-+       __asm__ __volatile__("movw %%es, %%ax;" :"=a"(regs->xes));
-+       __asm__ __volatile__("pushfl; popl %0" :"=m"(regs->eflags));
-+       regs->eip = (unsigned long)current_text_addr();
-+}
-+              
-Index: linux-2.4.20-rh/arch/i386/kernel/irq.c
-===================================================================
---- linux-2.4.20-rh.orig/arch/i386/kernel/irq.c        2003-10-30 08:29:38.000000000 +0800
-+++ linux-2.4.20-rh/arch/i386/kernel/irq.c     2003-10-30 08:30:13.000000000 +0800
-@@ -1043,7 +1043,20 @@
-       register_irq_proc(irq);
-       return 0;
- }
-+struct irqaction *find_irq_action(unsigned int irq, void *dev_id)
-+{
-+      struct irqaction *a, *r=0;
-+      spin_lock_irq(&irq_desc[irq].lock);
-+      for(a=irq_desc[irq].action; a; a=a->next) {
-+              if(a->dev_id == dev_id) {
-+                      r=a;
-+                      break;
-+              }
-+      }
-+      spin_unlock_irq(&irq_desc[irq].lock);
-+      return r;
-+}
- static struct proc_dir_entry * root_irq_dir;
- static struct proc_dir_entry * irq_dir [NR_IRQS];
-Index: linux-2.4.20-rh/net/core/dev.c
-===================================================================
---- linux-2.4.20-rh.orig/net/core/dev.c        2003-10-29 01:40:26.000000000 +0800
-+++ linux-2.4.20-rh/net/core/dev.c     2003-10-30 01:48:45.000000000 +0800
-@@ -1475,6 +1475,16 @@
-       skb_bond(skb);
-+      if (unlikely(skb->dev->rx_hook != NULL)) {
-+              int ret;
-+
-+              ret = skb->dev->rx_hook(skb);
-+              if (ret == NET_RX_DROP){
-+                      kfree_skb(skb);
-+                      return ret;
-+              }
-+        }
-+
-       netdev_rx_stat[smp_processor_id()].total++;
- #ifdef CONFIG_NET_FASTROUTE
-Index: linux-2.4.20-rh/include/asm-i386/irq.h
-===================================================================
---- linux-2.4.20-rh.orig/include/asm-i386/irq.h        2003-10-28 16:18:18.000000000 +0800
-+++ linux-2.4.20-rh/include/asm-i386/irq.h     2003-10-30 10:24:49.000000000 +0800
-@@ -38,7 +38,7 @@
- extern void disable_irq_nosync(unsigned int);
- extern void enable_irq(unsigned int);
- extern void release_x86_irqs(struct task_struct *);
--
-+extern struct irqaction *find_irq_action(unsigned int irq, void *dev_id);
- #ifdef CONFIG_X86_LOCAL_APIC
- #define ARCH_HAS_NMI_WATCHDOG         /* See include/linux/nmi.h */
- #endif
-Index: linux-2.4.20-rh/arch/i386/kernel/i386_ksyms.c
-===================================================================
---- linux-2.4.20-rh.orig/arch/i386/kernel/i386_ksyms.c 2003-10-28 19:44:57.000000000 +0800
-+++ linux-2.4.20-rh/arch/i386/kernel/i386_ksyms.c      2003-10-30 11:14:55.000000000 +0800
-@@ -68,6 +68,7 @@
- EXPORT_SYMBOL(iounmap);
- EXPORT_SYMBOL(enable_irq);
- EXPORT_SYMBOL(disable_irq);
-+EXPORT_SYMBOL(find_irq_action);
- EXPORT_SYMBOL(disable_irq_nosync);
- EXPORT_SYMBOL(probe_irq_mask);
- EXPORT_SYMBOL(kernel_thread);
-@@ -199,7 +200,6 @@
- EXPORT_SYMBOL(edd);
- EXPORT_SYMBOL(eddnr);
- #endif
--
- EXPORT_SYMBOL_GPL(show_mem);
- EXPORT_SYMBOL_GPL(show_state);
- EXPORT_SYMBOL_GPL(show_regs);
-Index: linux-2.4.20-rh/kernel/panic.c
-===================================================================
---- linux-2.4.20-rh.orig/kernel/panic.c        2003-10-31 07:25:19.000000000 +0800
-+++ linux-2.4.20-rh/kernel/panic.c     2003-10-31 07:25:59.000000000 +0800
-@@ -219,8 +219,6 @@
-       }
- #endif
--      if (netdump_func)
--              BUG();
-       if (in_interrupt())
-               printk(KERN_EMERG "In interrupt handler - not syncing\n");
-       else if (!current->pid)
diff --git a/lustre/kernel_patches/patches/nfs_export_kernel-2.4.20-rh.patch b/lustre/kernel_patches/patches/nfs_export_kernel-2.4.20-rh.patch
deleted file mode 100644 (file)
index 2f7f190..0000000
+++ /dev/null
@@ -1,739 +0,0 @@
- fs/Makefile        |    3 
- fs/file_table.c    |   11 ++
- fs/inode.c         |   23 ++++-
- fs/namei.c         |   12 ++
- fs/nfsd/export.c   |    5 +
- fs/nfsd/nfsfh.c    |   65 +++++++++++++-
- fs/nfsd/vfs.c      |  240 ++++++++++++++++++++++++++++++++++++++++++++++++-----
- include/linux/fs.h |   10 ++
- kernel/ksyms.c     |    2 
- 9 files changed, 337 insertions(+), 34 deletions(-)
-
---- linux-2.4.20-rh-20.9/fs/file_table.c~nfs_export_kernel-2.4.20-rh   2002-11-29 02:53:15.000000000 +0300
-+++ linux-2.4.20-rh-20.9-alexey/fs/file_table.c        2003-10-08 10:48:38.000000000 +0400
-@@ -82,7 +82,8 @@ struct file * get_empty_filp(void)
-  * and call the open function (if any).  The caller must verify that
-  * inode->i_fop is not NULL.
-  */
--int init_private_file(struct file *filp, struct dentry *dentry, int mode)
-+int init_private_file_it(struct file *filp, struct dentry *dentry, int mode,
-+                       struct lookup_intent *it)
- {
-       memset(filp, 0, sizeof(*filp));
-       filp->f_mode   = mode;
-@@ -90,12 +91,20 @@ int init_private_file(struct file *filp,
-       filp->f_dentry = dentry;
-       filp->f_uid    = current->fsuid;
-       filp->f_gid    = current->fsgid;
-+      if (it)
-+              filp->f_it = it;
-       filp->f_op     = dentry->d_inode->i_fop;
-       if (filp->f_op->open)
-               return filp->f_op->open(dentry->d_inode, filp);
-       else
-               return 0;
- }
-+EXPORT_SYMBOL(init_private_file_it);
-+
-+int init_private_file(struct file *filp, struct dentry *dentry, int mode)
-+{
-+      return init_private_file_it(filp, dentry, mode, NULL);
-+}
- void fput(struct file * file)
- {
---- linux-2.4.20-rh-20.9/fs/inode.c~nfs_export_kernel-2.4.20-rh        2003-09-14 17:35:22.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/fs/inode.c     2003-10-08 10:48:38.000000000 +0400
-@@ -1063,9 +1063,10 @@ struct inode *igrab(struct inode *inode)
- }
--struct inode *iget4(struct super_block *sb, unsigned long ino, find_inode_t find_actor, void *opaque)
-+static inline struct inode *ifind(struct super_block *sb, unsigned long ino,
-+                                struct list_head *head,
-+                                find_inode_t find_actor, void *opaque)
- {
--      struct list_head * head = inode_hashtable + hash(sb,ino);
-       struct inode * inode;
-       spin_lock(&inode_lock);
-@@ -1078,6 +1079,24 @@ struct inode *iget4(struct super_block *
-       }
-       spin_unlock(&inode_lock);
-+      return NULL;
-+}
-+
-+struct inode *ilookup4(struct super_block *sb, unsigned long ino,
-+                     find_inode_t find_actor, void *opaque)
-+{
-+      struct list_head * head = inode_hashtable + hash(sb,ino);
-+      return ifind(sb, ino, head, find_actor, opaque);
-+}
-+
-+struct inode *iget4(struct super_block *sb, unsigned long ino,
-+                  find_inode_t find_actor, void *opaque)
-+{
-+      struct list_head * head = inode_hashtable + hash(sb,ino);
-+      struct inode *inode = ifind(sb, ino, head, find_actor, opaque);
-+      if (inode)
-+              return inode;
-+
-       /*
-        * get_new_inode() will do the right thing, re-trying the search
-        * in case it had to block at any point.
---- linux-2.4.20-rh-20.9/fs/Makefile~nfs_export_kernel-2.4.20-rh       2003-09-14 17:35:20.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/fs/Makefile    2003-10-08 10:49:33.000000000 +0400
-@@ -9,7 +9,8 @@
- O_TARGET := fs.o
--export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o inode.o
-+export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o inode.o \
-+              namei.o file_table.o
- mod-subdirs :=        nls
- obj-y :=      open.o read_write.o devices.o file_table.o buffer.o \
---- linux-2.4.20-rh-20.9/fs/namei.c~nfs_export_kernel-2.4.20-rh        2003-09-14 17:35:22.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/fs/namei.c     2003-10-08 10:48:38.000000000 +0400
-@@ -22,6 +22,7 @@
- #include <linux/dnotify.h>
- #include <linux/smp_lock.h>
- #include <linux/personality.h>
-+#include <linux/module.h>
- #include <asm/namei.h>
- #include <asm/uaccess.h>
-@@ -100,6 +101,7 @@ void intent_release(struct lookup_intent
-               it->it_op_release(it);
- }
-+EXPORT_SYMBOL(intent_release);
- static void *lock_dir(struct inode *dir, struct qstr *name)
- {
-@@ -959,7 +961,8 @@ struct dentry * lookup_hash(struct qstr 
- /* SMP-safe */
--struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
-+struct dentry * lookup_one_len_it(const char * name, struct dentry * base,
-+                                int len, struct lookup_intent *it)
- {
-       unsigned long hash;
-       struct qstr this;
-@@ -979,11 +982,16 @@ struct dentry * lookup_one_len(const cha
-       }
-       this.hash = end_name_hash(hash);
--      return lookup_hash_it(&this, base, NULL);
-+      return lookup_hash_it(&this, base, it);
- access:
-       return ERR_PTR(-EACCES);
- }
-+struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
-+{
-+      return lookup_one_len_it(name, base, len, NULL);
-+}
-+
- /*
-  *    namei()
-  *
---- linux-2.4.20-rh-20.9/fs/nfsd/export.c~nfs_export_kernel-2.4.20-rh  2003-09-13 19:34:35.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/fs/nfsd/export.c       2003-10-08 10:48:38.000000000 +0400
-@@ -222,6 +222,11 @@ exp_export(struct nfsctl_export *nxp)
-       inode = nd.dentry->d_inode;
-       dev = inode->i_dev;
-       ino = inode->i_ino;
-+      if ((inode->i_sb->s_type->fs_flags & FS_NFSEXP_FSID) &&
-+          !(nxp->ex_flags & NFSEXP_FSID)) {
-+              nxp->ex_dev = inode->i_sb->s_dev;
-+              nxp->ex_flags |= NFSEXP_FSID;
-+      }
-       err = -EINVAL;
-       exp = exp_get(clp, dev, ino);
---- linux-2.4.20-rh-20.9/fs/nfsd/nfsfh.c~nfs_export_kernel-2.4.20-rh   2003-09-13 19:34:15.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/fs/nfsd/nfsfh.c        2003-10-08 10:48:38.000000000 +0400
-@@ -36,6 +36,13 @@ struct nfsd_getdents_callback {
-       int sequence;           /* sequence counter */
- };
-+static struct dentry *lookup_it(struct inode *inode, struct dentry * dentry)
-+{
-+      if (inode->i_op->lookup_it)
-+              return inode->i_op->lookup_it(inode, dentry, NULL, 0);
-+      return inode->i_op->lookup(inode, dentry);
-+}
-+
- /*
-  * A rather strange filldir function to capture
-  * the name matching the specified inode number.
-@@ -75,6 +84,8 @@ static int nfsd_get_name(struct dentry *
-       int error;
-       struct file file;
-       struct nfsd_getdents_callback buffer;
-+      struct lookup_intent it;
-+      struct file *filp = NULL;
-       error = -ENOTDIR;
-       if (!dir || !S_ISDIR(dir->i_mode))
-@@ -85,9 +96,37 @@ static int nfsd_get_name(struct dentry *
-       /*
-        * Open the directory ...
-        */
--      error = init_private_file(&file, dentry, FMODE_READ);
--      if (error)
-+      if (dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if ((dentry->d_flags & DCACHE_NFSD_DISCONNECTED) &&
-+                  (dentry->d_parent == dentry) ) {
-+                      it.it_op_release = NULL;
-+                      /*
-+                       * XXX Temporary Hack: Simulate init_private_file without
-+                       * f_op->open for disconnected dentry as we don't have
-+                       * actual dentry->d_name to revalidate in revalidate_it()
-+                       */
-+                      filp = &file;
-+                      memset(filp, 0, sizeof(*filp));
-+                      filp->f_mode   = FMODE_READ;
-+                      atomic_set(&filp->f_count, 1);
-+                      filp->f_dentry = dentry;
-+                      filp->f_uid = current->fsuid;
-+                      filp->f_gid = current->fsgid;
-+                      filp->f_op = dentry->d_inode->i_fop;
-+                      error = 0;
-+              } else {
-+                      intent_init(&it, IT_OPEN, 0);
-+                      error = revalidate_it(dentry, &it);
-+                      if (error)
-+                              goto out;
-+                      error = init_private_file_it(&file, dentry, FMODE_READ, &it);
-+              }
-+      } else {
-+              error = init_private_file_it(&file, dentry, FMODE_READ, NULL);
-+      }
-+      if (error)
-               goto out;
-+
-       error = -EINVAL;
-       if (!file.f_op->readdir)
-               goto out_close;
-@@ -113,9 +152,12 @@ static int nfsd_get_name(struct dentry *
-       }
- out_close:
--      if (file.f_op->release)
-+      if (file.f_op->release && !filp)
-               file.f_op->release(dir, &file);
- out:
-+      if (dentry->d_op && dentry->d_op->d_revalidate_it &&
-+          it.it_op_release && !filp)
-+              intent_release(&it);
-       return error;
- }
-@@ -274,7 +317,7 @@ struct dentry *nfsd_findparent(struct de
-        * it is well connected.  But nobody returns different dentrys do they?
-        */
-       down(&child->d_inode->i_sem);
--      pdentry = child->d_inode->i_op->lookup(child->d_inode, tdentry);
-+      pdentry = lookup_it(child->d_inode, tdentry);
-       up(&child->d_inode->i_sem);
-       d_drop(tdentry); /* we never want ".." hashed */
-       if (!pdentry && tdentry->d_inode == NULL) {
-@@ -306,6 +349,8 @@ struct dentry *nfsd_findparent(struct de
-                               igrab(tdentry->d_inode);
-                               pdentry->d_flags |= DCACHE_NFSD_DISCONNECTED;
-                       }
-+                      if (child->d_op && child->d_op->d_revalidate_it)
-+                              pdentry->d_op = child->d_op;
-               }
-               if (pdentry == NULL)
-                       pdentry = ERR_PTR(-ENOMEM);
-@@ -463,6 +508,8 @@ find_fh_dentry(struct super_block *sb, _
-               struct dentry *pdentry;
-               struct inode *parent;
-+              if (result->d_op && result->d_op->d_revalidate_it)
-+                      dentry->d_op = result->d_op;
-               pdentry = nfsd_findparent(dentry);
-               err = PTR_ERR(pdentry);
-               if (IS_ERR(pdentry))
-@@ -669,6 +716,10 @@ fh_verify(struct svc_rqst *rqstp, struct
-       inode = dentry->d_inode;
-+      /* cache coherency for non-device filesystems */
-+      if (inode->i_op && inode->i_op->revalidate_it)
-+              inode->i_op->revalidate_it(dentry, NULL);
-+
-       /* Type check. The correct error return for type mismatches
-        * does not seem to be generally agreed upon. SunOS seems to
-        * use EISDIR if file isn't S_IFREG; a comment in the NFSv3
-@@ -912,8 +964,9 @@ out_negative:
-               dentry->d_parent->d_name.name, dentry->d_name.name);
-       goto out;
- out_uptodate:
--      printk(KERN_ERR "fh_update: %s/%s already up-to-date!\n",
--              dentry->d_parent->d_name.name, dentry->d_name.name);
-+      if (!dentry->d_parent->d_inode->i_op->mkdir_raw)
-+              printk(KERN_ERR "fh_update: %s/%s already up-to-date!\n",
-+                    dentry->d_parent->d_name.name, dentry->d_name.name);
-       goto out;
- }
---- linux-2.4.20-rh-20.9/fs/nfsd/vfs.c~nfs_export_kernel-2.4.20-rh     2003-09-13 19:34:15.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/fs/nfsd/vfs.c  2003-10-08 10:48:38.000000000 +0400
-@@ -77,6 +77,126 @@ struct raparms {
- static struct raparms *               raparml;
- static struct raparms *               raparm_cache;
-+static int link_raw(struct dentry *dold, struct dentry *ddir,
-+                  struct dentry *dnew)
-+{
-+      int err;
-+
-+      struct nameidata old_nd = { .dentry = dold };
-+      struct nameidata nd = { .dentry = ddir, .last = dnew->d_name };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->link_raw(&old_nd, &nd);
-+      d_instantiate(dnew, dold->d_inode);
-+      if (dold->d_inode->i_op && dold->d_inode->i_op->revalidate_it)
-+              dold->d_inode->i_op->revalidate_it(dnew, NULL);
-+
-+      return err;
-+}
-+
-+static int unlink_raw(struct dentry *dentry, char *fname, int flen,
-+                    struct dentry *rdentry)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->unlink_raw(&nd);
-+      if (!err)
-+              d_delete(rdentry);
-+
-+      return err;
-+}
-+
-+static int rmdir_raw(struct dentry *dentry, char *fname, int flen,
-+                   struct dentry *rdentry)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->rmdir_raw(&nd);
-+      if (!err) {
-+              rdentry->d_inode->i_flags |= S_DEAD;
-+              d_delete(rdentry);
-+      }
-+
-+      return err;
-+}
-+
-+static int symlink_raw(struct dentry *dentry, char *fname, int flen,
-+                     char *path)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->symlink_raw(&nd, path);
-+
-+      return err;
-+}
-+
-+static int mkdir_raw(struct dentry *dentry, char *fname, int flen, int mode)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->mkdir_raw(&nd, mode);
-+
-+      return err;
-+}
-+
-+static int mknod_raw(struct dentry *dentry, char *fname, int flen, int mode,
-+                   dev_t dev)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->mknod_raw(&nd, mode, dev);
-+
-+      return err;
-+}
-+
-+static int rename_raw(struct dentry *fdentry, struct dentry *tdentry,
-+                    struct dentry *odentry, struct dentry *ndentry)
-+{
-+      int err;
-+
-+      struct nameidata old_nd = { .dentry = fdentry, .last = odentry->d_name};
-+      struct nameidata new_nd = { .dentry = tdentry, .last = ndentry->d_name};
-+      struct inode_operations *op = old_nd.dentry->d_inode->i_op;
-+      err = op->rename_raw(&old_nd, &new_nd);
-+      d_move(odentry, ndentry);
-+
-+      return err;
-+}
-+
-+static int setattr_raw(struct inode *inode, struct iattr *iap)
-+{
-+      int err;
-+
-+      iap->ia_valid |= ATTR_RAW;
-+      err = inode->i_op->setattr_raw(inode, iap);
-+
-+      return err;
-+}
-+
-+int revalidate_it(struct dentry *dentry, struct lookup_intent *it)
-+{
-+      int err = 0;
-+
-+      if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if (!dentry->d_op->d_revalidate_it(dentry, 0, it) &&
-+                      !d_invalidate(dentry)) {
-+                      err = -EINVAL;
-+                      return err;
-+              }
-+      }
-+
-+      return err;
-+}
-+
- /*
-  * Look up one component of a pathname.
-  * N.B. After this call _both_ fhp and resfh need an fh_put
-@@ -302,7 +424,10 @@ nfsd_setattr(struct svc_rqst *rqstp, str
-       }
-       err = nfserr_notsync;
-       if (!check_guard || guardtime == inode->i_ctime) {
--              err = notify_change(dentry, iap);
-+              if (dentry->d_inode->i_op && dentry->d_inode->i_op->setattr_raw)
-+                      err = setattr_raw(dentry->d_inode, iap);
-+              else
-+                      err = notify_change(dentry, iap);
-               err = nfserrno(err);
-       }
-       if (size_change) {
-@@ -429,6 +554,7 @@ nfsd_open(struct svc_rqst *rqstp, struct
- {
-       struct dentry   *dentry;
-       struct inode    *inode;
-+      struct lookup_intent it;
-       int             err;
-       /* If we get here, then the client has already done an "open", and (hopefully)
-@@ -475,6 +601,18 @@ nfsd_open(struct svc_rqst *rqstp, struct
-               filp->f_mode  = FMODE_READ;
-       }
-+#ifndef O_OWNER_OVERRIDE
-+#define O_OWNER_OVERRIDE 0200000000
-+#endif
-+      intent_init(&it, IT_OPEN, (filp->f_flags & ~O_ACCMODE) | filp->f_mode |
-+                  O_OWNER_OVERRIDE);
-+
-+      err = revalidate_it(dentry, &it);
-+      if (err)
-+              goto out_nfserr;
-+
-+      filp->f_it = &it;
-+
-       err = 0;
-       if (filp->f_op && filp->f_op->open) {
-               err = filp->f_op->open(inode, filp);
-@@ -489,6 +623,9 @@ nfsd_open(struct svc_rqst *rqstp, struct
-               }
-       }
- out_nfserr:
-+      if (it.it_op_release)
-+              intent_release(&it);
-+
-       if (err)
-               err = nfserrno(err);
- out:
-@@ -820,7 +958,7 @@ nfsd_create(struct svc_rqst *rqstp, stru
- {
-       struct dentry   *dentry, *dchild;
-       struct inode    *dirp;
--      int             err;
-+      int             err, error = -EOPNOTSUPP;
-       err = nfserr_perm;
-       if (!flen)
-@@ -836,20 +974,47 @@ nfsd_create(struct svc_rqst *rqstp, stru
-       dentry = fhp->fh_dentry;
-       dirp = dentry->d_inode;
-+      switch (type) {
-+      case S_IFDIR:
-+              if (dirp->i_op->mkdir_raw)
-+                      error = mkdir_raw(dentry, fname, flen, iap->ia_mode);
-+              break;
-+      case S_IFCHR:
-+      case S_IFBLK:
-+      case S_IFIFO:
-+      case S_IFSOCK:
-+      case S_IFREG:
-+              if (dirp->i_op->mknod_raw) {
-+                      if (type == S_IFREG)
-+                              rdev = 0;
-+                      error = mknod_raw(dentry, fname,flen,iap->ia_mode,rdev);
-+              }
-+              break;
-+      default:
-+              printk("nfsd: bad file type %o in nfsd_create\n", type);
-+      }
-+      if (error && error != -EOPNOTSUPP) {
-+              err = error;
-+              goto out_nfserr;
-+      }
-+
-       err = nfserr_notdir;
--      if(!dirp->i_op || !dirp->i_op->lookup)
-+      if (!dirp->i_op || !(dirp->i_op->lookup || dirp->i_op->lookup_it))
-               goto out;
-       /*
-        * Check whether the response file handle has been verified yet.
-        * If it has, the parent directory should already be locked.
-        */
--      if (!resfhp->fh_dentry) {
--              /* called from nfsd_proc_mkdir, or possibly nfsd3_proc_create */
--              fh_lock(fhp);
-+      if (!resfhp->fh_dentry || dirp->i_op->lookup_it) {
-+              /* called from nfsd_proc_mkdir, or possibly nfsd3_proc_create
-+               * and nfsd_proc_create in case of lustre */
-+              if (!resfhp->fh_dentry)
-+                      fh_lock(fhp);
-               dchild = lookup_one_len(fname, dentry, flen);
-               err = PTR_ERR(dchild);
-               if (IS_ERR(dchild))
-                       goto out_nfserr;
-+              resfhp->fh_dentry = NULL;
-               err = fh_compose(resfhp, fhp->fh_export, dchild, fhp);
-               if (err)
-                       goto out;
-@@ -870,10 +1032,12 @@ nfsd_create(struct svc_rqst *rqstp, stru
-        * Make sure the child dentry is still negative ...
-        */
-       err = nfserr_exist;
--      if (dchild->d_inode) {
--              dprintk("nfsd_create: dentry %s/%s not negative!\n",
--                      dentry->d_name.name, dchild->d_name.name);
--              goto out; 
-+      if (error == -EOPNOTSUPP) {
-+              if (dchild->d_inode) {
-+                      dprintk("nfsd_create: dentry %s/%s not negative!\n",
-+                              dentry->d_name.name, dchild->d_name.name);
-+                      goto out;
-+              }
-       }
-       if (!(iap->ia_valid & ATTR_MODE))
-@@ -886,16 +1050,19 @@ nfsd_create(struct svc_rqst *rqstp, stru
-       err = nfserr_perm;
-       switch (type) {
-       case S_IFREG:
--              err = vfs_create(dirp, dchild, iap->ia_mode);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_create(dirp, dchild, iap->ia_mode);
-               break;
-       case S_IFDIR:
--              err = vfs_mkdir(dirp, dchild, iap->ia_mode);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_mkdir(dirp, dchild, iap->ia_mode);
-               break;
-       case S_IFCHR:
-       case S_IFBLK:
-       case S_IFIFO:
-       case S_IFSOCK:
--              err = vfs_mknod(dirp, dchild, iap->ia_mode, rdev);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_mknod(dirp, dchild, iap->ia_mode, rdev);
-               break;
-       default:
-               printk("nfsd: bad file type %o in nfsd_create\n", type);
-@@ -964,7 +1131,13 @@ nfsd_create_v3(struct svc_rqst *rqstp, s
-       /* Get all the sanity checks out of the way before
-        * we lock the parent. */
-       err = nfserr_notdir;
--      if(!dirp->i_op || !dirp->i_op->lookup)
-+      if (dirp->i_op->mknod_raw) {
-+              err = mknod_raw(dentry, fname, flen, iap->ia_mode, 0);
-+              if (err && err != -EOPNOTSUPP)
-+                      goto out_nfserr;
-+      }
-+
-+      if (!dirp->i_op || !(dirp->i_op->lookup || dirp->i_op->lookup_it))
-               goto out;
-       fh_lock(fhp);
-@@ -1015,6 +1188,8 @@ nfsd_create_v3(struct svc_rqst *rqstp, s
-               case NFS3_CREATE_GUARDED:
-                       err = nfserr_exist;
-               }
-+              if (dirp->i_op->mknod_raw)
-+                      err = 0;
-               goto out;
-       }
-@@ -1121,7 +1296,7 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-                               struct iattr *iap)
- {
-       struct dentry   *dentry, *dnew;
--      int             err, cerr;
-+      int             err, cerr, error = -EOPNOTSUPP;
-       err = nfserr_noent;
-       if (!flen || !plen)
-@@ -1135,12 +1310,18 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-               goto out;
-       fh_lock(fhp);
-       dentry = fhp->fh_dentry;
-+
-+      if (dentry->d_inode->i_op->symlink_raw)
-+              error = symlink_raw(dentry, fname, flen, path);
-+
-       dnew = lookup_one_len(fname, dentry, flen);
-       err = PTR_ERR(dnew);
-       if (IS_ERR(dnew))
-               goto out_nfserr;
--      err = vfs_symlink(dentry->d_inode, dnew, path);
-+      err = error;
-+      if (err == -EOPNOTSUPP || !dentry->d_inode->i_op->symlink_raw)
-+              err = vfs_symlink(dentry->d_inode, dnew, path);
-       if (!err) {
-               if (EX_ISSYNC(fhp->fh_export))
-                       nfsd_sync_dir(dentry);
-@@ -1150,7 +1331,10 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-                               iap->ia_valid |= ATTR_CTIME;
-                               iap->ia_mode = (iap->ia_mode&S_IALLUGO)
-                                       | S_IFLNK;
--                              err = notify_change(dnew, iap);
-+                              if (dnew->d_inode->i_op && dnew->d_inode->i_op->setattr_raw)
-+                                      err = setattr_raw(dnew->d_inode, iap);
-+                              else
-+                                      err = notify_change(dnew, iap);
-                               if (!err && EX_ISSYNC(fhp->fh_export))
-                                       write_inode_now(dentry->d_inode, 1);
-                      }
-@@ -1208,7 +1392,10 @@ nfsd_link(struct svc_rqst *rqstp, struct
-       dold = tfhp->fh_dentry;
-       dest = dold->d_inode;
--      err = vfs_link(dold, dirp, dnew);
-+      if (dirp->i_op->link_raw)
-+              err = link_raw(dold, ddir, dnew);
-+      else
-+              err = vfs_link(dold, dirp, dnew);
-       if (!err) {
-               if (EX_ISSYNC(ffhp->fh_export)) {
-                       nfsd_sync_dir(ddir);
-@@ -1293,7 +1480,10 @@ nfsd_rename(struct svc_rqst *rqstp, stru
-                       err = nfserr_perm;
-       } else
- #endif
--      err = vfs_rename(fdir, odentry, tdir, ndentry);
-+      if (fdir->i_op->rename_raw)
-+              err = rename_raw(fdentry, tdentry, odentry, ndentry);
-+      else
-+              err = vfs_rename(fdir, odentry, tdir, ndentry);
-       if (!err && EX_ISSYNC(tfhp->fh_export)) {
-               nfsd_sync_dir(tdentry);
-               nfsd_sync_dir(fdentry);
-@@ -1314,7 +1504,7 @@ nfsd_rename(struct svc_rqst *rqstp, stru
-       fill_post_wcc(tfhp);
-       double_up(&tdir->i_sem, &fdir->i_sem);
-       ffhp->fh_locked = tfhp->fh_locked = 0;
--      
-+
- out:
-       return err;
- }
-@@ -1360,9 +1550,15 @@ nfsd_unlink(struct svc_rqst *rqstp, stru
-                       err = nfserr_perm;
-               } else
- #endif
--              err = vfs_unlink(dirp, rdentry);
-+              if (dirp->i_op->unlink_raw)
-+                      err = unlink_raw(dentry, fname, flen, rdentry);
-+              else
-+                      err = vfs_unlink(dirp, rdentry);
-       } else { /* It's RMDIR */
--              err = vfs_rmdir(dirp, rdentry);
-+              if (dirp->i_op->rmdir_raw)
-+                      err = rmdir_raw(dentry, fname, flen, rdentry);
-+              else
-+                      err = vfs_rmdir(dirp, rdentry);
-       }
-       dput(rdentry);
---- linux-2.4.20-rh-20.9/include/linux/fs.h~nfs_export_kernel-2.4.20-rh        2003-09-14 17:35:22.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/include/linux/fs.h     2003-10-08 10:48:38.000000000 +0400
-@@ -94,6 +94,8 @@ extern int leases_enable, dir_notify_ena
- #define FS_SINGLE     8 /* Filesystem that can have only one superblock */
- #define FS_NOMOUNT    16 /* Never mount from userland */
- #define FS_LITTER     32 /* Keeps the tree in dcache */
-+#define FS_NFSEXP_FSID        64 /* Use file system specific fsid for
-+                          * exporting non device filesystems. */
- #define FS_ODD_RENAME 32768   /* Temporary stuff; will go away as soon
-                                 * as nfs_rename() will be cleaned up
-                                 */
-@@ -1124,6 +1127,9 @@ extern int open_namei_it(const char *fil
-                        struct nameidata *nd, struct lookup_intent *it);
- extern struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-                           int flags, struct lookup_intent *it);
-+extern int revalidate_it(struct dentry *dentry, struct lookup_intent *it);
-+extern int init_private_file_it(struct file *, struct dentry *dentry, int mode,
-+                              struct lookup_intent *it);
- extern int filp_close(struct file *, fl_owner_t id);
- extern char * getname(const char *);
-@@ -1423,6 +1429,8 @@ extern void path_release(struct nameidat
- extern int follow_down(struct vfsmount **, struct dentry **);
- extern int follow_up(struct vfsmount **, struct dentry **);
- extern struct dentry * lookup_one_len(const char *, struct dentry *, int);
-+extern struct dentry * lookup_one_len_it(const char *, struct dentry *, int,
-+                                       struct lookup_intent *);
- extern struct dentry * lookup_hash(struct qstr *, struct dentry *);
- #define user_path_walk(name,nd)        __user_walk(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd)
- #define user_path_walk_link(name,nd) __user_walk(name, LOOKUP_POSITIVE, nd)
-@@ -1439,6 +1447,8 @@ extern ino_t iunique(struct super_block 
- typedef int (*find_inode_t)(struct inode *, unsigned long, void *);
- extern struct inode * iget4(struct super_block *, unsigned long, find_inode_t, void *);
-+extern struct inode * ilookup4(struct super_block *, unsigned long,
-+                             find_inode_t, void *);
- static inline struct inode *iget(struct super_block *sb, unsigned long ino)
- {
-       return iget4(sb, ino, NULL, NULL);
---- linux-2.4.20-rh-20.9/kernel/ksyms.c~nfs_export_kernel-2.4.20-rh    2003-09-14 17:35:20.000000000 +0400
-+++ linux-2.4.20-rh-20.9-alexey/kernel/ksyms.c 2003-10-08 10:48:38.000000000 +0400
-@@ -164,6 +164,7 @@ EXPORT_SYMBOL(fget);
- EXPORT_SYMBOL(igrab);
- EXPORT_SYMBOL(iunique);
- EXPORT_SYMBOL(iget4);
-+EXPORT_SYMBOL(ilookup4);
- EXPORT_SYMBOL(iput);
- EXPORT_SYMBOL(inode_init_once);
- EXPORT_SYMBOL(force_delete);
-@@ -175,6 +176,7 @@ EXPORT_SYMBOL(path_walk);
- EXPORT_SYMBOL(path_release);
- EXPORT_SYMBOL(__user_walk);
- EXPORT_SYMBOL(lookup_one_len);
-+EXPORT_SYMBOL(lookup_one_len_it);
- EXPORT_SYMBOL(lookup_hash);
- EXPORT_SYMBOL(sys_close);
- EXPORT_SYMBOL(sys_read);
-
-_
diff --git a/lustre/kernel_patches/patches/nfs_export_kernel-2.4.20.patch b/lustre/kernel_patches/patches/nfs_export_kernel-2.4.20.patch
deleted file mode 100644 (file)
index ba6fa2b..0000000
+++ /dev/null
@@ -1,735 +0,0 @@
-diff -uprN linux/fs/Makefile linux-2.4.20/fs/Makefile
---- linux/fs/Makefile  Sun Oct  5 21:52:51 2003
-+++ linux-2.4.20/fs/Makefile   Sun Oct  5 21:47:45 2003
-@@ -7,7 +7,8 @@
- O_TARGET := fs.o
--export-objs :=        filesystems.o open.o dcache.o buffer.o inode.o
-+export-objs :=        filesystems.o open.o dcache.o buffer.o inode.o namei.o \
-+              file_table.o
- mod-subdirs :=        nls
- obj-y :=      open.o read_write.o devices.o file_table.o buffer.o \
-diff -uprN linux/fs/file_table.c linux-2.4.20/fs/file_table.c
---- linux/fs/file_table.c      Fri Nov 29 05:23:15 2002
-+++ linux-2.4.20/fs/file_table.c       Sun Oct  5 21:47:45 2003
-@@ -82,7 +82,8 @@ struct file * get_empty_filp(void)
-  * and call the open function (if any).  The caller must verify that
-  * inode->i_fop is not NULL.
-  */
--int init_private_file(struct file *filp, struct dentry *dentry, int mode)
-+int init_private_file_it(struct file *filp, struct dentry *dentry, int mode,
-+                       struct lookup_intent *it)
- {
-       memset(filp, 0, sizeof(*filp));
-       filp->f_mode   = mode;
-@@ -90,12 +91,20 @@ int init_private_file(struct file *filp,
-       filp->f_dentry = dentry;
-       filp->f_uid    = current->fsuid;
-       filp->f_gid    = current->fsgid;
-+      if (it)
-+              filp->f_it = it;
-       filp->f_op     = dentry->d_inode->i_fop;
-       if (filp->f_op->open)
-               return filp->f_op->open(dentry->d_inode, filp);
-       else
-               return 0;
- }
-+EXPORT_SYMBOL(init_private_file_it);
-+
-+int init_private_file(struct file *filp, struct dentry *dentry, int mode)
-+{
-+      return init_private_file_it(filp, dentry, mode, NULL);
-+}
- void fput(struct file * file)
- {
-diff -uprN linux/fs/inode.c linux-2.4.20/fs/inode.c
---- linux/fs/inode.c   Sun Oct  5 21:52:49 2003
-+++ linux-2.4.20/fs/inode.c    Sun Oct  5 21:47:45 2003
-@@ -970,9 +970,10 @@ struct inode *igrab(struct inode *inode)
- }
--struct inode *iget4(struct super_block *sb, unsigned long ino, find_inode_t find_actor, void *opaque)
-+static inline struct inode *ifind(struct super_block *sb, unsigned long ino,
-+                                struct list_head *head,
-+                                find_inode_t find_actor, void *opaque)
- {
--      struct list_head * head = inode_hashtable + hash(sb,ino);
-       struct inode * inode;
-       spin_lock(&inode_lock);
-@@ -985,6 +986,24 @@ struct inode *iget4(struct super_block *
-       }
-       spin_unlock(&inode_lock);
-+      return NULL;
-+}
-+
-+struct inode *ilookup4(struct super_block *sb, unsigned long ino,
-+                     find_inode_t find_actor, void *opaque)
-+{
-+      struct list_head * head = inode_hashtable + hash(sb,ino);
-+      return ifind(sb, ino, head, find_actor, opaque);
-+}
-+
-+struct inode *iget4(struct super_block *sb, unsigned long ino,
-+                  find_inode_t find_actor, void *opaque)
-+{
-+      struct list_head * head = inode_hashtable + hash(sb,ino);
-+      struct inode *inode = ifind(sb, ino, head, find_actor, opaque);
-+      if (inode)
-+              return inode;
-+
-       /*
-        * get_new_inode() will do the right thing, re-trying the search
-        * in case it had to block at any point.
-diff -uprN linux/fs/namei.c linux-2.4.20/fs/namei.c
---- linux/fs/namei.c   Sun Oct  5 21:52:48 2003
-+++ linux-2.4.20/fs/namei.c    Sun Oct  5 21:47:45 2003
-@@ -22,6 +22,7 @@
- #include <linux/dnotify.h>
- #include <linux/smp_lock.h>
- #include <linux/personality.h>
-+#include <linux/module.h>
- #include <asm/namei.h>
- #include <asm/uaccess.h>
-@@ -100,6 +101,7 @@ void intent_release(struct lookup_intent
-               it->it_op_release(it);
- }
-+EXPORT_SYMBOL(intent_release);
- /* In order to reduce some races, while at the same time doing additional
-  * checking and hopefully speeding things up, we copy filenames to the
-@@ -900,7 +902,8 @@ struct dentry * lookup_hash(struct qstr 
- /* SMP-safe */
--struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
-+struct dentry * lookup_one_len_it(const char * name, struct dentry * base,
-+                                int len, struct lookup_intent *it)
- {
-       unsigned long hash;
-       struct qstr this;
-@@ -920,11 +923,16 @@ struct dentry * lookup_one_len(const cha
-       }
-       this.hash = end_name_hash(hash);
--      return lookup_hash_it(&this, base, NULL);
-+      return lookup_hash_it(&this, base, it);
- access:
-       return ERR_PTR(-EACCES);
- }
-+struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
-+{
-+      return lookup_one_len_it(name, base, len, NULL);
-+}
-+
- /*
-  *    namei()
-  *
-diff -uprN linux/fs/nfsd/export.c linux-2.4.20/fs/nfsd/export.c
---- linux/fs/nfsd/export.c     Fri Nov 29 05:23:15 2002
-+++ linux-2.4.20/fs/nfsd/export.c      Sun Oct  5 22:25:20 2003
-@@ -222,6 +222,11 @@ exp_export(struct nfsctl_export *nxp)
-       inode = nd.dentry->d_inode;
-       dev = inode->i_dev;
-       ino = inode->i_ino;
-+      if ((inode->i_sb->s_type->fs_flags & FS_NFSEXP_FSID) &&
-+          !(nxp->ex_flags & NFSEXP_FSID)) {
-+              nxp->ex_dev = inode->i_sb->s_dev;
-+              nxp->ex_flags |= NFSEXP_FSID;
-+      }
-       err = -EINVAL;
-       exp = exp_get(clp, dev, ino);
-diff -uprN linux/fs/nfsd/nfsfh.c linux-2.4.20/fs/nfsd/nfsfh.c
---- linux/fs/nfsd/nfsfh.c      Fri Nov 29 05:23:15 2002
-+++ linux-2.4.20/fs/nfsd/nfsfh.c       Sun Oct  5 21:47:45 2003
-@@ -36,6 +36,13 @@ struct nfsd_getdents_callback {
-       int sequence;           /* sequence counter */
- };
-+static struct dentry *lookup_it(struct inode *inode, struct dentry * dentry)
-+{
-+      if (inode->i_op->lookup_it)
-+              return inode->i_op->lookup_it(inode, dentry, NULL, 0);
-+      return inode->i_op->lookup(inode, dentry);
-+}
-+
- /*
-  * A rather strange filldir function to capture
-  * the name matching the specified inode number.
-@@ -75,6 +84,8 @@ static int nfsd_get_name(struct dentry *
-       int error;
-       struct file file;
-       struct nfsd_getdents_callback buffer;
-+      struct lookup_intent it;
-+      struct file *filp = NULL;
-       error = -ENOTDIR;
-       if (!dir || !S_ISDIR(dir->i_mode))
-@@ -85,9 +96,37 @@ static int nfsd_get_name(struct dentry *
-       /*
-        * Open the directory ...
-        */
--      error = init_private_file(&file, dentry, FMODE_READ);
--      if (error)
-+      if (dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if ((dentry->d_flags & DCACHE_NFSD_DISCONNECTED) &&
-+                  (dentry->d_parent == dentry) ) {
-+                      it.it_op_release = NULL;
-+                      /*
-+                       * XXX Temporary Hack: Simulate init_private_file without
-+                       * f_op->open for disconnected dentry as we don't have
-+                       * actual dentry->d_name to revalidate in revalidate_it()
-+                       */
-+                      filp = &file;
-+                      memset(filp, 0, sizeof(*filp));
-+                      filp->f_mode   = FMODE_READ;
-+                      atomic_set(&filp->f_count, 1);
-+                      filp->f_dentry = dentry;
-+                      filp->f_uid = current->fsuid;
-+                      filp->f_gid = current->fsgid;
-+                      filp->f_op = dentry->d_inode->i_fop;
-+                      error = 0;
-+              } else {
-+                      intent_init(&it, IT_OPEN, 0);
-+                      error = revalidate_it(dentry, &it);
-+                      if (error)
-+                              goto out;
-+                      error = init_private_file_it(&file, dentry, FMODE_READ, &it);
-+              }
-+      } else {
-+              error = init_private_file_it(&file, dentry, FMODE_READ, NULL);
-+      }
-+      if (error)
-               goto out;
-+
-       error = -EINVAL;
-       if (!file.f_op->readdir)
-               goto out_close;
-@@ -113,9 +152,12 @@ static int nfsd_get_name(struct dentry *
-       }
- out_close:
--      if (file.f_op->release)
-+      if (file.f_op->release && !filp)
-               file.f_op->release(dir, &file);
- out:
-+      if (dentry->d_op && dentry->d_op->d_revalidate_it &&
-+          it.it_op_release && !filp)
-+              intent_release(&it);
-       return error;
- }
-@@ -274,7 +317,7 @@ struct dentry *nfsd_findparent(struct de
-        * it is well connected.  But nobody returns different dentrys do they?
-        */
-       down(&child->d_inode->i_sem);
--      pdentry = child->d_inode->i_op->lookup(child->d_inode, tdentry);
-+      pdentry = lookup_it(child->d_inode, tdentry);
-       up(&child->d_inode->i_sem);
-       d_drop(tdentry); /* we never want ".." hashed */
-       if (!pdentry && tdentry->d_inode == NULL) {
-@@ -306,6 +349,8 @@ struct dentry *nfsd_findparent(struct de
-                               igrab(tdentry->d_inode);
-                               pdentry->d_flags |= DCACHE_NFSD_DISCONNECTED;
-                       }
-+                      if (child->d_op && child->d_op->d_revalidate_it)
-+                              pdentry->d_op = child->d_op;
-               }
-               if (pdentry == NULL)
-                       pdentry = ERR_PTR(-ENOMEM);
-@@ -463,6 +508,8 @@ find_fh_dentry(struct super_block *sb, _
-               struct dentry *pdentry;
-               struct inode *parent;
-+              if (result->d_op && result->d_op->d_revalidate_it)
-+                      dentry->d_op = result->d_op;
-               pdentry = nfsd_findparent(dentry);
-               err = PTR_ERR(pdentry);
-               if (IS_ERR(pdentry))
-@@ -662,6 +709,10 @@ fh_verify(struct svc_rqst *rqstp, struct
-       inode = dentry->d_inode;
-+      /* cache coherency for non-device filesystems */
-+      if (inode->i_op && inode->i_op->revalidate_it)
-+              inode->i_op->revalidate_it(dentry, NULL);
-+
-       /* Type check. The correct error return for type mismatches
-        * does not seem to be generally agreed upon. SunOS seems to
-        * use EISDIR if file isn't S_IFREG; a comment in the NFSv3
-@@ -900,8 +952,9 @@ out_negative:
-               dentry->d_parent->d_name.name, dentry->d_name.name);
-       goto out;
- out_uptodate:
--      printk(KERN_ERR "fh_update: %s/%s already up-to-date!\n",
--              dentry->d_parent->d_name.name, dentry->d_name.name);
-+      if (!dentry->d_parent->d_inode->i_op->mkdir_raw)
-+              printk(KERN_ERR "fh_update: %s/%s already up-to-date!\n",
-+                    dentry->d_parent->d_name.name, dentry->d_name.name);
-       goto out;
- }
-diff -uprN linux/fs/nfsd/vfs.c linux-2.4.20/fs/nfsd/vfs.c
---- linux/fs/nfsd/vfs.c        Fri Nov 29 05:23:15 2002
-+++ linux-2.4.20/fs/nfsd/vfs.c Sun Oct  5 21:47:45 2003
-@@ -77,6 +77,126 @@ struct raparms {
- static struct raparms *               raparml;
- static struct raparms *               raparm_cache;
-+static int link_raw(struct dentry *dold, struct dentry *ddir,
-+                  struct dentry *dnew)
-+{
-+      int err;
-+
-+      struct nameidata old_nd = { .dentry = dold };
-+      struct nameidata nd = { .dentry = ddir, .last = dnew->d_name };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->link_raw(&old_nd, &nd);
-+      d_instantiate(dnew, dold->d_inode);
-+      if (dold->d_inode->i_op && dold->d_inode->i_op->revalidate_it)
-+              dold->d_inode->i_op->revalidate_it(dnew, NULL);
-+
-+      return err;
-+}
-+
-+static int unlink_raw(struct dentry *dentry, char *fname, int flen,
-+                    struct dentry *rdentry)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->unlink_raw(&nd);
-+      if (!err)
-+              d_delete(rdentry);
-+
-+      return err;
-+}
-+
-+static int rmdir_raw(struct dentry *dentry, char *fname, int flen,
-+                   struct dentry *rdentry)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->rmdir_raw(&nd);
-+      if (!err) {
-+              rdentry->d_inode->i_flags |= S_DEAD;
-+              d_delete(rdentry);
-+      }
-+
-+      return err;
-+}
-+
-+static int symlink_raw(struct dentry *dentry, char *fname, int flen,
-+                     char *path)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->symlink_raw(&nd, path);
-+
-+      return err;
-+}
-+
-+static int mkdir_raw(struct dentry *dentry, char *fname, int flen, int mode)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->mkdir_raw(&nd, mode);
-+
-+      return err;
-+}
-+
-+static int mknod_raw(struct dentry *dentry, char *fname, int flen, int mode,
-+                   dev_t dev)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->mknod_raw(&nd, mode, dev);
-+
-+      return err;
-+}
-+
-+static int rename_raw(struct dentry *fdentry, struct dentry *tdentry,
-+                    struct dentry *odentry, struct dentry *ndentry)
-+{
-+      int err;
-+
-+      struct nameidata old_nd = { .dentry = fdentry, .last = odentry->d_name};
-+      struct nameidata new_nd = { .dentry = tdentry, .last = ndentry->d_name};
-+      struct inode_operations *op = old_nd.dentry->d_inode->i_op;
-+      err = op->rename_raw(&old_nd, &new_nd);
-+      d_move(odentry, ndentry);
-+
-+      return err;
-+}
-+
-+static int setattr_raw(struct inode *inode, struct iattr *iap)
-+{
-+      int err;
-+
-+      iap->ia_valid |= ATTR_RAW;
-+      err = inode->i_op->setattr_raw(inode, iap);
-+
-+      return err;
-+}
-+
-+int revalidate_it(struct dentry *dentry, struct lookup_intent *it)
-+{
-+      int err = 0;
-+
-+      if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if (!dentry->d_op->d_revalidate_it(dentry, 0, it) &&
-+                      !d_invalidate(dentry)) {
-+                      err = -EINVAL;
-+                      return err;
-+              }
-+      }
-+
-+      return err;
-+}
-+
- /*
-  * Look up one component of a pathname.
-  * N.B. After this call _both_ fhp and resfh need an fh_put
-@@ -300,7 +422,10 @@ nfsd_setattr(struct svc_rqst *rqstp, str
-       }
-       err = nfserr_notsync;
-       if (!check_guard || guardtime == inode->i_ctime) {
--              err = notify_change(dentry, iap);
-+              if (dentry->d_inode->i_op && dentry->d_inode->i_op->setattr_raw)
-+                      err = setattr_raw(dentry->d_inode, iap);
-+              else
-+                      err = notify_change(dentry, iap);
-               err = nfserrno(err);
-       }
-       if (size_change) {
-@@ -427,6 +552,7 @@ nfsd_open(struct svc_rqst *rqstp, struct
- {
-       struct dentry   *dentry;
-       struct inode    *inode;
-+      struct lookup_intent it;
-       int             err;
-       /* If we get here, then the client has already done an "open", and (hopefully)
-@@ -473,6 +599,18 @@ nfsd_open(struct svc_rqst *rqstp, struct
-               filp->f_mode  = FMODE_READ;
-       }
-+#ifndef O_OWNER_OVERRIDE
-+#define O_OWNER_OVERRIDE 0200000000
-+#endif
-+      intent_init(&it, IT_OPEN, (filp->f_flags & ~O_ACCMODE) | filp->f_mode |
-+                  O_OWNER_OVERRIDE);
-+
-+      err = revalidate_it(dentry, &it);
-+      if (err)
-+              goto out_nfserr;
-+
-+      filp->f_it = &it;
-+
-       err = 0;
-       if (filp->f_op && filp->f_op->open) {
-               err = filp->f_op->open(inode, filp);
-@@ -487,6 +621,9 @@ nfsd_open(struct svc_rqst *rqstp, struct
-               }
-       }
- out_nfserr:
-+      if (it.it_op_release)
-+              intent_release(&it);
-+
-       if (err)
-               err = nfserrno(err);
- out:
-@@ -818,7 +956,7 @@ nfsd_create(struct svc_rqst *rqstp, stru
- {
-       struct dentry   *dentry, *dchild;
-       struct inode    *dirp;
--      int             err;
-+      int             err, error = -EOPNOTSUPP;
-       err = nfserr_perm;
-       if (!flen)
-@@ -834,20 +972,47 @@ nfsd_create(struct svc_rqst *rqstp, stru
-       dentry = fhp->fh_dentry;
-       dirp = dentry->d_inode;
-+      switch (type) {
-+      case S_IFDIR:
-+              if (dirp->i_op->mkdir_raw)
-+                      error = mkdir_raw(dentry, fname, flen, iap->ia_mode);
-+              break;
-+      case S_IFCHR:
-+      case S_IFBLK:
-+      case S_IFIFO:
-+      case S_IFSOCK:
-+      case S_IFREG:
-+              if (dirp->i_op->mknod_raw) {
-+                      if (type == S_IFREG)
-+                              rdev = 0;
-+                      error = mknod_raw(dentry, fname,flen,iap->ia_mode,rdev);
-+              }
-+              break;
-+      default:
-+              printk("nfsd: bad file type %o in nfsd_create\n", type);
-+      }
-+      if (error && error != -EOPNOTSUPP) {
-+              err = error;
-+              goto out_nfserr;
-+      }
-+
-       err = nfserr_notdir;
--      if(!dirp->i_op || !dirp->i_op->lookup)
-+      if (!dirp->i_op || !(dirp->i_op->lookup || dirp->i_op->lookup_it))
-               goto out;
-       /*
-        * Check whether the response file handle has been verified yet.
-        * If it has, the parent directory should already be locked.
-        */
--      if (!resfhp->fh_dentry) {
--              /* called from nfsd_proc_mkdir, or possibly nfsd3_proc_create */
--              fh_lock(fhp);
-+      if (!resfhp->fh_dentry || dirp->i_op->lookup_it) {
-+              /* called from nfsd_proc_mkdir, or possibly nfsd3_proc_create
-+               * and nfsd_proc_create in case of lustre */
-+              if (!resfhp->fh_dentry)
-+                      fh_lock(fhp);
-               dchild = lookup_one_len(fname, dentry, flen);
-               err = PTR_ERR(dchild);
-               if (IS_ERR(dchild))
-                       goto out_nfserr;
-+              resfhp->fh_dentry = NULL;
-               err = fh_compose(resfhp, fhp->fh_export, dchild, fhp);
-               if (err)
-                       goto out;
-@@ -868,10 +1030,12 @@ nfsd_create(struct svc_rqst *rqstp, stru
-        * Make sure the child dentry is still negative ...
-        */
-       err = nfserr_exist;
--      if (dchild->d_inode) {
--              dprintk("nfsd_create: dentry %s/%s not negative!\n",
--                      dentry->d_name.name, dchild->d_name.name);
--              goto out; 
-+      if (error == -EOPNOTSUPP) {
-+              if (dchild->d_inode) {
-+                      dprintk("nfsd_create: dentry %s/%s not negative!\n",
-+                              dentry->d_name.name, dchild->d_name.name);
-+                      goto out;
-+              }
-       }
-       if (!(iap->ia_valid & ATTR_MODE))
-@@ -884,16 +1048,19 @@ nfsd_create(struct svc_rqst *rqstp, stru
-       err = nfserr_perm;
-       switch (type) {
-       case S_IFREG:
--              err = vfs_create(dirp, dchild, iap->ia_mode);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_create(dirp, dchild, iap->ia_mode);
-               break;
-       case S_IFDIR:
--              err = vfs_mkdir(dirp, dchild, iap->ia_mode);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_mkdir(dirp, dchild, iap->ia_mode);
-               break;
-       case S_IFCHR:
-       case S_IFBLK:
-       case S_IFIFO:
-       case S_IFSOCK:
--              err = vfs_mknod(dirp, dchild, iap->ia_mode, rdev);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_mknod(dirp, dchild, iap->ia_mode, rdev);
-               break;
-       default:
-               printk("nfsd: bad file type %o in nfsd_create\n", type);
-@@ -962,7 +1129,13 @@ nfsd_create_v3(struct svc_rqst *rqstp, s
-       /* Get all the sanity checks out of the way before
-        * we lock the parent. */
-       err = nfserr_notdir;
--      if(!dirp->i_op || !dirp->i_op->lookup)
-+      if (dirp->i_op->mknod_raw) {
-+              err = mknod_raw(dentry, fname, flen, iap->ia_mode, 0);
-+              if (err && err != -EOPNOTSUPP)
-+                      goto out_nfserr;
-+      }
-+
-+      if (!dirp->i_op || !(dirp->i_op->lookup || dirp->i_op->lookup_it))
-               goto out;
-       fh_lock(fhp);
-@@ -1013,6 +1186,8 @@ nfsd_create_v3(struct svc_rqst *rqstp, s
-               case NFS3_CREATE_GUARDED:
-                       err = nfserr_exist;
-               }
-+              if (dirp->i_op->mknod_raw)
-+                      err = 0;
-               goto out;
-       }
-@@ -1119,7 +1294,7 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-                               struct iattr *iap)
- {
-       struct dentry   *dentry, *dnew;
--      int             err, cerr;
-+      int             err, cerr, error = -EOPNOTSUPP;
-       err = nfserr_noent;
-       if (!flen || !plen)
-@@ -1133,12 +1308,18 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-               goto out;
-       fh_lock(fhp);
-       dentry = fhp->fh_dentry;
-+
-+      if (dentry->d_inode->i_op->symlink_raw)
-+              error = symlink_raw(dentry, fname, flen, path);
-+
-       dnew = lookup_one_len(fname, dentry, flen);
-       err = PTR_ERR(dnew);
-       if (IS_ERR(dnew))
-               goto out_nfserr;
--      err = vfs_symlink(dentry->d_inode, dnew, path);
-+      err = error;
-+      if (err == -EOPNOTSUPP || !dentry->d_inode->i_op->symlink_raw)
-+              err = vfs_symlink(dentry->d_inode, dnew, path);
-       if (!err) {
-               if (EX_ISSYNC(fhp->fh_export))
-                       nfsd_sync_dir(dentry);
-@@ -1148,7 +1329,10 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-                               iap->ia_valid |= ATTR_CTIME;
-                               iap->ia_mode = (iap->ia_mode&S_IALLUGO)
-                                       | S_IFLNK;
--                              err = notify_change(dnew, iap);
-+                              if (dnew->d_inode->i_op && dnew->d_inode->i_op->setattr_raw)
-+                                      err = setattr_raw(dnew->d_inode, iap);
-+                              else
-+                                      err = notify_change(dnew, iap);
-                               if (!err && EX_ISSYNC(fhp->fh_export))
-                                       write_inode_now(dentry->d_inode, 1);
-                      }
-@@ -1206,7 +1390,10 @@ nfsd_link(struct svc_rqst *rqstp, struct
-       dold = tfhp->fh_dentry;
-       dest = dold->d_inode;
--      err = vfs_link(dold, dirp, dnew);
-+      if (dirp->i_op->link_raw)
-+              err = link_raw(dold, ddir, dnew);
-+      else
-+              err = vfs_link(dold, dirp, dnew);
-       if (!err) {
-               if (EX_ISSYNC(ffhp->fh_export)) {
-                       nfsd_sync_dir(ddir);
-@@ -1291,7 +1478,10 @@ nfsd_rename(struct svc_rqst *rqstp, stru
-                       err = nfserr_perm;
-       } else
- #endif
--      err = vfs_rename(fdir, odentry, tdir, ndentry);
-+      if (fdir->i_op->rename_raw)
-+              err = rename_raw(fdentry, tdentry, odentry, ndentry);
-+      else
-+              err = vfs_rename(fdir, odentry, tdir, ndentry);
-       if (!err && EX_ISSYNC(tfhp->fh_export)) {
-               nfsd_sync_dir(tdentry);
-               nfsd_sync_dir(fdentry);
-@@ -1312,7 +1502,7 @@ nfsd_rename(struct svc_rqst *rqstp, stru
-       fill_post_wcc(tfhp);
-       double_up(&tdir->i_sem, &fdir->i_sem);
-       ffhp->fh_locked = tfhp->fh_locked = 0;
--      
-+
- out:
-       return err;
- }
-@@ -1358,9 +1548,15 @@ nfsd_unlink(struct svc_rqst *rqstp, stru
-                       err = nfserr_perm;
-               } else
- #endif
--              err = vfs_unlink(dirp, rdentry);
-+              if (dirp->i_op->unlink_raw)
-+                      err = unlink_raw(dentry, fname, flen, rdentry);
-+              else
-+                      err = vfs_unlink(dirp, rdentry);
-       } else { /* It's RMDIR */
--              err = vfs_rmdir(dirp, rdentry);
-+              if (dirp->i_op->rmdir_raw)
-+                      err = rmdir_raw(dentry, fname, flen, rdentry);
-+              else
-+                      err = vfs_rmdir(dirp, rdentry);
-       }
-       dput(rdentry);
-diff -uprN linux/include/linux/fs.h linux-2.4.20/include/linux/fs.h
---- linux/include/linux/fs.h   Sun Oct  5 21:52:56 2003
-+++ linux-2.4.20/include/linux/fs.h    Sun Oct  5 22:25:20 2003
-@@ -93,6 +93,8 @@ extern int leases_enable, dir_notify_ena
- #define FS_SINGLE     8 /* Filesystem that can have only one superblock */
- #define FS_NOMOUNT    16 /* Never mount from userland */
- #define FS_LITTER     32 /* Keeps the tree in dcache */
-+#define FS_NFSEXP_FSID        64 /* Use file system specific fsid for
-+                          * exporting non device filesystems. */
- #define FS_ODD_RENAME 32768   /* Temporary stuff; will go away as soon
-                                 * as nfs_rename() will be cleaned up
-                                 */
-@@ -1099,6 +1102,9 @@ extern int open_namei_it(const char *fil
-                        struct nameidata *nd, struct lookup_intent *it);
- extern struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-                           int flags, struct lookup_intent *it);
-+extern int revalidate_it(struct dentry *dentry, struct lookup_intent *it);
-+extern int init_private_file_it(struct file *, struct dentry *dentry, int mode,
-+                              struct lookup_intent *it);
- extern int filp_close(struct file *, fl_owner_t id);
- extern char * getname(const char *);
-@@ -1369,6 +1375,8 @@ extern void path_release(struct nameidat
- extern int follow_down(struct vfsmount **, struct dentry **);
- extern int follow_up(struct vfsmount **, struct dentry **);
- extern struct dentry * lookup_one_len(const char *, struct dentry *, int);
-+extern struct dentry * lookup_one_len_it(const char *, struct dentry *, int,
-+                                       struct lookup_intent *);
- extern struct dentry * lookup_hash(struct qstr *, struct dentry *);
- #define user_path_walk(name,nd)        __user_walk(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd)
- #define user_path_walk_link(name,nd) __user_walk(name, LOOKUP_POSITIVE, nd)
-@@ -1382,6 +1390,8 @@ extern ino_t iunique(struct super_block 
- typedef int (*find_inode_t)(struct inode *, unsigned long, void *);
- extern struct inode * iget4(struct super_block *, unsigned long, find_inode_t, void *);
-+extern struct inode * ilookup4(struct super_block *, unsigned long,
-+                             find_inode_t, void *);
- static inline struct inode *iget(struct super_block *sb, unsigned long ino)
- {
-       return iget4(sb, ino, NULL, NULL);
-diff -uprN linux/kernel/ksyms.c linux-2.4.20/kernel/ksyms.c
---- linux/kernel/ksyms.c       Sun Oct  5 21:52:51 2003
-+++ linux-2.4.20/kernel/ksyms.c        Sun Oct  5 22:25:20 2003
-@@ -146,6 +146,7 @@ EXPORT_SYMBOL(fget);
- EXPORT_SYMBOL(igrab);
- EXPORT_SYMBOL(iunique);
- EXPORT_SYMBOL(iget4);
-+EXPORT_SYMBOL(ilookup4);
- EXPORT_SYMBOL(iput);
- EXPORT_SYMBOL(force_delete);
- EXPORT_SYMBOL(follow_up);
-@@ -156,6 +157,7 @@ EXPORT_SYMBOL(path_walk);
- EXPORT_SYMBOL(path_release);
- EXPORT_SYMBOL(__user_walk);
- EXPORT_SYMBOL(lookup_one_len);
-+EXPORT_SYMBOL(lookup_one_len_it);
- EXPORT_SYMBOL(lookup_hash);
- EXPORT_SYMBOL(sys_close);
- EXPORT_SYMBOL(dcache_lock);
diff --git a/lustre/kernel_patches/patches/nfs_export_kernel-2.4.22-rh.patch b/lustre/kernel_patches/patches/nfs_export_kernel-2.4.22-rh.patch
deleted file mode 100644 (file)
index 436d99b..0000000
+++ /dev/null
@@ -1,737 +0,0 @@
- fs/Makefile        |    3 
- fs/file_table.c    |   11 ++
- fs/inode.c         |   23 ++++-
- fs/namei.c         |   12 ++
- fs/nfsd/export.c   |    5 +
- fs/nfsd/nfsfh.c    |   65 +++++++++++++-
- fs/nfsd/vfs.c      |  235 ++++++++++++++++++++++++++++++++++++++++++++++++-----
- include/linux/fs.h |   11 ++
- kernel/ksyms.c     |    2 
- 9 files changed, 333 insertions(+), 34 deletions(-)
-
---- linux-2.4.22-ac1/fs/file_table.c~nfs_export_kernel-2.4.22-rh       2002-11-29 02:53:15.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/file_table.c    2003-10-08 13:41:27.000000000 +0400
-@@ -82,7 +82,8 @@ struct file * get_empty_filp(void)
-  * and call the open function (if any).  The caller must verify that
-  * inode->i_fop is not NULL.
-  */
--int init_private_file(struct file *filp, struct dentry *dentry, int mode)
-+int init_private_file_it(struct file *filp, struct dentry *dentry, int mode,
-+                       struct lookup_intent *it)
- {
-       memset(filp, 0, sizeof(*filp));
-       filp->f_mode   = mode;
-@@ -90,12 +91,20 @@ int init_private_file(struct file *filp,
-       filp->f_dentry = dentry;
-       filp->f_uid    = current->fsuid;
-       filp->f_gid    = current->fsgid;
-+      if (it)
-+              filp->f_it = it;
-       filp->f_op     = dentry->d_inode->i_fop;
-       if (filp->f_op->open)
-               return filp->f_op->open(dentry->d_inode, filp);
-       else
-               return 0;
- }
-+EXPORT_SYMBOL(init_private_file_it);
-+
-+int init_private_file(struct file *filp, struct dentry *dentry, int mode)
-+{
-+      return init_private_file_it(filp, dentry, mode, NULL);
-+}
- void fput(struct file * file)
- {
---- linux-2.4.22-ac1/fs/inode.c~nfs_export_kernel-2.4.22-rh    2003-09-26 00:57:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/inode.c 2003-10-08 13:43:31.000000000 +0400
-@@ -998,9 +998,10 @@ struct inode *igrab(struct inode *inode)
-       return inode;
- }
--struct inode *iget4_locked(struct super_block *sb, unsigned long ino, find_inode_t find_actor, void *opaque)
-+struct inode *ifind(struct super_block *sb, unsigned long ino,
-+                  struct list_head *head,
-+                  find_inode_t find_actor, void *opaque)
- {
--      struct list_head * head = inode_hashtable + hash(sb,ino);
-       struct inode * inode;
-       spin_lock(&inode_lock);
-@@ -1013,6 +1014,24 @@ struct inode *iget4_locked(struct super_
-       }
-       spin_unlock(&inode_lock);
-+      return NULL;
-+}
-+
-+struct inode *ilookup4(struct super_block *sb, unsigned long ino,
-+                     find_inode_t find_actor, void *opaque)
-+{
-+      struct list_head * head = inode_hashtable + hash(sb,ino);
-+      return ifind(sb, ino, head, find_actor, opaque);
-+}
-+
-+struct inode *iget4_locked(struct super_block *sb, unsigned long ino,
-+                         find_inode_t find_actor, void *opaque)
-+{
-+      struct list_head * head = inode_hashtable + hash(sb,ino);
-+      struct inode *inode = ifind(sb, ino, head, find_actor, opaque);
-+      if (inode)
-+              return inode;
-+
-       /*
-        * get_new_inode() will do the right thing, re-trying the search
-        * in case it had to block at any point.
---- linux-2.4.22-ac1/fs/Makefile~nfs_export_kernel-2.4.22-rh   2003-09-26 00:57:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/Makefile        2003-10-08 13:41:55.000000000 +0400
-@@ -7,7 +7,8 @@
- O_TARGET := fs.o
--export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o inode.o
-+export-objs :=        filesystems.o open.o dcache.o buffer.o dquot.o dcookies.o inode.o \
-+              namei.o file_table.o
- mod-subdirs :=        nls xfs
- obj-y :=      open.o read_write.o devices.o file_table.o buffer.o \
---- linux-2.4.22-ac1/fs/namei.c~nfs_export_kernel-2.4.22-rh    2003-09-26 00:57:27.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/namei.c 2003-10-08 13:41:27.000000000 +0400
-@@ -22,6 +22,7 @@
- #include <linux/dnotify.h>
- #include <linux/smp_lock.h>
- #include <linux/personality.h>
-+#include <linux/module.h>
- #include <asm/namei.h>
- #include <asm/uaccess.h>
-@@ -100,6 +101,7 @@ void intent_release(struct lookup_intent
-               it->it_op_release(it);
- }
-+EXPORT_SYMBOL(intent_release);
- /* In order to reduce some races, while at the same time doing additional
-  * checking and hopefully speeding things up, we copy filenames to the
-@@ -903,7 +905,8 @@ struct dentry * lookup_hash(struct qstr 
- /* SMP-safe */
--struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
-+struct dentry * lookup_one_len_it(const char * name, struct dentry * base,
-+                                int len, struct lookup_intent *it)
- {
-       unsigned long hash;
-       struct qstr this;
-@@ -923,11 +926,16 @@ struct dentry * lookup_one_len(const cha
-       }
-       this.hash = end_name_hash(hash);
--      return lookup_hash_it(&this, base, NULL);
-+      return lookup_hash_it(&this, base, it);
- access:
-       return ERR_PTR(-EACCES);
- }
-+struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
-+{
-+      return lookup_one_len_it(name, base, len, NULL);
-+}
-+
- /*
-  *    namei()
-  *
---- linux-2.4.22-ac1/fs/nfsd/export.c~nfs_export_kernel-2.4.22-rh      2003-09-25 14:16:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/nfsd/export.c   2003-10-08 13:41:27.000000000 +0400
-@@ -223,6 +223,11 @@ exp_export(struct nfsctl_export *nxp)
-       inode = nd.dentry->d_inode;
-       dev = inode->i_dev;
-       ino = inode->i_ino;
-+      if ((inode->i_sb->s_type->fs_flags & FS_NFSEXP_FSID) &&
-+          !(nxp->ex_flags & NFSEXP_FSID)) {
-+              nxp->ex_dev = inode->i_sb->s_dev;
-+              nxp->ex_flags |= NFSEXP_FSID;
-+      }
-       err = -EINVAL;
-       exp = exp_get(clp, dev, ino);
---- linux-2.4.22-ac1/fs/nfsd/nfsfh.c~nfs_export_kernel-2.4.22-rh       2003-08-25 15:44:43.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/nfsd/nfsfh.c    2003-10-08 13:41:27.000000000 +0400
-@@ -36,6 +36,13 @@ struct nfsd_getdents_callback {
-       int sequence;           /* sequence counter */
- };
-+static struct dentry *lookup_it(struct inode *inode, struct dentry * dentry)
-+{
-+      if (inode->i_op->lookup_it)
-+              return inode->i_op->lookup_it(inode, dentry, NULL, 0);
-+      return inode->i_op->lookup(inode, dentry);
-+}
-+
- /*
-  * A rather strange filldir function to capture
-  * the name matching the specified inode number.
-@@ -75,6 +84,8 @@ static int nfsd_get_name(struct dentry *
-       int error;
-       struct file file;
-       struct nfsd_getdents_callback buffer;
-+      struct lookup_intent it;
-+      struct file *filp = NULL;
-       error = -ENOTDIR;
-       if (!dir || !S_ISDIR(dir->i_mode))
-@@ -85,9 +96,37 @@ static int nfsd_get_name(struct dentry *
-       /*
-        * Open the directory ...
-        */
--      error = init_private_file(&file, dentry, FMODE_READ);
--      if (error)
-+      if (dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if ((dentry->d_flags & DCACHE_NFSD_DISCONNECTED) &&
-+                  (dentry->d_parent == dentry) ) {
-+                      it.it_op_release = NULL;
-+                      /*
-+                       * XXX Temporary Hack: Simulate init_private_file without
-+                       * f_op->open for disconnected dentry as we don't have
-+                       * actual dentry->d_name to revalidate in revalidate_it()
-+                       */
-+                      filp = &file;
-+                      memset(filp, 0, sizeof(*filp));
-+                      filp->f_mode   = FMODE_READ;
-+                      atomic_set(&filp->f_count, 1);
-+                      filp->f_dentry = dentry;
-+                      filp->f_uid = current->fsuid;
-+                      filp->f_gid = current->fsgid;
-+                      filp->f_op = dentry->d_inode->i_fop;
-+                      error = 0;
-+              } else {
-+                      intent_init(&it, IT_OPEN, 0);
-+                      error = revalidate_it(dentry, &it);
-+                      if (error)
-+                              goto out;
-+                      error = init_private_file_it(&file, dentry, FMODE_READ, &it);
-+              }
-+      } else {
-+              error = init_private_file_it(&file, dentry, FMODE_READ, NULL);
-+      }
-+      if (error)
-               goto out;
-+
-       error = -EINVAL;
-       if (!file.f_op->readdir)
-               goto out_close;
-@@ -113,9 +152,12 @@ static int nfsd_get_name(struct dentry *
-       }
- out_close:
--      if (file.f_op->release)
-+      if (file.f_op->release && !filp)
-               file.f_op->release(dir, &file);
- out:
-+      if (dentry->d_op && dentry->d_op->d_revalidate_it &&
-+          it.it_op_release && !filp)
-+              intent_release(&it);
-       return error;
- }
-@@ -274,7 +317,7 @@ struct dentry *nfsd_findparent(struct de
-        * it is well connected.  But nobody returns different dentrys do they?
-        */
-       down(&child->d_inode->i_sem);
--      pdentry = child->d_inode->i_op->lookup(child->d_inode, tdentry);
-+      pdentry = lookup_it(child->d_inode, tdentry);
-       up(&child->d_inode->i_sem);
-       d_drop(tdentry); /* we never want ".." hashed */
-       if (!pdentry && tdentry->d_inode == NULL) {
-@@ -306,6 +349,8 @@ struct dentry *nfsd_findparent(struct de
-                               igrab(tdentry->d_inode);
-                               pdentry->d_flags |= DCACHE_NFSD_DISCONNECTED;
-                       }
-+                      if (child->d_op && child->d_op->d_revalidate_it)
-+                              pdentry->d_op = child->d_op;
-               }
-               if (pdentry == NULL)
-                       pdentry = ERR_PTR(-ENOMEM);
-@@ -463,6 +508,8 @@ find_fh_dentry(struct super_block *sb, _
-               struct dentry *pdentry;
-               struct inode *parent;
-+              if (result->d_op && result->d_op->d_revalidate_it)
-+                      dentry->d_op = result->d_op;
-               pdentry = nfsd_findparent(dentry);
-               err = PTR_ERR(pdentry);
-               if (IS_ERR(pdentry))
-@@ -669,6 +716,10 @@ fh_verify(struct svc_rqst *rqstp, struct
-       inode = dentry->d_inode;
-+      /* cache coherency for non-device filesystems */
-+      if (inode->i_op && inode->i_op->revalidate_it)
-+              inode->i_op->revalidate_it(dentry, NULL);
-+
-       /* Type check. The correct error return for type mismatches
-        * does not seem to be generally agreed upon. SunOS seems to
-        * use EISDIR if file isn't S_IFREG; a comment in the NFSv3
-@@ -902,8 +954,9 @@ out_negative:
-               dentry->d_parent->d_name.name, dentry->d_name.name);
-       goto out;
- out_uptodate:
--      printk(KERN_ERR "fh_update: %s/%s already up-to-date!\n",
--              dentry->d_parent->d_name.name, dentry->d_name.name);
-+      if (!dentry->d_parent->d_inode->i_op->mkdir_raw)
-+              printk(KERN_ERR "fh_update: %s/%s already up-to-date!\n",
-+                    dentry->d_parent->d_name.name, dentry->d_name.name);
-       goto out;
- }
---- linux-2.4.22-ac1/fs/nfsd/vfs.c~nfs_export_kernel-2.4.22-rh 2003-08-25 15:44:43.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/nfsd/vfs.c      2003-10-08 13:41:27.000000000 +0400
-@@ -77,6 +77,126 @@ struct raparms {
- static struct raparms *               raparml;
- static struct raparms *               raparm_cache;
-+static int link_raw(struct dentry *dold, struct dentry *ddir,
-+                  struct dentry *dnew)
-+{
-+      int err;
-+
-+      struct nameidata old_nd = { .dentry = dold };
-+      struct nameidata nd = { .dentry = ddir, .last = dnew->d_name };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->link_raw(&old_nd, &nd);
-+      d_instantiate(dnew, dold->d_inode);
-+      if (dold->d_inode->i_op && dold->d_inode->i_op->revalidate_it)
-+              dold->d_inode->i_op->revalidate_it(dnew, NULL);
-+
-+      return err;
-+}
-+
-+static int unlink_raw(struct dentry *dentry, char *fname, int flen,
-+                    struct dentry *rdentry)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->unlink_raw(&nd);
-+      if (!err)
-+              d_delete(rdentry);
-+
-+      return err;
-+}
-+
-+static int rmdir_raw(struct dentry *dentry, char *fname, int flen,
-+                   struct dentry *rdentry)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->rmdir_raw(&nd);
-+      if (!err) {
-+              rdentry->d_inode->i_flags |= S_DEAD;
-+              d_delete(rdentry);
-+      }
-+
-+      return err;
-+}
-+
-+static int symlink_raw(struct dentry *dentry, char *fname, int flen,
-+                     char *path)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->symlink_raw(&nd, path);
-+
-+      return err;
-+}
-+
-+static int mkdir_raw(struct dentry *dentry, char *fname, int flen, int mode)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->mkdir_raw(&nd, mode);
-+
-+      return err;
-+}
-+
-+static int mknod_raw(struct dentry *dentry, char *fname, int flen, int mode,
-+                   dev_t dev)
-+{
-+      int err;
-+      struct qstr last = { .name = fname, .len = flen };
-+      struct nameidata nd = { .dentry = dentry, .last = last };
-+      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+      err = op->mknod_raw(&nd, mode, dev);
-+
-+      return err;
-+}
-+
-+static int rename_raw(struct dentry *fdentry, struct dentry *tdentry,
-+                    struct dentry *odentry, struct dentry *ndentry)
-+{
-+      int err;
-+
-+      struct nameidata old_nd = { .dentry = fdentry, .last = odentry->d_name};
-+      struct nameidata new_nd = { .dentry = tdentry, .last = ndentry->d_name};
-+      struct inode_operations *op = old_nd.dentry->d_inode->i_op;
-+      err = op->rename_raw(&old_nd, &new_nd);
-+      d_move(odentry, ndentry);
-+
-+      return err;
-+}
-+
-+static int setattr_raw(struct inode *inode, struct iattr *iap)
-+{
-+      int err;
-+
-+      iap->ia_valid |= ATTR_RAW;
-+      err = inode->i_op->setattr_raw(inode, iap);
-+
-+      return err;
-+}
-+
-+int revalidate_it(struct dentry *dentry, struct lookup_intent *it)
-+{
-+      int err = 0;
-+
-+      if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if (!dentry->d_op->d_revalidate_it(dentry, 0, it) &&
-+                      !d_invalidate(dentry)) {
-+                      err = -EINVAL;
-+                      return err;
-+              }
-+      }
-+
-+      return err;
-+}
-+
- /*
-  * Look up one component of a pathname.
-  * N.B. After this call _both_ fhp and resfh need an fh_put
-@@ -302,7 +424,10 @@ nfsd_setattr(struct svc_rqst *rqstp, str
-       }
-       err = nfserr_notsync;
-       if (!check_guard || guardtime == inode->i_ctime) {
--              err = notify_change(dentry, iap);
-+              if (dentry->d_inode->i_op && dentry->d_inode->i_op->setattr_raw)
-+                      err = setattr_raw(dentry->d_inode, iap);
-+              else
-+                      err = notify_change(dentry, iap);
-               err = nfserrno(err);
-       }
-       if (size_change) {
-@@ -429,6 +554,7 @@ nfsd_open(struct svc_rqst *rqstp, struct
- {
-       struct dentry   *dentry;
-       struct inode    *inode;
-+      struct lookup_intent it;
-       int             err;
-       /* If we get here, then the client has already done an "open", and (hopefully)
-@@ -475,6 +601,18 @@ nfsd_open(struct svc_rqst *rqstp, struct
-               filp->f_mode  = FMODE_READ;
-       }
-+#ifndef O_OWNER_OVERRIDE
-+#define O_OWNER_OVERRIDE 0200000000
-+#endif
-+      intent_init(&it, IT_OPEN, (filp->f_flags & ~O_ACCMODE) | filp->f_mode |
-+                  O_OWNER_OVERRIDE);
-+
-+      err = revalidate_it(dentry, &it);
-+      if (err)
-+              goto out_nfserr;
-+
-+      filp->f_it = &it;
-+
-       err = 0;
-       if (filp->f_op && filp->f_op->open) {
-               err = filp->f_op->open(inode, filp);
-@@ -489,6 +623,9 @@ nfsd_open(struct svc_rqst *rqstp, struct
-               }
-       }
- out_nfserr:
-+      if (it.it_op_release)
-+              intent_release(&it);
-+
-       if (err)
-               err = nfserrno(err);
- out:
-@@ -820,7 +958,7 @@ nfsd_create(struct svc_rqst *rqstp, stru
- {
-       struct dentry   *dentry, *dchild;
-       struct inode    *dirp;
--      int             err;
-+      int             err, error = -EOPNOTSUPP;
-       err = nfserr_perm;
-       if (!flen)
-@@ -836,20 +974,47 @@ nfsd_create(struct svc_rqst *rqstp, stru
-       dentry = fhp->fh_dentry;
-       dirp = dentry->d_inode;
-+      switch (type) {
-+      case S_IFDIR:
-+              if (dirp->i_op->mkdir_raw)
-+                      error = mkdir_raw(dentry, fname, flen, iap->ia_mode);
-+              break;
-+      case S_IFCHR:
-+      case S_IFBLK:
-+      case S_IFIFO:
-+      case S_IFSOCK:
-+      case S_IFREG:
-+              if (dirp->i_op->mknod_raw) {
-+                      if (type == S_IFREG)
-+                              rdev = 0;
-+                      error = mknod_raw(dentry, fname,flen,iap->ia_mode,rdev);
-+              }
-+              break;
-+      default:
-+              printk("nfsd: bad file type %o in nfsd_create\n", type);
-+      }
-+      if (error && error != -EOPNOTSUPP) {
-+              err = error;
-+              goto out_nfserr;
-+      }
-+
-       err = nfserr_notdir;
--      if(!dirp->i_op || !dirp->i_op->lookup)
-+      if (!dirp->i_op || !(dirp->i_op->lookup || dirp->i_op->lookup_it))
-               goto out;
-       /*
-        * Check whether the response file handle has been verified yet.
-        * If it has, the parent directory should already be locked.
-        */
--      if (!resfhp->fh_dentry) {
--              /* called from nfsd_proc_mkdir, or possibly nfsd3_proc_create */
--              fh_lock(fhp);
-+      if (!resfhp->fh_dentry || dirp->i_op->lookup_it) {
-+              /* called from nfsd_proc_mkdir, or possibly nfsd3_proc_create
-+               * and nfsd_proc_create in case of lustre */
-+              if (!resfhp->fh_dentry)
-+                      fh_lock(fhp);
-               dchild = lookup_one_len(fname, dentry, flen);
-               err = PTR_ERR(dchild);
-               if (IS_ERR(dchild))
-                       goto out_nfserr;
-+              resfhp->fh_dentry = NULL;
-               err = fh_compose(resfhp, fhp->fh_export, dchild, fhp);
-               if (err)
-                       goto out;
-@@ -870,10 +1032,12 @@ nfsd_create(struct svc_rqst *rqstp, stru
-        * Make sure the child dentry is still negative ...
-        */
-       err = nfserr_exist;
--      if (dchild->d_inode) {
--              dprintk("nfsd_create: dentry %s/%s not negative!\n",
--                      dentry->d_name.name, dchild->d_name.name);
--              goto out; 
-+      if (error == -EOPNOTSUPP) {
-+              if (dchild->d_inode) {
-+                      dprintk("nfsd_create: dentry %s/%s not negative!\n",
-+                              dentry->d_name.name, dchild->d_name.name);
-+                      goto out;
-+              }
-       }
-       if (!(iap->ia_valid & ATTR_MODE))
-@@ -886,16 +1050,19 @@ nfsd_create(struct svc_rqst *rqstp, stru
-       err = nfserr_perm;
-       switch (type) {
-       case S_IFREG:
--              err = vfs_create(dirp, dchild, iap->ia_mode);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_create(dirp, dchild, iap->ia_mode);
-               break;
-       case S_IFDIR:
--              err = vfs_mkdir(dirp, dchild, iap->ia_mode);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_mkdir(dirp, dchild, iap->ia_mode);
-               break;
-       case S_IFCHR:
-       case S_IFBLK:
-       case S_IFIFO:
-       case S_IFSOCK:
--              err = vfs_mknod(dirp, dchild, iap->ia_mode, rdev);
-+              if (error == -EOPNOTSUPP)
-+                      err = vfs_mknod(dirp, dchild, iap->ia_mode, rdev);
-               break;
-       default:
-               printk("nfsd: bad file type %o in nfsd_create\n", type);
-@@ -964,7 +1131,13 @@ nfsd_create_v3(struct svc_rqst *rqstp, s
-       /* Get all the sanity checks out of the way before
-        * we lock the parent. */
-       err = nfserr_notdir;
--      if(!dirp->i_op || !dirp->i_op->lookup)
-+      if (dirp->i_op->mknod_raw) {
-+              err = mknod_raw(dentry, fname, flen, iap->ia_mode, 0);
-+              if (err && err != -EOPNOTSUPP)
-+                      goto out_nfserr;
-+      }
-+
-+      if (!dirp->i_op || !(dirp->i_op->lookup || dirp->i_op->lookup_it))
-               goto out;
-       fh_lock(fhp);
-@@ -1015,6 +1188,8 @@ nfsd_create_v3(struct svc_rqst *rqstp, s
-               case NFS3_CREATE_GUARDED:
-                       err = nfserr_exist;
-               }
-+              if (dirp->i_op->mknod_raw)
-+                      err = 0;
-               goto out;
-       }
-@@ -1121,7 +1296,7 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-                               struct iattr *iap)
- {
-       struct dentry   *dentry, *dnew;
--      int             err, cerr;
-+      int             err, cerr, error = -EOPNOTSUPP;
-       err = nfserr_noent;
-       if (!flen || !plen)
-@@ -1135,12 +1310,18 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-               goto out;
-       fh_lock(fhp);
-       dentry = fhp->fh_dentry;
-+
-+      if (dentry->d_inode->i_op->symlink_raw)
-+              error = symlink_raw(dentry, fname, flen, path);
-+
-       dnew = lookup_one_len(fname, dentry, flen);
-       err = PTR_ERR(dnew);
-       if (IS_ERR(dnew))
-               goto out_nfserr;
--      err = vfs_symlink(dentry->d_inode, dnew, path);
-+      err = error;
-+      if (err == -EOPNOTSUPP || !dentry->d_inode->i_op->symlink_raw)
-+              err = vfs_symlink(dentry->d_inode, dnew, path);
-       if (!err) {
-               if (EX_ISSYNC(fhp->fh_export))
-                       nfsd_sync_dir(dentry);
-@@ -1148,7 +1329,10 @@ nfsd_symlink(struct svc_rqst *rqstp, str
-                               iap->ia_valid |= ATTR_CTIME;
-                               iap->ia_mode = (iap->ia_mode&S_IALLUGO)
-                                       | S_IFLNK;
--                              err = notify_change(dnew, iap);
-+                              if (dnew->d_inode->i_op && dnew->d_inode->i_op->setattr_raw)
-+                                      err = setattr_raw(dnew->d_inode, iap);
-+                              else
-+                                      err = notify_change(dnew, iap);
-                               if (err)
-                                       err = nfserrno(err);
-                               else if (EX_ISSYNC(fhp->fh_export))
-@@ -1210,7 +1391,10 @@ nfsd_link(struct svc_rqst *rqstp, struct
-       dold = tfhp->fh_dentry;
-       dest = dold->d_inode;
--      err = vfs_link(dold, dirp, dnew);
-+      if (dirp->i_op->link_raw)
-+              err = link_raw(dold, ddir, dnew);
-+      else
-+              err = vfs_link(dold, dirp, dnew);
-       if (!err) {
-               if (EX_ISSYNC(ffhp->fh_export)) {
-                       nfsd_sync_dir(ddir);
-@@ -1295,7 +1479,10 @@ nfsd_rename(struct svc_rqst *rqstp, stru
-                       err = nfserr_perm;
-       } else
- #endif
--      err = vfs_rename(fdir, odentry, tdir, ndentry);
-+      if (fdir->i_op->rename_raw)
-+              err = rename_raw(fdentry, tdentry, odentry, ndentry);
-+      else
-+              err = vfs_rename(fdir, odentry, tdir, ndentry);
-       if (!err && EX_ISSYNC(tfhp->fh_export)) {
-               nfsd_sync_dir(tdentry);
-               nfsd_sync_dir(fdentry);
-@@ -1316,7 +1503,7 @@ nfsd_rename(struct svc_rqst *rqstp, stru
-       fill_post_wcc(tfhp);
-       double_up(&tdir->i_sem, &fdir->i_sem);
-       ffhp->fh_locked = tfhp->fh_locked = 0;
--      
-+
- out:
-       return err;
- }
-@@ -1362,9 +1549,15 @@ nfsd_unlink(struct svc_rqst *rqstp, stru
-                       err = nfserr_perm;
-               } else
- #endif
--              err = vfs_unlink(dirp, rdentry);
-+              if (dirp->i_op->unlink_raw)
-+                      err = unlink_raw(dentry, fname, flen, rdentry);
-+              else
-+                      err = vfs_unlink(dirp, rdentry);
-       } else { /* It's RMDIR */
--              err = vfs_rmdir(dirp, rdentry);
-+              if (dirp->i_op->rmdir_raw)
-+                      err = rmdir_raw(dentry, fname, flen, rdentry);
-+              else
-+                      err = vfs_rmdir(dirp, rdentry);
-       }
-       dput(rdentry);
---- linux-2.4.22-ac1/include/linux/fs.h~nfs_export_kernel-2.4.22-rh    2003-09-26 01:00:26.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/fs.h 2003-10-08 13:44:53.000000000 +0400
-@@ -93,6 +93,8 @@ extern int leases_enable, dir_notify_ena
- #define FS_SINGLE     8 /* Filesystem that can have only one superblock */
- #define FS_NOMOUNT    16 /* Never mount from userland */
- #define FS_LITTER     32 /* Keeps the tree in dcache */
-+#define FS_NFSEXP_FSID        64 /* Use file system specific fsid for
-+                          * exporting non device filesystems. */
- #define FS_ALWAYS_REVAL       16384   /* Always revalidate dentries returned by
-                                  link_path_walk */
- #define FS_ODD_RENAME 32768   /* Temporary stuff; will go away as soon
-@@ -1121,6 +1124,9 @@ extern int open_namei_it(const char *fil
-                        struct nameidata *nd, struct lookup_intent *it);
- extern struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-                           int flags, struct lookup_intent *it);
-+extern int revalidate_it(struct dentry *dentry, struct lookup_intent *it);
-+extern int init_private_file_it(struct file *, struct dentry *dentry, int mode,
-+                              struct lookup_intent *it);
- extern int filp_close(struct file *, fl_owner_t id);
- extern char * getname(const char *);
-@@ -1420,6 +1426,8 @@ extern void path_release(struct nameidat
- extern int follow_down(struct vfsmount **, struct dentry **);
- extern int follow_up(struct vfsmount **, struct dentry **);
- extern struct dentry * lookup_one_len(const char *, struct dentry *, int);
-+extern struct dentry * lookup_one_len_it(const char *, struct dentry *, int,
-+                                       struct lookup_intent *);
- extern struct dentry * lookup_hash(struct qstr *, struct dentry *);
- #define user_path_walk(name,nd)        __user_walk(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd)
- #define user_path_walk_link(name,nd) __user_walk(name, LOOKUP_POSITIVE, nd)
-@@ -1439,6 +1447,8 @@ typedef int (*find_inode_t)(struct inode
- extern struct inode * iget4_locked(struct super_block *, unsigned long,
-                                  find_inode_t, void *);
-+extern struct inode * ilookup4(struct super_block *, unsigned long,
-+                             find_inode_t, void *);
-
- static inline struct inode *iget4(struct super_block *sb, unsigned long ino,
-                                 find_inode_t find_actor, void *opaque)
---- linux-2.4.22-ac1/kernel/ksyms.c~nfs_export_kernel-2.4.22-rh        2003-09-26 00:57:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/kernel/ksyms.c     2003-10-08 13:45:20.000000000 +0400
-@@ -165,6 +165,7 @@ EXPORT_SYMBOL(fget);
- EXPORT_SYMBOL(igrab);
- EXPORT_SYMBOL(iunique);
- EXPORT_SYMBOL(iget4_locked);
-+EXPORT_SYMBOL(ilookup4);
- EXPORT_SYMBOL(unlock_new_inode);
- EXPORT_SYMBOL(iput);
- EXPORT_SYMBOL(inode_init_once);
-@@ -178,6 +179,7 @@ EXPORT_SYMBOL(path_walk);
- EXPORT_SYMBOL(path_release);
- EXPORT_SYMBOL(__user_walk);
- EXPORT_SYMBOL(lookup_one_len);
-+EXPORT_SYMBOL(lookup_one_len_it);
- EXPORT_SYMBOL(lookup_hash);
- EXPORT_SYMBOL(sys_close);
- EXPORT_SYMBOL(dcache_lock);
diff --git a/lustre/kernel_patches/patches/revert-76chaos.patch b/lustre/kernel_patches/patches/revert-76chaos.patch
deleted file mode 100644 (file)
index 25f5440..0000000
+++ /dev/null
@@ -1,289 +0,0 @@
-Index: linux/arch/i386/kernel/traps.c
-===================================================================
---- linux.orig/arch/i386/kernel/traps.c        2004-11-05 19:00:03.000000000 -0800
-+++ linux/arch/i386/kernel/traps.c     2004-11-05 19:00:06.000000000 -0800
-@@ -133,141 +133,48 @@
- #endif
--void scan_stack (unsigned long *stack)
-+void show_trace(unsigned long * stack)
- {
-+#if !CONFIG_FRAME_POINTER
-       int i;
-+#endif
-       unsigned long addr;
--      /* static to not take up stackspace */
--      static char buffer[NR_CPUS][512], *bufp;
-+      /* static to not take up stackspace; if we race here too bad */
-+      static char buffer[512];
--      bufp = buffer[smp_processor_id()];
-+      if (!stack)
-+              stack = (unsigned long*)&stack;
-+      printk("Call Trace:   ");
-       /*
-        * If we have frame pointers then use them to get
-        * a 100% exact backtrace, up until the entry frame:
-        */
-+#if CONFIG_FRAME_POINTER
-+#define DO(n) \
-+      addr = (int)__builtin_return_address(n);        \
-+      if (!kernel_text_address(addr))                 \
-+              goto out;                               \
-+      lookup_symbol(addr, buffer, 512);               \
-+      printk("[<%08lx>] %s\n", addr, buffer);
-+
-+      DO(0); DO(1); DO(2); DO(3); DO(4); DO(5); DO(7); DO(8); DO(9);
-+      DO(10); DO(11); DO(12); DO(13); DO(14); DO(15); DO(17); DO(18); DO(19);
-+out:
-+#else
-       i = 1;
-       while (((long) stack & (THREAD_SIZE-1)) != 0) {
-               addr = *stack++;
-               if (kernel_text_address(addr)) {
--                      lookup_symbol(addr, bufp, 512);
--                      printk("[<%08lx>] %s (0x%p)\n", addr,bufp,stack-1);
-+                      lookup_symbol(addr, buffer, 512);
-+                      printk("[<%08lx>] %s (0x%p)\n", addr,buffer,stack-1);
-                       i++;
-               }
-       }
--}
--
--#if CONFIG_FRAME_POINTER
--void show_stack_frame_params (int param_count, unsigned long params[])
--{
--      int i;
--      unsigned long *p, task_addr, stack_base;
--
--      if (param_count <= 0)
--              return;
--
--      task_addr = (unsigned long) current;
--      stack_base = task_addr + THREAD_SIZE - 1;
--
--      printk("             (");
--
--      for (i = 0, p = params;
--           ((param_count - i) > 1) && (p >= task_addr) && (p <= stack_base);
--           i++, p++) {
--              printk("0x%x, ", *p);
--
--              if ((i % 4) == 3)
--                      printk("\n              ");
--      }
--
--      if ((p >= task_addr) && (p <= stack_base))
--              printk("0x%x)\n", *p);
--}
--
--/* Display a stack trace for the currently executing task.  The 'dummy'
-- * parameter serves a purpose although its value is unused.  We use the
-- * address of 'dummy' as a reference point for finding the saved %ebp register
-- * value on the stack.
-- */
--void frame_pointer_walk (void *dummy)
--{
--      int i;
--      unsigned long addr, task_addr, *frame_ptr, *next_frame_ptr, *eip_ptr,
--                    eip, stack_base;
--      /* static to not take up stackspace */
--      static char buffer[NR_CPUS][512], *bufp;
--
--      bufp = buffer[smp_processor_id()];
--      task_addr = (unsigned long) current;
--      stack_base = task_addr + THREAD_SIZE - 1;
--      frame_ptr = (unsigned long *) (&dummy - 2);
--
--      for (; ; ) {
--              next_frame_ptr = (unsigned long *) (*frame_ptr);
--              addr = (unsigned long) next_frame_ptr;
--
--              /* Stop when we reach a frame pointer that points to a
--               * location clearly outside our own kernel stack.
--               */
--              if ((addr < task_addr) || (addr > stack_base))
--                      break;
--
--              eip_ptr = frame_ptr + 1;
--              eip = *eip_ptr;
--
--              if (kernel_text_address(eip)) {
--                      lookup_symbol(eip, bufp, 512);
--                      show_stack_frame_params(4, frame_ptr + 2);
--                      printk("[<%08lx>] %s (0x%x)\n", eip, bufp,
--                             eip_ptr);
--              }
--
--              frame_ptr = next_frame_ptr;
--      }
--}
--
--typedef void (*stack_trace_fn_t) (unsigned long *stack);
--
--void show_trace(unsigned long * stack)
--{
--      static const stack_trace_fn_t trace_fn_vector[] =
--              { scan_stack, frame_pointer_walk };
--      unsigned long addr, task_addr, stack_base;
--      int task_is_current;
--
--      if (!stack)
--              stack = (unsigned long*)&stack;
--
--      printk("Call Trace:\n");
--      addr = (unsigned long) stack;
--      task_addr = (unsigned long) current;
--      stack_base = task_addr + THREAD_SIZE - 1;
--      task_is_current = (addr >= task_addr) && (addr <= stack_base);
--
--      /* We may use frame pointers to do a stack trace only if the current
--       * task is being traced.  Tracing some other task in this manner
--       * would require a saved %ebp register value.  Perhaps in the future
--       * I'll consider providing a means of obtaining this.
--       */
--      trace_fn_vector[task_is_current](stack);
--
--      printk("\n");
--}
--
--#else /* CONFIG_FRAME_POINTER */
--
--void show_trace(unsigned long * stack)
--{
--      if (!stack)
--              stack = (unsigned long*)&stack;
--
--      printk("Call Trace:\n");
--      scan_stack(stack);
-+#endif
-       printk("\n");
- }
--#endif /* CONFIG_FRAME_POINTER */
--
- void show_trace_task(struct task_struct *tsk)
- {
-       unsigned long esp = tsk->thread.esp;
-Index: linux/fs/namei.c
-===================================================================
---- linux.orig/fs/namei.c      2004-11-05 19:00:03.000000000 -0800
-+++ linux/fs/namei.c   2004-11-05 19:00:06.000000000 -0800
-@@ -1022,7 +1022,7 @@
-        * The simplest case - just a plain lookup.
-        */
-       if (!(flag & O_CREAT)) {
--              error = path_lookup_it(pathname, lookup_flags(flag), nd);
-+              error = path_lookup(pathname, lookup_flags(flag), nd);
-               if (error)
-                       return error;
-               dentry = nd->dentry;
-Index: linux/include/asm-i386/hw_irq.h
-===================================================================
---- linux.orig/include/asm-i386/hw_irq.h       2004-11-05 19:00:03.000000000 -0800
-+++ linux/include/asm-i386/hw_irq.h    2004-11-05 19:00:06.000000000 -0800
-@@ -158,9 +158,6 @@
-       /* there is a second layer of macro just to get the symbolic
-          name for the vector evaluated. This change is for RTLinux */
- #define BUILD_SMP_INTERRUPT(x,v) XBUILD_SMP_INTERRUPT(x,v)
--
--#if CONFIG_X86_HIGH_ENTRY
--
- #define XBUILD_SMP_INTERRUPT(x,v)\
- asmlinkage void x(void); \
- asmlinkage void call_##x(void); \
-@@ -173,26 +170,7 @@
-       "movl $"SYMBOL_NAME_STR(smp_##x)", %ebp; call *%ebp\n\t" \
-       "jmp ret_from_intr; .previous\n");
--#else
--
--#define XBUILD_SMP_INTERRUPT(x,v)\
--asmlinkage void x(void); \
--asmlinkage void call_##x(void); \
--__asm__( \
--".section .entry.text,\"ax\"\n"__ALIGN_STR"\n" \
--SYMBOL_NAME_STR(x) ":\n\t" \
--      "pushl $"#v"-256\n\t" \
--      SAVE_ALL_SWITCH \
--      SYMBOL_NAME_STR(call_##x)":\n\t" \
--      "call "SYMBOL_NAME_STR(smp_##x)"\n\t" \
--      "jmp ret_from_intr; .previous\n");
--
--#endif
--
- #define BUILD_SMP_TIMER_INTERRUPT(x,v) XBUILD_SMP_TIMER_INTERRUPT(x,v)
--
--#if CONFIG_X86_HIGH_ENTRY
--
- #define XBUILD_SMP_TIMER_INTERRUPT(x,v) \
- asmlinkage void x(struct pt_regs * regs); \
- asmlinkage void call_##x(void); \
-@@ -208,27 +186,6 @@
-       "addl $4,%esp\n\t" \
-       "jmp ret_from_intr; .previous\n");
--#else
--
--#define XBUILD_SMP_TIMER_INTERRUPT(x,v) \
--asmlinkage void x(struct pt_regs * regs); \
--asmlinkage void call_##x(void); \
--__asm__( \
--".section .entry.text,\"ax\"\n"__ALIGN_STR"\n" \
--SYMBOL_NAME_STR(x) ":\n\t" \
--      "pushl $"#v"-256\n\t" \
--      SAVE_ALL_SWITCH \
--      "movl %esp,%eax\n\t" \
--      "pushl %eax\n\t" \
--      SYMBOL_NAME_STR(call_##x)":\n\t" \
--      "call "SYMBOL_NAME_STR(smp_##x)"\n\t" \
--      "addl $4,%esp\n\t" \
--      "jmp ret_from_intr; .previous\n");
--
--#endif
--
--#if CONFIG_X86_HIGH_ENTRY
--
- #define BUILD_COMMON_IRQ() \
- asmlinkage void call_do_IRQ(void); \
- __asm__( \
-@@ -239,20 +196,6 @@
-       "movl $"SYMBOL_NAME_STR(do_IRQ)", %ebp; call *%ebp\n\t" \
-       "jmp ret_from_intr; .previous\n");
--#else
--
--#define BUILD_COMMON_IRQ() \
--asmlinkage void call_do_IRQ(void); \
--__asm__( \
--      ".section .entry.text,\"ax\"\n" __ALIGN_STR"\n" \
--      "common_interrupt:\n\t" \
--      SAVE_ALL_SWITCH \
--      SYMBOL_NAME_STR(call_do_IRQ)":\n\t" \
--      "call "SYMBOL_NAME_STR(do_IRQ)"\n\t" \
--      "jmp ret_from_intr; .previous\n");
--
--#endif
--
- /* 
-  * subtle. orig_eax is used by the signal code to distinct between
-  * system calls and interrupted 'random user-space'. Thus we have
-Index: linux/mm/highmem.c
-===================================================================
---- linux.orig/mm/highmem.c    2004-11-05 08:59:32.000000000 -0800
-+++ linux/mm/highmem.c 2004-11-05 19:00:06.000000000 -0800
-@@ -465,11 +465,7 @@
- /*
-  * FIXME: assuming PAGE_SIZE buffer_heads
-  */
--
--/*
-- * don't allow SUPERBH_MAX_USERS to go < 1 - mag
-- */
--#define SUPERBH_MAX_USERS     max(POOL_SIZE * PAGE_SIZE / MAX_SUPERBH, 1)
-+#define SUPERBH_MAX_USERS     (POOL_SIZE * PAGE_SIZE / MAX_SUPERBH)
- static int superbh_users;
- static DECLARE_WAIT_QUEUE_HEAD(superbh_wait);
diff --git a/lustre/kernel_patches/patches/sd_iostats-2.6-rhel4.patch b/lustre/kernel_patches/patches/sd_iostats-2.6-rhel4.patch
new file mode 100644 (file)
index 0000000..d8494ff
--- /dev/null
@@ -0,0 +1,457 @@
+Index: linux-2.6.9-5.0.3.EL/drivers/scsi/Kconfig
+===================================================================
+--- linux-2.6.9-5.0.3.EL.orig/drivers/scsi/Kconfig     2005-02-25 03:25:42.000000000 -0500
++++ linux-2.6.9-5.0.3.EL/drivers/scsi/Kconfig  2005-03-03 16:10:10.000000000 -0500
+@@ -61,6 +61,13 @@
+       help
+          SCSI dump support
++config SD_IOSTATS
++   bool "Enable SCSI disk I/O stats"
++   depends on BLK_DEV_SD
++   ---help---
++     This enables SCSI disk I/O stats collection.  You must also enable
++     /proc file system support if you want this feature.
++
+ config CHR_DEV_ST
+       tristate "SCSI tape support"
+       depends on SCSI
+Index: linux-2.6.9-5.0.3.EL/drivers/scsi/sd.c
+===================================================================
+--- linux-2.6.9-5.0.3.EL.orig/drivers/scsi/sd.c        2005-02-25 03:25:40.000000000 -0500
++++ linux-2.6.9-5.0.3.EL/drivers/scsi/sd.c     2005-03-03 16:11:07.000000000 -0500
+@@ -63,6 +63,38 @@
+ #include "scsi_logging.h"
++#if (defined(CONFIG_SD_IOSTATS) && defined(CONFIG_PROC_FS))
++# include <linux/proc_fs.h>
++# include <linux/seq_file.h>
++
++typedef struct {
++        unsigned long long iostat_size;
++        unsigned long long iostat_count;
++} iostat_counter_t;
++
++#define IOSTAT_NCOUNTERS 16
++typedef struct {
++        iostat_counter_t        iostat_read_histogram[IOSTAT_NCOUNTERS];
++        iostat_counter_t        iostat_write_histogram[IOSTAT_NCOUNTERS];
++        struct timeval          iostat_timeval;
++} iostat_stats_t;
++
++iostat_stats_t       **sd_iostats;
++spinlock_t             sd_iostats_lock;
++struct proc_dir_entry *sd_iostats_procdir;
++char                   sd_iostats_procdir_name[] = "sd_iostats";
++
++extern void sd_iostats_init(void);
++extern void sd_iostats_init_disk(struct gendisk *);
++extern void sd_iostats_fini(void);
++extern void sd_iostats_bump(int disk, unsigned int nsect, int iswrite);
++#else
++static inline void sd_iostats_init(void) {}
++static inline void sd_iostats_init_disk(struct gendisk *) {}
++static inline void sd_iostats_fini(void) {}
++static inline void sd_iostats_bump(kdev_t dev, unsigned int nsect, int iswrite) {}
++#endif
++
+ /*
+  * More than enough for everybody ;)  The huge number of majors
+  * is a leftover from 16bit dev_t days, we don't really need that
+@@ -76,6 +108,7 @@
+  */
+ #define SD_MAX_DISKS  (((26 * 26) + 26 + 1) * 26)
++#define SD_STATS 256
+ /*
+  * Time out in seconds for disks and Magneto-opticals (which are slower).
+  */
+@@ -276,6 +309,9 @@
+       SCSI_LOG_HLQUEUE(2, printk("%s : block=%llu\n",
+                                  disk->disk_name, (unsigned long long)block));
++   sd_iostats_bump(scsi_disk(disk)->index, this_count,
++                   rq_data_dir(SCpnt->request) == WRITE);
++
+       /*
+        * If we have a 1K hardware sectorsize, prevent access to single
+        * 512 byte sectors.  In theory we could handle this - in fact
+@@ -472,6 +508,7 @@
+                       scsi_set_medium_removal(sdev, SCSI_REMOVAL_PREVENT);
+       }
++   sd_iostats_init_disk(disk);
+       return 0;
+ error_out:
+@@ -1573,6 +1610,327 @@
+       sd_sync_cache(sdp);
+ }     
++#if (defined(CONFIG_SD_IOSTATS) && defined(CONFIG_PROC_FS))
++static int
++sd_iostats_seq_show(struct seq_file *seq, void *v)
++{
++        struct timeval     now;
++        struct gendisk *disk = seq->private;
++        iostat_stats_t    *stats;
++        unsigned long long read_len;
++        unsigned long long read_len_tot;
++        unsigned long      read_num;
++        unsigned long      read_num_tot;
++        unsigned long long write_len;
++        unsigned long long write_len_tot;
++        unsigned long      write_num;
++        unsigned long      write_num_tot;
++        int                i;
++        int                maxi;
++
++        if (sd_iostats == NULL) {
++                printk(KERN_ERR "sd_iostats_seq_show: NULL stats array\n");
++                BUG();
++        }
++
++        stats = sd_iostats[scsi_disk(disk)->index];
++        if (stats == NULL) {
++                printk(KERN_ERR "sd_iostats_seq_show: NULL stats entry\n");
++                BUG();
++        }
++
++        do_gettimeofday(&now);
++        now.tv_sec -= stats->iostat_timeval.tv_sec;
++        now.tv_usec -= stats->iostat_timeval.tv_usec;
++        if (now.tv_usec < 0) {
++                now.tv_usec += 1000000;
++                now.tv_sec--;
++        }
++
++        /* this sampling races with updates */
++        seq_printf(seq, "index:        %lu   snapshot_time:         %lu.%06lu\n",
++                   scsi_disk(disk)->index, now.tv_sec, now.tv_usec);
++
++        for (i = IOSTAT_NCOUNTERS - 1; i > 0; i--)
++                if (stats->iostat_read_histogram[i].iostat_count != 0 ||
++                    stats->iostat_write_histogram[i].iostat_count != 0)
++                        break;
++        maxi = i;
++
++        seq_printf(seq, "%8s %8s %12s %8s %12s\n", "size", 
++                   "reads", "total", "writes", "total");
++
++        read_len_tot = write_len_tot = 0;
++        read_num_tot = write_num_tot = 0;
++        for (i = 0; i <= maxi; i++) {
++                read_len = stats->iostat_read_histogram[i].iostat_size;
++                read_len_tot += read_len;
++                read_num = stats->iostat_read_histogram[i].iostat_count;
++                read_num_tot += read_num;
++
++                write_len = stats->iostat_write_histogram[i].iostat_size;
++                write_len_tot += write_len;
++                write_num = stats->iostat_write_histogram[i].iostat_count;
++                write_num_tot += write_num;
++
++                seq_printf (seq, "%8d %8lu %12llu %8lu %12llu\n", 
++                            512<<i, read_num, read_len, write_num, write_len);
++        }
++        
++        seq_printf(seq, "%8s %8lu %12llu %8lu %12llu\n", "total",
++                   read_num_tot, read_len_tot, 
++                   write_num_tot, write_len_tot);
++        return 0;
++}
++
++static void *
++sd_iostats_seq_start(struct seq_file *p, loff_t *pos)
++{
++        return (*pos == 0) ? (void *)1 : NULL;
++}
++
++static void *
++sd_iostats_seq_next(struct seq_file *p, void *v, loff_t *pos)
++{
++        ++*pos;
++        return NULL;
++}
++
++static void
++sd_iostats_seq_stop(struct seq_file *p, void *v)
++{
++}
++
++static struct seq_operations sd_iostats_seqops = {
++        .start = sd_iostats_seq_start,
++        .stop  = sd_iostats_seq_stop,
++        .next  = sd_iostats_seq_next,
++        .show  = sd_iostats_seq_show,
++};
++
++static int
++sd_iostats_seq_open (struct inode *inode, struct file *file)
++{
++        int                    rc;
++
++        rc = seq_open(file, &sd_iostats_seqops);
++        if (rc != 0)
++                return rc;
++
++        ((struct seq_file *)file->private_data)->private = PDE(inode)->data;
++        return 0;
++}
++
++static ssize_t
++sd_iostats_seq_write(struct file *file, const char *buffer,
++                     size_t len, loff_t *off)
++{
++        struct seq_file   *seq = file->private_data;
++        struct gendisk *disk = seq->private;
++        iostat_stats_t    *stats = sd_iostats[scsi_disk(disk)->index];
++        unsigned long      flags;
++        
++        
++        spin_lock_irqsave (&sd_iostats_lock, flags);
++        memset (stats, 0, sizeof(*stats));
++        do_gettimeofday(&stats->iostat_timeval);
++        spin_unlock_irqrestore (&sd_iostats_lock, flags);
++
++        return len;
++}
++
++static struct file_operations sd_iostats_proc_fops = {
++        .owner   = THIS_MODULE,
++        .open    = sd_iostats_seq_open,
++        .read    = seq_read,
++        .write   = sd_iostats_seq_write,
++        .llseek  = seq_lseek,
++        .release = seq_release,
++};
++
++extern struct proc_dir_entry *proc_scsi;
++
++void
++sd_iostats_init(void)
++{
++        int    i;
++
++        spin_lock_init(&sd_iostats_lock);
++
++        sd_iostats = kmalloc(SD_STATS * sizeof(iostat_stats_t *), GFP_KERNEL);
++        if (sd_iostats == NULL) {
++                printk(KERN_WARNING "Can't keep sd iostats: "
++                       "ENOMEM allocating stats array size %ld\n",
++                       SD_STATS * sizeof(iostat_stats_t *));
++                return;
++        }
++
++        for (i = 0; i < SD_STATS; i++)
++                sd_iostats[i] = NULL;
++
++        if (proc_scsi == NULL) {
++                printk(KERN_WARNING "No access to sd iostats: "
++                       "proc_scsi is NULL\n");
++                return;
++        }
++
++        sd_iostats_procdir = create_proc_entry(sd_iostats_procdir_name,
++                                               S_IFDIR | S_IRUGO | S_IXUGO,
++                                               proc_scsi);
++        if (sd_iostats_procdir == NULL) {
++                printk(KERN_WARNING "No access to sd iostats: "
++                       "can't create /proc/scsi/%s\n", sd_iostats_procdir_name);
++                return;
++        }
++}
++
++void
++sd_iostats_init_disk(struct gendisk *disk)
++{
++        struct proc_dir_entry *pde;
++        unsigned long          flags;
++        iostat_stats_t        *stats;
++
++        if (sd_iostats == NULL ||
++            sd_iostats_procdir == NULL)
++                return;
++
++        if (scsi_disk(disk)->index > SD_STATS) {
++                printk(KERN_ERR "sd_iostats_init_disk: "
++                       "unexpected disk index %d(%d)\n",
++                       scsi_disk(disk)->index, SD_STATS);
++                                  return;
++        }
++
++        if (sd_iostats[scsi_disk(disk)->index] != NULL)
++                return;
++
++        stats = kmalloc(sizeof(*stats), GFP_KERNEL);
++        if (stats == NULL) {
++                printk(KERN_WARNING "Can't keep %s iostats: "
++                       "ENOMEM allocating stats size %ld\n", 
++                       disk->disk_name, sizeof(*stats));
++                return;
++        }
++
++        memset (stats, 0, sizeof(*stats));
++        do_gettimeofday(&stats->iostat_timeval);
++
++        spin_lock_irqsave(&sd_iostats_lock, flags);
++
++        if (sd_iostats[scsi_disk(disk)->index] != NULL) {
++                spin_unlock_irqrestore(&sd_iostats_lock, flags);
++                kfree (stats);
++                return;
++        }
++
++        sd_iostats[scsi_disk(disk)->index] = stats;
++        
++        spin_unlock_irqrestore(&sd_iostats_lock, flags);
++        
++        pde = create_proc_entry(disk->disk_name, S_IRUGO | S_IWUSR, 
++                                sd_iostats_procdir);
++        if (pde == NULL) {
++                printk(KERN_WARNING "Can't create /proc/scsi/%s/%s\n",
++                       sd_iostats_procdir_name, disk->disk_name);
++        } else {
++                pde->proc_fops = &sd_iostats_proc_fops;
++                pde->data = disk;
++        }
++}
++
++static void sd_devname(unsigned int disknum, char *buffer)
++{
++        if (disknum < 26)
++                sprintf(buffer, "sd%c", 'a' + disknum);
++        else {
++                unsigned int min1;
++                unsigned int min2;
++                /*
++                 * For larger numbers of disks, we need to go to a new
++                 * naming scheme.
++                 */
++                min1 = disknum / 26;
++                min2 = disknum % 26;
++                sprintf(buffer, "sd%c%c", 'a' + min1 - 1, 'a' + min2);
++        }
++}
++
++void
++sd_iostats_fini(void)
++{
++        char name[6];
++        int  i;
++        
++        if (sd_iostats_procdir != NULL) {
++                for (i = 0; i < SD_STATS; i++) {
++                        sd_devname(i, name);
++                        remove_proc_entry(name, sd_iostats_procdir);
++                }
++
++                if (proc_scsi == NULL) {
++                        printk(KERN_ERR "sd_iostats_fini: proc_scsi NULL\n");
++                        BUG();
++                }
++                remove_proc_entry(sd_iostats_procdir_name,
++                                  proc_scsi);
++
++                sd_iostats_procdir = NULL;
++        }
++        
++        if (sd_iostats != NULL) {
++                for (i = 0; i < SD_STATS; i++) {
++                        if (sd_iostats[i] != NULL)
++                                kfree (sd_iostats[i]);
++                }
++                
++                kfree(sd_iostats);
++                sd_iostats = NULL;
++        }
++}
++
++void
++sd_iostats_bump(int disk, unsigned int nsect, int iswrite)
++{
++        iostat_stats_t    *stats;
++        iostat_counter_t  *counter;
++        int                bucket;
++        int                tmp;
++        unsigned long      irqflags;
++
++        if (sd_iostats == NULL)
++                return;
++
++        if (disk < 0 || disk >= SD_STATS) {
++                printk(KERN_ERR "sd_iostats_bump: unexpected disk index %d([0-%d])\n",
++                       disk, SD_STATS);
++                BUG();
++        }
++
++        for (bucket = 0, tmp = nsect; tmp > 1; bucket++)
++                tmp /= 2;
++
++        if (bucket >= IOSTAT_NCOUNTERS) {
++                printk (KERN_ERR "sd_iostats_bump: nsect %d too big\n", nsect);
++                BUG();
++        }
++
++        spin_lock_irqsave(&sd_iostats_lock, irqflags);
++        
++        stats = sd_iostats[disk];
++        if (stats != NULL) {
++                counter = iswrite ? 
++                          &stats->iostat_write_histogram[bucket] :
++                          &stats->iostat_read_histogram[bucket];
++
++                counter->iostat_size += nsect;
++                counter->iostat_count++;
++        }
++
++        spin_unlock_irqrestore(&sd_iostats_lock, irqflags);
++}
++#endif
++
+ /**
+  *    init_sd - entry point for this driver (both when built in or when
+  *    a module).
+@@ -1582,6 +1940,7 @@
+ static int __init init_sd(void)
+ {
+       int majors = 0, i;
++   int rc = 0;
+       SCSI_LOG_HLQUEUE(3, printk("init_sd: sd driver entry point\n"));
+@@ -1592,7 +1951,10 @@
+       if (!majors)
+               return -ENODEV;
+-      return scsi_register_driver(&sd_template.gendrv);
++   rc = scsi_register_driver(&sd_template.gendrv);
++   if (rc == 0)
++      sd_iostats_init();
++   return rc;
+ }
+ /**
+@@ -1606,6 +1968,7 @@
+       SCSI_LOG_HLQUEUE(3, printk("exit_sd: exiting sd driver\n"));
++   sd_iostats_fini();
+       scsi_unregister_driver(&sd_template.gendrv);
+       for (i = 0; i < SD_MAJORS; i++)
+               unregister_blkdev(sd_major(i), "sd");
+Index: linux-2.6.9-5.0.3.EL/drivers/scsi/scsi_proc.c
+===================================================================
+--- linux-2.6.9-5.0.3.EL.orig/drivers/scsi/scsi_proc.c 2004-10-18 17:53:11.000000000 -0400
++++ linux-2.6.9-5.0.3.EL/drivers/scsi/scsi_proc.c      2005-03-03 16:10:10.000000000 -0500
+@@ -38,7 +38,8 @@
+ /* 4K page size, but our output routines, use some slack for overruns */
+ #define PROC_BLOCK_SIZE (3*1024)
+-static struct proc_dir_entry *proc_scsi;
++struct proc_dir_entry *proc_scsi;
++EXPORT_SYMBOL(proc_scsi);
+ /* Protect sht->present and sht->proc_dir */
+ static DECLARE_MUTEX(global_host_template_sem);
diff --git a/lustre/kernel_patches/patches/socket-exports-2.4.22-rh.patch b/lustre/kernel_patches/patches/socket-exports-2.4.22-rh.patch
deleted file mode 100644 (file)
index 08ca1b2..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
- include/linux/socket.h |    4 ++++
- net/netsyms.c          |    1 +
- net/socket.c           |    2 +-
- 3 files changed, 6 insertions(+), 1 deletion(-)
-
---- linux-2.4.22-ac1/include/linux/socket.h~socket-exports-2.4.22-rh   2003-06-13 18:51:39.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/socket.h     2003-09-26 00:49:43.000000000 +0400
-@@ -275,6 +275,10 @@ extern void memcpy_tokerneliovec(struct 
- extern int move_addr_to_user(void *kaddr, int klen, void *uaddr, int *ulen);
- extern int move_addr_to_kernel(void *uaddr, int ulen, void *kaddr);
- extern int put_cmsg(struct msghdr*, int level, int type, int len, void *data);
-+struct socket;
-+extern int sock_map_fd(struct socket *sock);
-+extern struct socket *sockfd_lookup(int fd, int *err);
-+
- #endif
- #endif /* not kernel and not glibc */
- #endif /* _LINUX_SOCKET_H */
---- linux-2.4.22-ac1/net/netsyms.c~socket-exports-2.4.22-rh    2003-09-26 00:49:19.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/net/netsyms.c      2003-09-26 00:50:20.000000000 +0400
-@@ -163,6 +163,7 @@ EXPORT_SYMBOL(put_cmsg);
- EXPORT_SYMBOL(sock_kmalloc);
- EXPORT_SYMBOL(sock_kfree_s);
- EXPORT_SYMBOL(sockfd_lookup);
-+EXPORT_SYMBOL(sock_map_fd);
- #ifdef CONFIG_FILTER
- EXPORT_SYMBOL(sk_run_filter);
---- linux-2.4.22-ac1/net/socket.c~socket-exports-2.4.22-rh     2003-08-25 15:44:44.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/net/socket.c       2003-09-26 00:49:43.000000000 +0400
-@@ -325,7 +325,7 @@ static struct dentry_operations sockfs_d
-  *    but we take care of internal coherence yet.
-  */
--static int sock_map_fd(struct socket *sock)
-+int sock_map_fd(struct socket *sock)
- {
-       int fd;
-       struct qstr this;
-
-_
diff --git a/lustre/kernel_patches/patches/tcp_zero_copy_2.4.20_chaos.patch b/lustre/kernel_patches/patches/tcp_zero_copy_2.4.20_chaos.patch
deleted file mode 100644 (file)
index a64ecf9..0000000
+++ /dev/null
@@ -1,476 +0,0 @@
- include/linux/skbuff.h |   30 +++++
- include/net/tcp.h      |    5 
- net/core/skbuff.c      |   25 ++++
- net/ipv4/tcp.c         |  252 ++++++++++++++++++++++++++++++++++++++++++++++++-
- net/netsyms.c          |    2 
- 5 files changed, 311 insertions(+), 3 deletions(-)
-
-Index: linux-2.4.20-rh-20.9/include/linux/skbuff.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/linux/skbuff.h   2003-09-13 19:34:24.000000000 +0400
-+++ linux-2.4.20-rh-20.9/include/linux/skbuff.h        2003-12-19 14:14:55.000000000 +0300
-@@ -116,6 +116,30 @@
-       __u16 size;
- };
-+/* Support for callback when skb data has been released */
-+typedef struct zccd                           /* Zero Copy Callback Descriptor */
-+{                                             /* (embed as first member of custom struct) */
-+      atomic_t        zccd_count;             /* reference count */
-+      void           (*zccd_destructor)(struct zccd *); /* callback when refcount reaches zero */
-+} zccd_t;
-+
-+static inline void zccd_init (zccd_t *d, void (*callback)(zccd_t *))
-+{
-+      atomic_set (&d->zccd_count, 1);
-+      d->zccd_destructor = callback;
-+}
-+
-+static inline void zccd_get (zccd_t *d)               /* take a reference */
-+{
-+      atomic_inc (&d->zccd_count);
-+}
-+
-+static inline void zccd_put (zccd_t *d)               /* release a reference */
-+{
-+      if (atomic_dec_and_test (&d->zccd_count))
-+              (d->zccd_destructor)(d);
-+}
-+
- /* This data is invariant across clones and lives at
-  * the end of the header data, ie. at skb->end.
-  */
-@@ -123,6 +147,12 @@
-       atomic_t        dataref;
-       unsigned int    nr_frags;
-       struct sk_buff  *frag_list;
-+      zccd_t          *zccd;                  /* zero copy descriptor */
-+      zccd_t          *zccd2;                 /* 2nd zero copy descriptor */
-+      /* NB we expect zero-copy data to be at least 1 packet, so
-+       * having 2 zccds means we don't unneccessarily split the packet
-+       * where consecutive zero-copy sends abutt.
-+       */
-       skb_frag_t      frags[MAX_SKB_FRAGS];
- };
-Index: linux-2.4.20-rh-20.9/include/net/tcp.h
-===================================================================
---- linux-2.4.20-rh-20.9.orig/include/net/tcp.h        2003-09-13 19:34:25.000000000 +0400
-+++ linux-2.4.20-rh-20.9/include/net/tcp.h     2003-12-19 14:14:55.000000000 +0300
-@@ -643,6 +643,8 @@
- extern int                    tcp_sendmsg(struct sock *sk, struct msghdr *msg, int size);
- extern ssize_t                        tcp_sendpage(struct socket *sock, struct page *page, int offset, size_t size, int flags);
-+extern ssize_t                        tcp_sendpage_zccd(struct socket *sock, struct page *page, int offset, size_t size,
-+                                                int flags, zccd_t *zccd);
- extern int                    tcp_ioctl(struct sock *sk, 
-                                         int cmd, 
-@@ -737,6 +739,9 @@
-                                           struct msghdr *msg,
-                                           int len, int nonblock, 
-                                           int flags, int *addr_len);
-+extern int                    tcp_recvpackets(struct sock *sk,
-+                                              struct sk_buff_head *packets,
-+                                              int len, int nonblock);
- extern int                    tcp_listen_start(struct sock *sk);
-Index: linux-2.4.20-rh-20.9/net/netsyms.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/net/netsyms.c    2003-09-13 19:34:24.000000000 +0400
-+++ linux-2.4.20-rh-20.9/net/netsyms.c 2003-12-19 14:15:24.000000000 +0300
-@@ -396,7 +396,7 @@
- EXPORT_SYMBOL(sysctl_tcp_wmem);
- EXPORT_SYMBOL(sysctl_tcp_ecn);
- EXPORT_SYMBOL(tcp_cwnd_application_limited);
--EXPORT_SYMBOL(tcp_sendpage);
-+EXPORT_SYMBOL(tcp_recvpackets);
- EXPORT_SYMBOL(sysctl_tcp_low_latency);
- EXPORT_SYMBOL(tcp_write_xmit);
-@@ -417,6 +417,8 @@
- #endif
-+EXPORT_SYMBOL(tcp_sendpage);
-+EXPORT_SYMBOL(tcp_sendpage_zccd);
- EXPORT_SYMBOL(tcp_read_sock);
- EXPORT_SYMBOL(netlink_set_err);
-Index: linux-2.4.20-rh-20.9/net/core/skbuff.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/net/core/skbuff.c        2003-09-13 19:34:19.000000000 +0400
-+++ linux-2.4.20-rh-20.9/net/core/skbuff.c     2003-12-19 14:14:56.000000000 +0300
-@@ -208,6 +208,8 @@
-       atomic_set(&(skb_shinfo(skb)->dataref), 1);
-       skb_shinfo(skb)->nr_frags = 0;
-       skb_shinfo(skb)->frag_list = NULL;
-+      skb_shinfo(skb)->zccd = NULL;           /* skbuffs kick off with NO user zero copy descriptors */
-+      skb_shinfo(skb)->zccd2 = NULL;
-       return skb;
- nodata:
-@@ -276,6 +278,10 @@
- {
-       if (!skb->cloned ||
-           atomic_dec_and_test(&(skb_shinfo(skb)->dataref))) {
-+              if (skb_shinfo(skb)->zccd != NULL) /* zero copy callback descriptor? */
-+                      zccd_put (skb_shinfo(skb)->zccd); /* release hold */
-+              if (skb_shinfo(skb)->zccd2 != NULL) /* 2nd zero copy callback descriptor? */
-+                      zccd_put (skb_shinfo(skb)->zccd2); /* release hold */
-               if (skb_shinfo(skb)->nr_frags) {
-                       int i;
-                       for (i = 0; i < skb_shinfo(skb)->nr_frags; i++)
-@@ -532,6 +538,8 @@
-       atomic_set(&(skb_shinfo(skb)->dataref), 1);
-       skb_shinfo(skb)->nr_frags = 0;
-       skb_shinfo(skb)->frag_list = NULL;
-+      skb_shinfo(skb)->zccd = NULL;           /* copied data => no user zero copy descriptor */
-+      skb_shinfo(skb)->zccd2 = NULL;
-       /* We are no longer a clone, even if we were. */
-       skb->cloned = 0;
-@@ -578,6 +586,14 @@
-       n->data_len = skb->data_len;
-       n->len = skb->len;
-+      if (skb_shinfo(skb)->zccd != NULL)      /* user zero copy descriptor? */
-+              zccd_get (skb_shinfo(skb)->zccd); /* 1 more ref (pages are shared) */
-+      skb_shinfo(n)->zccd = skb_shinfo(skb)->zccd;
-+
-+      if (skb_shinfo(skb)->zccd2 != NULL)     /* 2nd user zero copy descriptor? */
-+              zccd_get (skb_shinfo(skb)->zccd2); /* 1 more ref (pages are shared) */
-+      skb_shinfo(n)->zccd2 = skb_shinfo(skb)->zccd2;
-+
-       if (skb_shinfo(skb)->nr_frags) {
-               int i;
-@@ -620,6 +636,8 @@
-       u8 *data;
-       int size = nhead + (skb->end - skb->head) + ntail;
-       long off;
-+      zccd_t *zccd = skb_shinfo(skb)->zccd;   /* stash user zero copy descriptor */
-+      zccd_t *zccd2 = skb_shinfo(skb)->zccd2; /* stash 2nd user zero copy descriptor */
-       if (skb_shared(skb))
-               BUG();
-@@ -641,6 +659,11 @@
-       if (skb_shinfo(skb)->frag_list)
-               skb_clone_fraglist(skb);
-+      if (zccd != NULL)                       /* user zero copy descriptor? */
-+              zccd_get (zccd);                /* extra ref (pages are shared) */
-+      if (zccd2 != NULL)                      /* 2nd user zero copy descriptor? */
-+              zccd_get (zccd2);               /* extra ref (pages are shared) */
-+
-       skb_release_data(skb);
-       off = (data+nhead) - skb->head;
-@@ -655,6 +678,8 @@
-       skb->nh.raw += off;
-       skb->cloned = 0;
-       atomic_set(&skb_shinfo(skb)->dataref, 1);
-+      skb_shinfo(skb)->zccd = zccd;
-+      skb_shinfo(skb)->zccd2 = zccd2;
-       return 0;
- nodata:
-Index: linux-2.4.20-rh-20.9/net/ipv4/tcp.c
-===================================================================
---- linux-2.4.20-rh-20.9.orig/net/ipv4/tcp.c   2003-09-13 19:34:25.000000000 +0400
-+++ linux-2.4.20-rh-20.9/net/ipv4/tcp.c        2003-12-19 14:14:56.000000000 +0300
-@@ -747,7 +747,7 @@
-       goto out;
- }
--ssize_t do_tcp_sendpages(struct sock *sk, struct page **pages, int poffset, size_t psize, int flags);
-+ssize_t do_tcp_sendpages(struct sock *sk, struct page **pages, int poffset, size_t psize, int flags, zccd_t *zccd);
- static inline int
- can_coalesce(struct sk_buff *skb, int i, struct page *page, int off)
-@@ -826,7 +826,8 @@
-       return err;
- }
--ssize_t do_tcp_sendpages(struct sock *sk, struct page **pages, int poffset, size_t psize, int flags)
-+/* Extra parameter: user zero copy descriptor (or NULL if not doing that) */
-+ssize_t do_tcp_sendpages(struct sock *sk, struct page **pages, int poffset, size_t psize, int flags, zccd_t *zccd)
- {
-       struct tcp_opt *tp = &(sk->tp_pinfo.af_tcp);
-       int mss_now;
-@@ -874,6 +875,17 @@
-                       copy = size;
-               i = skb_shinfo(skb)->nr_frags;
-+
-+              if (zccd != NULL &&             /* this is a zcc I/O */
-+                  skb_shinfo(skb)->zccd != NULL && /* skb is part of a zcc I/O */
-+                  skb_shinfo(skb)->zccd2 != NULL &&
-+                  skb_shinfo(skb)->zccd != zccd && /* not the same one */
-+                  skb_shinfo(skb)->zccd2 != zccd)
-+              {
-+                      tcp_mark_push (tp, skb);
-+                      goto new_segment;
-+              }
-+
-               if (can_coalesce(skb, i, page, offset)) {
-                       skb_shinfo(skb)->frags[i-1].size += copy;
-               } else if (i < MAX_SKB_FRAGS) {
-@@ -884,6 +896,20 @@
-                       goto new_segment;
-               }
-+              if (zccd != NULL &&     /* this is a zcc I/O */
-+                  skb_shinfo(skb)->zccd != zccd && /* not already referencing this zccd */
-+                  skb_shinfo(skb)->zccd2 != zccd)
-+              {
-+                      zccd_get (zccd);        /* bump ref count */
-+
-+                      BUG_TRAP (skb_shinfo(skb)->zccd2 == NULL);
-+
-+                      if (skb_shinfo(skb)->zccd == NULL) /* reference this zccd */
-+                              skb_shinfo(skb)->zccd = zccd;
-+                      else
-+                              skb_shinfo(skb)->zccd2 = zccd;
-+              }
-+
-               skb->len += copy;
-               skb->data_len += copy;
-               skb->ip_summed = CHECKSUM_HW;
-@@ -947,7 +973,31 @@
-       lock_sock(sk);
-       TCP_CHECK_TIMER(sk);
--      res = do_tcp_sendpages(sk, &page, offset, size, flags);
-+      res = do_tcp_sendpages(sk, &page, offset, size, flags, NULL);
-+      TCP_CHECK_TIMER(sk);
-+      release_sock(sk);
-+      return res;
-+}
-+
-+ssize_t tcp_sendpage_zccd(struct socket *sock, struct page *page, int offset, size_t size,
-+                        int flags, zccd_t *zccd)
-+{
-+      ssize_t res;
-+      struct sock *sk = sock->sk;
-+
-+#define TCP_ZC_CSUM_FLAGS (NETIF_F_IP_CSUM|NETIF_F_NO_CSUM|NETIF_F_HW_CSUM)
-+
-+      if (!(sk->route_caps & NETIF_F_SG) ||   /* caller shouldn't waste her time */
-+          !(sk->route_caps & TCP_ZC_CSUM_FLAGS)) /* on double mapping */
-+              BUG ();
-+
-+#undef TCP_ZC_CSUM_FLAGS
-+
-+      lock_sock(sk);
-+      TCP_CHECK_TIMER(sk);
-+
-+      res = do_tcp_sendpages(sk, &page, offset, size, flags, zccd);
-+
-       TCP_CHECK_TIMER(sk);
-       release_sock(sk);
-       return res;
-@@ -1771,6 +1821,202 @@
-       goto out;
- }
-+int tcp_recvpackets (struct sock *sk, struct sk_buff_head *packets,
-+                   int len, int nonblock)
-+{
-+      struct tcp_opt *tp = &(sk->tp_pinfo.af_tcp);
-+      int copied;
-+      long timeo;
-+
-+      BUG_TRAP (len > 0);
-+      /*BUG_TRAP ((flags & (MSG_OOB | MSG_PEEK | MSG_TRUNC)) == 0);*/
-+
-+      lock_sock(sk);
-+
-+      TCP_CHECK_TIMER(sk);
-+
-+      copied = -ENOTCONN;
-+      if (sk->state == TCP_LISTEN)
-+              goto out;
-+
-+      copied = 0;
-+      timeo = sock_rcvtimeo(sk, nonblock);
-+
-+      do {
-+              struct sk_buff * skb;
-+              u32 offset;
-+              unsigned long used;
-+              int exhausted;
-+              int eaten;
-+
-+              /* Are we at urgent data? Stop if we have read anything. */
-+              if (copied && tp->urg_data && tp->urg_seq == tp->copied_seq)
-+                      break;
-+
-+              /* We need to check signals first, to get correct SIGURG
-+               * handling. FIXME: Need to check this doesnt impact 1003.1g
-+               * and move it down to the bottom of the loop
-+               */
-+              if (signal_pending(current)) {
-+                      if (copied)
-+                              break;
-+                      copied = timeo ? sock_intr_errno(timeo) : -EAGAIN;
-+                      break;
-+              }
-+
-+              /* Next get a buffer. */
-+
-+              skb = skb_peek(&sk->receive_queue);
-+
-+              if (skb == NULL)                /* nothing ready */
-+              {
-+                      if (copied) {
-+                              if (sk->err ||
-+                                  sk->state == TCP_CLOSE ||
-+                                  (sk->shutdown & RCV_SHUTDOWN) ||
-+                                  !timeo ||
-+                                  (0))
-+                                      break;
-+                      } else {
-+                              if (sk->done)
-+                                      break;
-+
-+                              if (sk->err) {
-+                                      copied = sock_error(sk);
-+                                      break;
-+                              }
-+
-+                              if (sk->shutdown & RCV_SHUTDOWN)
-+                                      break;
-+
-+                              if (sk->state == TCP_CLOSE) {
-+                                      if (!sk->done) {
-+                                              /* This occurs when user tries to read
-+                                               * from never connected socket.
-+                                               */
-+                                              copied = -ENOTCONN;
-+                                              break;
-+                                      }
-+                                      break;
-+                              }
-+
-+                              if (!timeo) {
-+                                      copied = -EAGAIN;
-+                                      break;
-+                              }
-+                      }
-+
-+                      cleanup_rbuf(sk, copied);
-+                      timeo = tcp_data_wait(sk, timeo);
-+                      continue;
-+              }
-+
-+              BUG_TRAP (atomic_read (&skb->users) == 1);
-+
-+              exhausted = eaten = 0;
-+
-+              offset = tp->copied_seq - TCP_SKB_CB(skb)->seq;
-+              if (skb->h.th->syn)
-+                      offset--;
-+
-+              used = skb->len - offset;
-+
-+              if (tp->urg_data) {
-+                      u32 urg_offset = tp->urg_seq - tp->copied_seq;
-+                      if (urg_offset < used) {
-+                              if (!urg_offset) { /* at urgent date */
-+                                      if (!sk->urginline) {
-+                                              tp->copied_seq++; /* discard the single byte of urgent data */
-+                                              offset++;
-+                                              used--;
-+                                      }
-+                              } else          /* truncate read */
-+                                      used = urg_offset;
-+                      }
-+              }
-+
-+              BUG_TRAP (used >= 0);
-+              if (len < used)
-+                      used = len;
-+
-+              if (used == 0)
-+                      exhausted = 1;
-+              else
-+              {
-+                      if (skb_is_nonlinear (skb))
-+                      {
-+                              int   rc = skb_linearize (skb, GFP_KERNEL);
-+
-+                              printk ("tcp_recvpackets(): linearising: %d\n", rc);
-+
-+                              if (rc)
-+                              {
-+                                      if (!copied)
-+                                              copied = rc;
-+                                      break;
-+                              }
-+                      }
-+
-+                      if ((offset + used) == skb->len) /* consuming the whole packet */
-+                      {
-+                              __skb_unlink (skb, &sk->receive_queue);
-+                              dst_release (skb->dst);
-+                              skb_orphan (skb);
-+                              __skb_pull (skb, offset);
-+                              __skb_queue_tail (packets, skb);
-+                              exhausted = eaten = 1;
-+                      }
-+                      else                    /* consuming only part of the packet */
-+                      {
-+                              struct sk_buff *skb2 = skb_clone (skb, GFP_KERNEL);
-+
-+                              if (skb2 == NULL)
-+                              {
-+                                      if (!copied)
-+                                              copied = -ENOMEM;
-+                                      break;
-+                              }
-+
-+                              dst_release (skb2->dst);
-+                              __skb_pull (skb2, offset);
-+                              __skb_trim (skb2, used);
-+                              __skb_queue_tail (packets, skb2);
-+                      }
-+
-+                      tp->copied_seq += used;
-+                      copied += used;
-+                      len -= used;
-+              }
-+
-+              if (tp->urg_data && after(tp->copied_seq,tp->urg_seq)) {
-+                      tp->urg_data = 0;
-+                      tcp_fast_path_check(sk, tp);
-+              }
-+
-+              if (!exhausted)
-+                      continue;
-+
-+              if (skb->h.th->fin)
-+              {
-+                      tp->copied_seq++;
-+                      if (!eaten)
-+                              tcp_eat_skb (sk, skb);
-+                      break;
-+              }
-+
-+              if (!eaten)
-+                      tcp_eat_skb (sk, skb);
-+
-+      } while (len > 0);
-+
-+ out:
-+      /* Clean up data we have read: This will do ACK frames. */
-+      cleanup_rbuf(sk, copied);
-+      TCP_CHECK_TIMER(sk);
-+      release_sock(sk);
-+      return copied;
-+}
-+
- /*
-  *    State processing on a close. This implements the state shift for
-  *    sending our FIN frame. Note that we only send a FIN for some
diff --git a/lustre/kernel_patches/patches/vfs-pdirops-2.4.20-rh.patch b/lustre/kernel_patches/patches/vfs-pdirops-2.4.20-rh.patch
deleted file mode 100644 (file)
index 6ab7a21..0000000
+++ /dev/null
@@ -1,269 +0,0 @@
- fs/inode.c         |    1 
- fs/namei.c         |   66 ++++++++++++++++++++++++++++++++++++++---------------
- include/linux/fs.h |   11 ++++----
- 3 files changed, 54 insertions(+), 24 deletions(-)
-
-Index: linux-2.4.20-rh/fs/namei.c
-===================================================================
---- linux-2.4.20-rh.orig/fs/namei.c    2003-09-04 20:58:33.000000000 +0800
-+++ linux-2.4.20-rh/fs/namei.c 2003-09-04 21:21:20.000000000 +0800
-@@ -101,6 +101,36 @@
- }
-+static void *lock_dir(struct inode *dir, struct qstr *name)
-+{
-+      unsigned long hash;
-+      
-+      if (!IS_PDIROPS(dir)) {
-+              down(&dir->i_sem);
-+              return 0;
-+      }
-+
-+      /* OK. fs understands parallel directory operations.
-+       * so, we try to acquire lock for hash of requested
-+       * filename in order to prevent any operations with
-+       * same name in same time -bzzz */
-+
-+      /* calculate name hash */
-+      hash = full_name_hash(name->name, name->len);
-+
-+      /* lock this hash */
-+      return dynlock_lock(&dir->i_dcache_lock, hash, 1, GFP_ATOMIC);
-+}
-+
-+static void unlock_dir(struct inode *dir, void *lock)
-+{
-+      if (!IS_PDIROPS(dir)) {
-+              up(&dir->i_sem);
-+              return;
-+      }
-+      dynlock_unlock(&dir->i_dcache_lock, lock);
-+}
-+
- /* In order to reduce some races, while at the same time doing additional
-  * checking and hopefully speeding things up, we copy filenames to the
-  * kernel data space before using them..
-@@ -303,10 +333,11 @@
-       struct dentry * result;
-       struct inode *dir = parent->d_inode;
-       int counter = 0;
-+      void *lock;
- again:
-       counter++;
--      down(&dir->i_sem);
-+      lock = lock_dir(dir, name);
-       /*
-        * First re-do the cached lookup just in case it was created
-        * while we waited for the directory semaphore..
-@@ -329,7 +359,7 @@
-                       else
-                               result = dentry;
-               }
--              up(&dir->i_sem);
-+              unlock_dir(dir, lock);
-               return result;
-       }
-@@ -337,7 +367,7 @@
-        * Uhhuh! Nasty case: the cache was re-populated while
-        * we waited on the semaphore. Need to revalidate.
-        */
--      up(&dir->i_sem);
-+      unlock_dir(dir, lock);
-       if (result->d_op && result->d_op->d_revalidate) {
-               if (!result->d_op->d_revalidate(result, flags) && !d_invalidate(result)) {
-                       dput(result);
-@@ -1180,13 +1210,13 @@
-               goto exit;
-       dir = nd->dentry;
--      down(&dir->d_inode->i_sem);
-+      nd->lock = lock_dir(dir->d_inode, &nd->last);
-       dentry = lookup_hash_it(&nd->last, nd->dentry, it);
- do_last:
-       error = PTR_ERR(dentry);
-       if (IS_ERR(dentry)) {
--              up(&dir->d_inode->i_sem);
-+              unlock_dir(dir->d_inode, nd->lock);
-               goto exit;
-       }
-@@ -1195,7 +1225,7 @@
-       if (!dentry->d_inode) {
-               error = vfs_create_it(dir->d_inode, dentry,
-                                  mode & ~current->fs->umask, it);
--              up(&dir->d_inode->i_sem);
-+              unlock_dir(dir->d_inode, nd->lock);             
-               dput(nd->dentry);
-               nd->dentry = dentry;
-               if (error)
-@@ -1209,7 +1239,7 @@
-       /*
-        * It already exists.
-        */
--      up(&dir->d_inode->i_sem);
-+      unlock_dir(dir->d_inode, nd->lock);
-       error = -EEXIST;
-       if (flag & O_EXCL)
-@@ -1362,7 +1392,7 @@
-               goto exit;
-       }
-       dir = nd->dentry;
--      down(&dir->d_inode->i_sem);
-+      nd->lock = lock_dir(dir->d_inode, &nd->last);
-       dentry = lookup_hash_it(&nd->last, nd->dentry, it);
-       putname(nd->last.name);
-       goto do_last;
-@@ -1380,7 +1410,7 @@
- {
-       struct dentry *dentry;
--      down(&nd->dentry->d_inode->i_sem);
-+      nd->lock = lock_dir(nd->dentry->d_inode, &nd->last);
-       dentry = ERR_PTR(-EEXIST);
-       if (nd->last_type != LAST_NORM)
-               goto fail;
-@@ -1469,7 +1499,7 @@
-               }
-               dput(dentry);
-       }
--      up(&nd.dentry->d_inode->i_sem);
-+      unlock_dir(nd.dentry->d_inode, nd.lock);
- out2:
-       path_release(&nd);
- out:
-@@ -1532,7 +1562,7 @@
-                                         mode & ~current->fs->umask);
-                       dput(dentry);
-               }
--              up(&nd.dentry->d_inode->i_sem);
-+              unlock_dir(nd.dentry->d_inode, nd.lock);
- out2:
-               path_release(&nd);
- out:
-@@ -1642,14 +1672,14 @@
-               if (error != -EOPNOTSUPP)
-                       goto exit1;
-       }
--      down(&nd.dentry->d_inode->i_sem);
-+      nd.lock = lock_dir(nd.dentry->d_inode, &nd.last);
-       dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-               error = vfs_rmdir(nd.dentry->d_inode, dentry);
-               dput(dentry);
-       }
--      up(&nd.dentry->d_inode->i_sem);
-+      unlock_dir(nd.dentry->d_inode, nd.lock);
- exit1:
-       path_release(&nd);
- exit:
-@@ -1708,7 +1738,7 @@
-               if (error != -EOPNOTSUPP)
-                       goto exit1;
-       }
--      down(&nd.dentry->d_inode->i_sem);
-+      nd.lock = lock_dir(nd.dentry->d_inode, &nd.last);
-       dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-@@ -1719,7 +1749,7 @@
-       exit2:
-               dput(dentry);
-       }
--      up(&nd.dentry->d_inode->i_sem);
-+      unlock_dir(nd.dentry->d_inode, nd.lock);
- exit1:
-       path_release(&nd);
- exit:
-@@ -1789,7 +1819,7 @@
-                       error = vfs_symlink(nd.dentry->d_inode, dentry, from);
-                       dput(dentry);
-               }
--              up(&nd.dentry->d_inode->i_sem);
-+              unlock_dir(nd.dentry->d_inode, nd.lock);
-       out2:
-               path_release(&nd);
-       out:
-@@ -1881,7 +1911,7 @@
-                       error = vfs_link(old_nd.dentry, nd.dentry->d_inode, new_dentry);
-                       dput(new_dentry);
-               }
--              up(&nd.dentry->d_inode->i_sem);
-+              unlock_dir(nd.dentry->d_inode, nd.lock);
- out_release:
-               path_release(&nd);
- out:
-Index: linux-2.4.20-rh/include/linux/fs.h
-===================================================================
---- linux-2.4.20-rh.orig/include/linux/fs.h    2003-09-04 20:59:14.000000000 +0800
-+++ linux-2.4.20-rh/include/linux/fs.h 2003-09-04 21:03:46.000000000 +0800
-@@ -21,6 +21,7 @@
- #include <linux/cache.h>
- #include <linux/stddef.h>
- #include <linux/string.h>
-+#include <linux/dynlocks.h>
- #include <asm/atomic.h>
- #include <asm/bitops.h>
-@@ -136,6 +137,7 @@
- #define S_IMMUTABLE   16      /* Immutable file */
- #define S_DEAD                32      /* removed, but still open directory */
- #define S_NOQUOTA     64      /* Inode is not counted to quota */
-+#define S_PDIROPS     256     /* Parallel directory operations */
- /*
-  * Note that nosuid etc flags are inode-specific: setting some file-system
-@@ -162,6 +164,7 @@
- #define IS_IMMUTABLE(inode)   ((inode)->i_flags & S_IMMUTABLE)
- #define IS_NOATIME(inode)     (__IS_FLG(inode, MS_NOATIME) || ((inode)->i_flags & S_NOATIME))
- #define IS_NODIRATIME(inode)  __IS_FLG(inode, MS_NODIRATIME)
-+#define IS_PDIROPS(inode)     __IS_FLG(inode, S_PDIROPS)
- #define IS_DEADDIR(inode)     ((inode)->i_flags & S_DEAD)
-@@ -489,6 +492,7 @@
-       atomic_t                i_writecount;
-       unsigned int            i_attr_flags;
-       __u32                   i_generation;
-+      struct dynlock          i_dcache_lock;  /* for parallel directory ops */
-       union {
-               struct minix_inode_info         minix_i;
-               struct ext2_inode_info          ext2_i;
-@@ -708,6 +712,7 @@
-       unsigned int flags;
-       int last_type;
-       struct lookup_intent *intent;
-+      void *lock;
- };
- /*
-@@ -1621,12 +1626,6 @@
-       return dget(dentry->d_parent);
- }
--static inline void unlock_dir(struct dentry *dir)
--{
--      up(&dir->d_inode->i_sem);
--      dput(dir);
--}
--
- /*
-  * Whee.. Deadlock country. Happily there are only two VFS
-  * operations that does this..
-Index: linux-2.4.20-rh/fs/inode.c
-===================================================================
---- linux-2.4.20-rh.orig/fs/inode.c    2003-09-04 20:58:35.000000000 +0800
-+++ linux-2.4.20-rh/fs/inode.c 2003-09-04 21:03:46.000000000 +0800
-@@ -121,6 +121,7 @@
-               mapping->host = inode;
-               mapping->gfp_mask = GFP_HIGHUSER;
-               inode->i_mapping = mapping;
-+              dynlock_init(&inode->i_dcache_lock);
-       }
-       return inode;
- }
diff --git a/lustre/kernel_patches/patches/vfs_intent-2.4.20-rh.patch b/lustre/kernel_patches/patches/vfs_intent-2.4.20-rh.patch
deleted file mode 100644 (file)
index 3133c62..0000000
+++ /dev/null
@@ -1,1880 +0,0 @@
- fs/dcache.c               |   19 ++
- fs/exec.c                 |   17 +-
- fs/namei.c                |  333 ++++++++++++++++++++++++++++++++++++++--------
- fs/namespace.c            |   28 ++-
- fs/open.c                 |  176 +++++++++++++++++-------
- fs/proc/base.c            |    3 
- fs/stat.c                 |   28 ++-
- include/linux/dcache.h    |   60 ++++++++
- include/linux/fs.h        |   32 ++++
- include/linux/fs_struct.h |    4 
- kernel/exit.c             |    3 
- kernel/fork.c             |    3 
- kernel/ksyms.c            |    1 
- 13 files changed, 578 insertions(+), 129 deletions(-)
-
-Index: linux-2.4.20/fs/dcache.c
-===================================================================
---- linux-2.4.20.orig/fs/dcache.c      Wed Mar 17 13:57:05 2004
-+++ linux-2.4.20/fs/dcache.c   Wed Mar 17 13:57:11 2004
-@@ -186,6 +186,13 @@
-               spin_unlock(&dcache_lock);
-               return 0;
-       }
-+
-+      /* network invalidation by Lustre */
-+      if (dentry->d_flags & DCACHE_LUSTRE_INVALID) {
-+              spin_unlock(&dcache_lock);
-+              return 0;
-+      }
-+
-       /*
-        * Check whether to do a partial shrink_dcache
-        * to get rid of unused child entries.
-@@ -841,13 +848,19 @@
-  * Adds a dentry to the hash according to its name.
-  */
-  
--void d_rehash(struct dentry * entry)
-+void __d_rehash(struct dentry * entry, int lock)
- {
-       struct list_head *list = d_hash(entry->d_parent, entry->d_name.hash);
-       if (!list_empty(&entry->d_hash)) BUG();
--      spin_lock(&dcache_lock);
-+      if (lock) spin_lock(&dcache_lock);
-       list_add(&entry->d_hash, list);
--      spin_unlock(&dcache_lock);
-+      if (lock) spin_unlock(&dcache_lock);
-+}
-+EXPORT_SYMBOL(__d_rehash);
-+
-+void d_rehash(struct dentry * entry)
-+{
-+      __d_rehash(entry, 1);
- }
- #define do_switch(x,y) do { \
-Index: linux-2.4.20/fs/exec.c
-===================================================================
---- linux-2.4.20.orig/fs/exec.c        Wed Mar 17 13:57:05 2004
-+++ linux-2.4.20/fs/exec.c     Wed Mar 17 13:57:11 2004
-@@ -114,8 +114,10 @@
-       struct file * file;
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_OPEN,
-+                                  .it_flags = FMODE_READ|FMODE_EXEC };
--      error = user_path_walk(library, &nd);
-+      error = user_path_walk_it(library, &nd, &it);
-       if (error)
-               goto out;
-@@ -127,7 +129,8 @@
-       if (error)
-               goto exit;
--      file = dentry_open(nd.dentry, nd.mnt, O_RDONLY);
-+      file = dentry_open_it(nd.dentry, nd.mnt, O_RDONLY, &it);
-+      intent_release(&it);
-       error = PTR_ERR(file);
-       if (IS_ERR(file))
-               goto out;
-@@ -382,8 +385,10 @@
-       struct inode *inode;
-       struct file *file;
-       int err = 0;
-+      struct lookup_intent it = { .it_op = IT_OPEN,
-+                                  .it_flags = FMODE_READ|FMODE_EXEC };
--      err = path_lookup(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd);
-+      err = path_lookup_it(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd, &it);
-       file = ERR_PTR(err);
-       if (!err) {
-               inode = nd.dentry->d_inode;
-@@ -395,7 +400,8 @@
-                               err = -EACCES;
-                       file = ERR_PTR(err);
-                       if (!err) {
--                              file = dentry_open(nd.dentry, nd.mnt, O_RDONLY);
-+                              file = dentry_open_it(nd.dentry, nd.mnt, O_RDONLY, &it);
-+                              intent_release(&it);
-                               if (!IS_ERR(file)) {
-                                       err = deny_write_access(file);
-                                       if (err) {
-@@ -407,6 +413,7 @@
-                               return file;
-                       }
-               }
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       goto out;
-@@ -1296,7 +1303,7 @@
-               goto close_fail;
-       if (!file->f_op->write)
-               goto close_fail;
--      if (do_truncate(file->f_dentry, 0) != 0)
-+      if (do_truncate(file->f_dentry, 0, 0) != 0)
-               goto close_fail;
-       retval = binfmt->core_dump(signr, regs, file);
-Index: linux-2.4.20/fs/namei.c
-===================================================================
---- linux-2.4.20.orig/fs/namei.c       Wed Mar 17 13:57:03 2004
-+++ linux-2.4.20/fs/namei.c    Wed Mar 17 13:58:01 2004
-@@ -94,6 +94,13 @@
-  * XEmacs seems to be relying on it...
-  */
-+void intent_release(struct lookup_intent *it)
-+{
-+      if (it && it->it_op_release)
-+              it->it_op_release(it);
-+
-+}
-+
- /* In order to reduce some races, while at the same time doing additional
-  * checking and hopefully speeding things up, we copy filenames to the
-  * kernel data space before using them..
-@@ -260,10 +267,19 @@
-  * Internal lookup() using the new generic dcache.
-  * SMP-safe
-  */
--static struct dentry * cached_lookup(struct dentry * parent, struct qstr * name, int flags)
-+static struct dentry *cached_lookup(struct dentry *parent, struct qstr *name,
-+                                  int flags, struct lookup_intent *it)
- {
-       struct dentry * dentry = d_lookup(parent, name);
-+      if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if (!dentry->d_op->d_revalidate_it(dentry, flags, it) &&
-+                  !d_invalidate(dentry)) {
-+                      dput(dentry);
-+                      dentry = NULL;
-+              }
-+              return dentry;
-+      } else
-       if (dentry && dentry->d_op && dentry->d_op->d_revalidate) {
-               if (!dentry->d_op->d_revalidate(dentry, flags) && !d_invalidate(dentry)) {
-                       dput(dentry);
-@@ -281,11 +297,15 @@
-  * make sure that nobody added the entry to the dcache in the meantime..
-  * SMP-safe
-  */
--static struct dentry * real_lookup(struct dentry * parent, struct qstr * name, int flags)
-+static struct dentry *real_lookup(struct dentry *parent, struct qstr *name,
-+                                int flags, struct lookup_intent *it)
- {
-       struct dentry * result;
-       struct inode *dir = parent->d_inode;
-+      int counter = 0;
-+again:
-+      counter++;
-       down(&dir->i_sem);
-       /*
-        * First re-do the cached lookup just in case it was created
-@@ -300,6 +320,9 @@
-               result = ERR_PTR(-ENOMEM);
-               if (dentry) {
-                       lock_kernel();
-+                      if (dir->i_op->lookup_it)
-+                              result = dir->i_op->lookup_it(dir, dentry, it, flags);
-+                      else
-                       result = dir->i_op->lookup(dir, dentry);
-                       unlock_kernel();
-                       if (result)
-@@ -321,6 +344,15 @@
-                       dput(result);
-                       result = ERR_PTR(-ENOENT);
-               }
-+      } else if (result->d_op && result->d_op->d_revalidate_it) {
-+              if (!result->d_op->d_revalidate_it(result, flags, it) &&
-+                  !d_invalidate(result)) {
-+                      dput(result);
-+                      if (counter > 10)
-+                              result = ERR_PTR(-ESTALE);
-+                      if (!IS_ERR(result))
-+                              goto again;
-+              }
-       }
-       return result;
- }
-@@ -334,7 +366,8 @@
-  * Without that kind of total limit, nasty chains of consecutive
-  * symlinks can cause almost arbitrarily long lookups. 
-  */
--static inline int do_follow_link(struct dentry *dentry, struct nameidata *nd)
-+static inline int do_follow_link(struct dentry *dentry, struct nameidata *nd,
-+                               struct lookup_intent *it)
- {
-       int err;
-       if (current->link_count >= max_recursive_link)
-@@ -348,10 +381,18 @@
-       current->link_count++;
-       current->total_link_count++;
-       UPDATE_ATIME(dentry->d_inode);
-+      nd->intent = it;
-       err = dentry->d_inode->i_op->follow_link(dentry, nd);
-+      if (!err && it != NULL && !(it->d.lustre.it_int_flags & IT_FL_FOLLOWED)) {
-+              /* vfs_follow_link was never called */
-+              intent_release(it);
-+              path_release(nd);
-+              err = -ENOLINK;
-+      }
-       current->link_count--;
-       return err;
- loop:
-+      intent_release(it);
-       path_release(nd);
-       return -ELOOP;
- }
-@@ -381,15 +422,26 @@
-       return __follow_up(mnt, dentry);
- }
--static inline int __follow_down(struct vfsmount **mnt, struct dentry **dentry)
-+static inline int __follow_down(struct vfsmount **mnt, struct dentry **dentry,
-+                              struct lookup_intent *it)
- {
-       struct vfsmount *mounted;
-       spin_lock(&dcache_lock);
-       mounted = lookup_mnt(*mnt, *dentry);
-       if (mounted) {
-+              int opc = 0, mode = 0;
-               *mnt = mntget(mounted);
-               spin_unlock(&dcache_lock);
-+              if (it) {
-+                      opc = it->it_op;
-+                      mode = it->it_create_mode;
-+              }
-+              intent_release(it);
-+              if (it) {
-+                      it->it_op = opc;
-+                      it->it_create_mode = mode;
-+              }
-               dput(*dentry);
-               mntput(mounted->mnt_parent);
-               *dentry = dget(mounted->mnt_root);
-@@ -401,7 +453,7 @@
- int follow_down(struct vfsmount **mnt, struct dentry **dentry)
- {
--      return __follow_down(mnt,dentry);
-+      return __follow_down(mnt, dentry, NULL);
- }
-  
- static inline void follow_dotdot(struct nameidata *nd)
-@@ -437,7 +489,7 @@
-               mntput(nd->mnt);
-               nd->mnt = parent;
-       }
--      while (d_mountpoint(nd->dentry) && __follow_down(&nd->mnt, &nd->dentry))
-+      while (d_mountpoint(nd->dentry) && __follow_down(&nd->mnt, &nd->dentry, NULL))
-               ;
- }
-@@ -449,7 +501,8 @@
-  *
-  * We expect 'base' to be positive and a directory.
-  */
--int link_path_walk(const char * name, struct nameidata *nd)
-+int link_path_walk_it(const char *name, struct nameidata *nd,
-+                    struct lookup_intent *it)
- {
-       struct dentry *dentry;
-       struct inode *inode;
-@@ -526,18 +579,18 @@
-                               break;
-               }
-               /* This does the actual lookups.. */
--              dentry = cached_lookup(nd->dentry, &this, LOOKUP_CONTINUE);
-+              dentry = cached_lookup(nd->dentry, &this, LOOKUP_CONTINUE, NULL);
-               if (!dentry) {
-                       err = -EWOULDBLOCKIO;
-                       if (atomic)
-                               break;
--                      dentry = real_lookup(nd->dentry, &this, LOOKUP_CONTINUE);
-+                      dentry = real_lookup(nd->dentry, &this, LOOKUP_CONTINUE, NULL);
-                       err = PTR_ERR(dentry);
-                       if (IS_ERR(dentry))
-                               break;
-               }
-               /* Check mountpoints.. */
--              while (d_mountpoint(dentry) && __follow_down(&nd->mnt, &dentry))
-+              while (d_mountpoint(dentry) && __follow_down(&nd->mnt, &dentry, NULL))
-                       ;
-               err = -ENOENT;
-@@ -549,7 +601,7 @@
-                       goto out_dput;
-               if (inode->i_op->follow_link) {
--                      err = do_follow_link(dentry, nd);
-+                      err = do_follow_link(dentry, nd, NULL);
-                       dput(dentry);
-                       if (err)
-                               goto return_err;
-@@ -565,7 +617,7 @@
-                       nd->dentry = dentry;
-               }
-               err = -ENOTDIR; 
--              if (!inode->i_op->lookup)
-+              if (!inode->i_op->lookup && !inode->i_op->lookup_it)
-                       break;
-               continue;
-               /* here ends the main loop */
-@@ -592,22 +644,22 @@
-                       if (err < 0)
-                               break;
-               }
--              dentry = cached_lookup(nd->dentry, &this, 0);
-+              dentry = cached_lookup(nd->dentry, &this, 0, it);
-               if (!dentry) {
-                       err = -EWOULDBLOCKIO;
-                       if (atomic)
-                               break;
--                      dentry = real_lookup(nd->dentry, &this, 0);
-+                      dentry = real_lookup(nd->dentry, &this, 0, it);
-                       err = PTR_ERR(dentry);
-                       if (IS_ERR(dentry))
-                               break;
-               }
--              while (d_mountpoint(dentry) && __follow_down(&nd->mnt, &dentry))
-+              while (d_mountpoint(dentry) && __follow_down(&nd->mnt, &dentry, it))
-                       ;
-               inode = dentry->d_inode;
-               if ((lookup_flags & LOOKUP_FOLLOW)
-                   && inode && inode->i_op && inode->i_op->follow_link) {
--                      err = do_follow_link(dentry, nd);
-+                      err = do_follow_link(dentry, nd, it);
-                       dput(dentry);
-                       if (err)
-                               goto return_err;
-@@ -621,7 +673,8 @@
-                       goto no_inode;
-               if (lookup_flags & LOOKUP_DIRECTORY) {
-                       err = -ENOTDIR; 
--                      if (!inode->i_op || !inode->i_op->lookup)
-+                      if (!inode->i_op ||
-+                          (!inode->i_op->lookup && !inode->i_op->lookup_it))
-                               break;
-               }
-               goto return_base;
-@@ -645,6 +698,34 @@
-                * Check the cached dentry for staleness.
-                */
-               dentry = nd->dentry;
-+              if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+                      err = -ESTALE;
-+                      if (!dentry->d_op->d_revalidate_it(dentry, 0, it)) {
-+                              struct dentry *new;
-+                              err = permission(dentry->d_parent->d_inode,
-+                                               MAY_EXEC);
-+                              if (err)
-+                                      break;
-+                              new = real_lookup(dentry->d_parent,
-+                                                &dentry->d_name, 0, it);
-+                              if (IS_ERR(new)) {
-+                                      err = PTR_ERR(new);
-+                                      break;
-+                              }
-+                              d_invalidate(dentry);
-+                              dput(dentry);
-+                              nd->dentry = new;
-+                      }
-+                      if (!nd->dentry->d_inode)
-+                              goto no_inode;
-+                      if (lookup_flags & LOOKUP_DIRECTORY) {
-+                              err = -ENOTDIR; 
-+                              if (!nd->dentry->d_inode->i_op ||
-+                                  (!nd->dentry->d_inode->i_op->lookup &&
-+                                   !nd->dentry->d_inode->i_op->lookup_it))
-+                                      break;
-+                      }
-+              } else
-               if (dentry && dentry->d_op && dentry->d_op->d_revalidate) {
-                       err = -ESTALE;
-                       if (!dentry->d_op->d_revalidate(dentry, 0)) {
-@@ -658,15 +732,28 @@
-               dput(dentry);
-               break;
-       }
-+      if (err)
-+              intent_release(it);
-       path_release(nd);
- return_err:
-       return err;
- }
-+int link_path_walk(const char * name, struct nameidata *nd)
-+{
-+      return link_path_walk_it(name, nd, NULL);
-+}
-+
-+int path_walk_it(const char * name, struct nameidata *nd, struct lookup_intent *it)
-+{
-+      current->total_link_count = 0;
-+      return link_path_walk_it(name, nd, it);
-+}
-+
- int path_walk(const char * name, struct nameidata *nd)
- {
-       current->total_link_count = 0;
--      return link_path_walk(name, nd);
-+      return link_path_walk_it(name, nd, NULL);
- }
- /* SMP-safe */
-@@ -751,6 +838,17 @@
- }
- /* SMP-safe */
-+int path_lookup_it(const char *path, unsigned flags, struct nameidata *nd,
-+                 struct lookup_intent *it)
-+{
-+      int error = 0;
-+      if (path_init(path, flags, nd))
-+              error = path_walk_it(path, nd, it);
-+      return error;
-+}
-+
-+
-+/* SMP-safe */
- int path_lookup(const char *path, unsigned flags, struct nameidata *nd)
- {
-       int error = 0;
-@@ -765,6 +863,7 @@
- {
-       nd->last_type = LAST_ROOT; /* if there are only slashes... */
-       nd->flags = flags;
-+      nd->intent = NULL;
-       if (*name=='/')
-               return walk_init_root(name,nd);
-       read_lock(&current->fs->lock);
-@@ -779,7 +878,8 @@
-  * needs parent already locked. Doesn't follow mounts.
-  * SMP-safe.
-  */
--struct dentry * lookup_hash(struct qstr *name, struct dentry * base)
-+struct dentry * lookup_hash_it(struct qstr *name, struct dentry * base,
-+                             struct lookup_intent *it)
- {
-       struct dentry * dentry;
-       struct inode *inode;
-@@ -802,13 +902,16 @@
-                       goto out;
-       }
--      dentry = cached_lookup(base, name, 0);
-+      dentry = cached_lookup(base, name, 0, it);
-       if (!dentry) {
-               struct dentry *new = d_alloc(base, name);
-               dentry = ERR_PTR(-ENOMEM);
-               if (!new)
-                       goto out;
-               lock_kernel();
-+              if (inode->i_op->lookup_it)
-+                      dentry = inode->i_op->lookup_it(inode, new, it, 0);
-+              else
-               dentry = inode->i_op->lookup(inode, new);
-               unlock_kernel();
-               if (!dentry)
-@@ -820,6 +923,12 @@
-       return dentry;
- }
-+struct dentry * lookup_hash(struct qstr *name, struct dentry * base)
-+{
-+      return lookup_hash_it(name, base, NULL);
-+}
-+
-+
- /* SMP-safe */
- struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
- {
-@@ -841,7 +950,7 @@
-       }
-       this.hash = end_name_hash(hash);
--      return lookup_hash(&this, base);
-+      return lookup_hash_it(&this, base, NULL);
- access:
-       return ERR_PTR(-EACCES);
- }
-@@ -872,6 +981,23 @@
-       return err;
- }
-+int __user_walk_it(const char *name, unsigned flags, struct nameidata *nd,
-+                 struct lookup_intent *it)
-+{
-+      char *tmp;
-+      int err;
-+
-+      tmp = getname(name);
-+      err = PTR_ERR(tmp);
-+      if (!IS_ERR(tmp)) {
-+              err = 0;
-+              if (path_init(tmp, flags, nd))
-+                      err = path_walk_it(tmp, nd, it);
-+              putname(tmp);
-+      }
-+      return err;
-+}
-+
- /*
-  * It's inline, so penalty for filesystems that don't use sticky bit is
-  * minimal.
-@@ -969,7 +1095,8 @@
-       return retval;
- }
--int vfs_create(struct inode *dir, struct dentry *dentry, int mode)
-+static int vfs_create_it(struct inode *dir, struct dentry *dentry, int mode,
-+                       struct lookup_intent *it)
- {
-       int error;
-@@ -982,12 +1109,15 @@
-               goto exit_lock;
-       error = -EACCES;        /* shouldn't it be ENOSYS? */
--      if (!dir->i_op || !dir->i_op->create)
-+      if (!dir->i_op || (!dir->i_op->create && !dir->i_op->create_it))
-               goto exit_lock;
-       DQUOT_INIT(dir);
-       lock_kernel();
--      error = dir->i_op->create(dir, dentry, mode);
-+      if (dir->i_op->create_it)
-+              error = dir->i_op->create_it(dir, dentry, mode, it);
-+      else
-+              error = dir->i_op->create(dir, dentry, mode);
-       unlock_kernel();
- exit_lock:
-       up(&dir->i_zombie);
-@@ -996,6 +1126,11 @@
-       return error;
- }
-+int vfs_create(struct inode *dir, struct dentry *dentry, int mode)
-+{
-+      return vfs_create_it(dir, dentry, mode, NULL);
-+}
-+
- /*
-  *    open_namei()
-  *
-@@ -1010,7 +1145,8 @@
-  * for symlinks (where the permissions are checked later).
-  * SMP-safe
-  */
--int open_namei(const char * pathname, int flag, int mode, struct nameidata *nd)
-+int open_namei_it(const char *pathname, int flag, int mode,
-+                struct nameidata *nd, struct lookup_intent *it)
- {
-       int acc_mode, error = 0;
-       struct inode *inode;
-@@ -1020,11 +1156,14 @@
-       acc_mode = ACC_MODE(flag);
-+      if (it)
-+              it->it_flags = flag;
-+
-       /*
-        * The simplest case - just a plain lookup.
-        */
-       if (!(flag & O_CREAT)) {
--              error = path_lookup(pathname, lookup_flags(flag), nd);
-+              error = path_lookup_it(pathname, lookup_flags(flag), nd, it);
-               if (error)
-                       return error;
-               dentry = nd->dentry;
-@@ -1034,6 +1173,10 @@
-       /*
-        * Create - we need to know the parent.
-        */
-+      if (it) {
-+              it->it_create_mode = mode;
-+              it->it_op |= IT_CREAT;
-+      }
-       error = path_lookup(pathname, LOOKUP_PARENT, nd);
-       if (error)
-               return error;
-@@ -1049,7 +1192,7 @@
-       dir = nd->dentry;
-       down(&dir->d_inode->i_sem);
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
- do_last:
-       error = PTR_ERR(dentry);
-@@ -1058,10 +1201,11 @@
-               goto exit;
-       }
-+      it->it_create_mode = mode;
-       /* Negative dentry, just create the file */
-       if (!dentry->d_inode) {
--              error = vfs_create(dir->d_inode, dentry,
--                                 mode & ~current->fs->umask);
-+              error = vfs_create_it(dir->d_inode, dentry,
-+                                 mode & ~current->fs->umask, it);
-               up(&dir->d_inode->i_sem);
-               dput(nd->dentry);
-               nd->dentry = dentry;
-@@ -1086,7 +1230,7 @@
-               error = -ELOOP;
-               if (flag & O_NOFOLLOW)
-                       goto exit_dput;
--              while (__follow_down(&nd->mnt,&dentry) && d_mountpoint(dentry));
-+              while (__follow_down(&nd->mnt,&dentry,it) && d_mountpoint(dentry));
-       }
-       error = -ENOENT;
-       if (!dentry->d_inode)
-@@ -1165,7 +1309,7 @@
-               if (!error) {
-                       DQUOT_INIT(inode);
-                       
--                      error = do_truncate(dentry, 0);
-+                      error = do_truncate(dentry, 0, 1);
-               }
-               put_write_access(inode);
-               if (error)
-@@ -1177,8 +1321,10 @@
-       return 0;
- exit_dput:
-+      intent_release(it);
-       dput(dentry);
- exit:
-+      intent_release(it);
-       path_release(nd);
-       return error;
-@@ -1197,7 +1343,16 @@
-        * are done. Procfs-like symlinks just set LAST_BIND.
-        */
-       UPDATE_ATIME(dentry->d_inode);
-+      nd->intent = it;
-       error = dentry->d_inode->i_op->follow_link(dentry, nd);
-+      if (error) {
-+              intent_release(it);
-+      } else if (it != NULL && !(it->d.lustre.it_int_flags & IT_FL_FOLLOWED)) {
-+              /* vfs_follow_link was never called */
-+              intent_release(it);
-+              path_release(nd);
-+              error = -ENOLINK;
-+      }
-       dput(dentry);
-       if (error)
-               return error;
-@@ -1219,13 +1374,20 @@
-       }
-       dir = nd->dentry;
-       down(&dir->d_inode->i_sem);
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
-       putname(nd->last.name);
-       goto do_last;
- }
-+int open_namei(const char *pathname, int flag, int mode, struct nameidata *nd)
-+{
-+      return open_namei_it(pathname, flag, mode, nd, NULL);
-+}
-+
-+
- /* SMP-safe */
--static struct dentry *lookup_create(struct nameidata *nd, int is_dir)
-+static struct dentry *lookup_create(struct nameidata *nd, int is_dir,
-+                                  struct lookup_intent *it)
- {
-       struct dentry *dentry;
-@@ -1233,7 +1395,7 @@
-       dentry = ERR_PTR(-EEXIST);
-       if (nd->last_type != LAST_NORM)
-               goto fail;
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
-       if (IS_ERR(dentry))
-               goto fail;
-       if (!is_dir && nd->last.name[nd->last.len] && !dentry->d_inode)
-@@ -1289,7 +1451,20 @@
-       error = path_lookup(tmp, LOOKUP_PARENT, &nd);
-       if (error)
-               goto out;
--      dentry = lookup_create(&nd, 0);
-+
-+      if (nd.last_type != LAST_NORM) {
-+              error = -EEXIST;
-+              goto out2;
-+      }
-+      if (nd.dentry->d_inode->i_op->mknod_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+              error = op->mknod_raw(&nd, mode, dev);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto out2;
-+      }
-+
-+      dentry = lookup_create(&nd, 0, NULL);
-       error = PTR_ERR(dentry);
-       mode &= ~current->fs->umask;
-@@ -1310,6 +1485,7 @@
-               dput(dentry);
-       }
-       up(&nd.dentry->d_inode->i_sem);
-+out2:
-       path_release(&nd);
- out:
-       putname(tmp);
-@@ -1357,7 +1533,18 @@
-               error = path_lookup(tmp, LOOKUP_PARENT, &nd);
-               if (error)
-                       goto out;
--              dentry = lookup_create(&nd, 1);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out2;
-+              }
-+              if (nd.dentry->d_inode->i_op->mkdir_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->mkdir_raw(&nd, mode);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out2;
-+              }
-+              dentry = lookup_create(&nd, 1, NULL);
-               error = PTR_ERR(dentry);
-               if (!IS_ERR(dentry)) {
-                       error = vfs_mkdir(nd.dentry->d_inode, dentry,
-@@ -1365,6 +1552,7 @@
-                       dput(dentry);
-               }
-               up(&nd.dentry->d_inode->i_sem);
-+out2:
-               path_release(&nd);
- out:
-               putname(tmp);
-@@ -1465,8 +1653,16 @@
-                       error = -EBUSY;
-                       goto exit1;
-       }
-+      if (nd.dentry->d_inode->i_op->rmdir_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              error = op->rmdir_raw(&nd);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit1;
-+      }
-       down(&nd.dentry->d_inode->i_sem);
--      dentry = lookup_hash(&nd.last, nd.dentry);
-+      dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-               error = vfs_rmdir(nd.dentry->d_inode, dentry);
-@@ -1524,8 +1720,15 @@
-       error = -EISDIR;
-       if (nd.last_type != LAST_NORM)
-               goto exit1;
-+      if (nd.dentry->d_inode->i_op->unlink_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+              error = op->unlink_raw(&nd);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit1;
-+      }
-       down(&nd.dentry->d_inode->i_sem);
--      dentry = lookup_hash(&nd.last, nd.dentry);
-+      dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-               /* Why not before? Because we want correct error value */
-@@ -1592,15 +1795,27 @@
-               error = path_lookup(to, LOOKUP_PARENT, &nd);
-               if (error)
-                       goto out;
--              dentry = lookup_create(&nd, 0);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out2;
-+              }
-+              if (nd.dentry->d_inode->i_op->symlink_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->symlink_raw(&nd, from);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out2;
-+              }
-+              dentry = lookup_create(&nd, 0, NULL);
-               error = PTR_ERR(dentry);
-               if (!IS_ERR(dentry)) {
-                       error = vfs_symlink(nd.dentry->d_inode, dentry, from);
-                       dput(dentry);
-               }
-               up(&nd.dentry->d_inode->i_sem);
-+      out2:
-               path_release(&nd);
--out:
-+      out:
-               putname(to);
-       }
-       putname(from);
-@@ -1676,7 +1891,18 @@
-               error = -EXDEV;
-               if (old_nd.mnt != nd.mnt)
-                       goto out_release;
--              new_dentry = lookup_create(&nd, 0);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out_release;
-+              }
-+              if (nd.dentry->d_inode->i_op->link_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->link_raw(&old_nd, &nd);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out_release;
-+              }
-+              new_dentry = lookup_create(&nd, 0, NULL);
-               error = PTR_ERR(new_dentry);
-               if (!IS_ERR(new_dentry)) {
-                       error = vfs_link(old_nd.dentry, nd.dentry->d_inode, new_dentry);
-@@ -1720,7 +1946,7 @@
-  *       locking].
-  */
- int vfs_rename_dir(struct inode *old_dir, struct dentry *old_dentry,
--             struct inode *new_dir, struct dentry *new_dentry)
-+                 struct inode *new_dir, struct dentry *new_dentry)
- {
-       int error;
-       struct inode *target;
-@@ -1799,7 +2025,7 @@
- }
- int vfs_rename_other(struct inode *old_dir, struct dentry *old_dentry,
--             struct inode *new_dir, struct dentry *new_dentry)
-+                   struct inode *new_dir, struct dentry *new_dentry)
- {
-       int error;
-@@ -1887,9 +2113,18 @@
-       if (newnd.last_type != LAST_NORM)
-               goto exit2;
-+      if (old_dir->d_inode->i_op->rename_raw) {
-+              lock_kernel();
-+              error = old_dir->d_inode->i_op->rename_raw(&oldnd, &newnd);
-+              unlock_kernel();
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit2;
-+      }
-+
-       double_lock(new_dir, old_dir);
--      old_dentry = lookup_hash(&oldnd.last, old_dir);
-+      old_dentry = lookup_hash_it(&oldnd.last, old_dir, NULL);
-       error = PTR_ERR(old_dentry);
-       if (IS_ERR(old_dentry))
-               goto exit3;
-@@ -1905,16 +2140,16 @@
-               if (newnd.last.name[newnd.last.len])
-                       goto exit4;
-       }
--      new_dentry = lookup_hash(&newnd.last, new_dir);
-+      new_dentry = lookup_hash_it(&newnd.last, new_dir, NULL);
-       error = PTR_ERR(new_dentry);
-       if (IS_ERR(new_dentry))
-               goto exit4;
-+
-       lock_kernel();
-       error = vfs_rename(old_dir->d_inode, old_dentry,
-                                  new_dir->d_inode, new_dentry);
-       unlock_kernel();
--
-       dput(new_dentry);
- exit4:
-       dput(old_dentry);
-@@ -1965,20 +2200,28 @@
- }
- static inline int
--__vfs_follow_link(struct nameidata *nd, const char *link)
-+__vfs_follow_link(struct nameidata *nd, const char *link,
-+                struct lookup_intent *it)
- {
-       int res = 0;
-       char *name;
-       if (IS_ERR(link))
-               goto fail;
-+      if (it == NULL)
-+              it = nd->intent;
-+      else if (it != nd->intent)
-+              printk("it != nd->intent: tell phil@clusterfs.com\n");
-+      if (it != NULL)
-+              it->d.lustre.it_int_flags |= IT_FL_FOLLOWED;
-+
-       if (*link == '/') {
-               path_release(nd);
-               if (!walk_init_root(link, nd))
-                       /* weird __emul_prefix() stuff did it */
-                       goto out;
-       }
--      res = link_path_walk(link, nd);
-+      res = link_path_walk_it(link, nd, it);
- out:
-       if (current->link_count || res || nd->last_type!=LAST_NORM)
-               return res;
-@@ -2002,7 +2245,13 @@
- int vfs_follow_link(struct nameidata *nd, const char *link)
- {
--      return __vfs_follow_link(nd, link);
-+      return __vfs_follow_link(nd, link, NULL);
-+}
-+
-+int vfs_follow_link_it(struct nameidata *nd, const char *link,
-+                     struct lookup_intent *it)
-+{
-+      return __vfs_follow_link(nd, link, it);
- }
- /* get the link contents into pagecache */
-@@ -2044,7 +2293,7 @@
- {
-       struct page *page = NULL;
-       char *s = page_getlink(dentry, &page);
--      int res = __vfs_follow_link(nd, s);
-+      int res = __vfs_follow_link(nd, s, NULL);
-       if (page) {
-               kunmap(page);
-               page_cache_release(page);
-Index: linux-2.4.20/fs/namespace.c
-===================================================================
---- linux-2.4.20.orig/fs/namespace.c   Wed Mar 17 13:57:05 2004
-+++ linux-2.4.20/fs/namespace.c        Wed Mar 17 13:57:11 2004
-@@ -99,6 +99,7 @@
- {
-       old_nd->dentry = mnt->mnt_mountpoint;
-       old_nd->mnt = mnt->mnt_parent;
-+      UNPIN(old_nd->dentry, old_nd->mnt, 1);
-       mnt->mnt_parent = mnt;
-       mnt->mnt_mountpoint = mnt->mnt_root;
-       list_del_init(&mnt->mnt_child);
-@@ -110,6 +111,7 @@
- {
-       mnt->mnt_parent = mntget(nd->mnt);
-       mnt->mnt_mountpoint = dget(nd->dentry);
-+      PIN(nd->dentry, nd->mnt, 1);
-       list_add(&mnt->mnt_hash, mount_hashtable+hash(nd->mnt, nd->dentry));
-       list_add(&mnt->mnt_child, &nd->mnt->mnt_mounts);
-       nd->dentry->d_mounted++;
-@@ -485,14 +487,17 @@
- {
-       struct nameidata old_nd;
-       struct vfsmount *mnt = NULL;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int err = mount_is_safe(nd);
-       if (err)
-               return err;
-       if (!old_name || !*old_name)
-               return -EINVAL;
--      err = path_lookup(old_name, LOOKUP_POSITIVE|LOOKUP_FOLLOW, &old_nd);
--      if (err)
-+      err = path_lookup_it(old_name, LOOKUP_POSITIVE|LOOKUP_FOLLOW, &old_nd, &it);
-+      if (err) {
-+              intent_release(&it);
-               return err;
-+      }
-       down_write(&current->namespace->sem);
-       err = -EINVAL;
-@@ -515,6 +520,7 @@
-       }
-       up_write(&current->namespace->sem);
-+      intent_release(&it);
-       path_release(&old_nd);
-       return err;
- }
-@@ -698,6 +704,7 @@
-                 unsigned long flags, void *data_page)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int retval = 0;
-       int mnt_flags = 0;
-@@ -722,10 +729,11 @@
-       flags &= ~(MS_NOSUID|MS_NOEXEC|MS_NODEV);
-       /* ... and get the mountpoint */
--      retval = path_lookup(dir_name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd);
--      if (retval)
-+      retval = path_lookup_it(dir_name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd, &it);
-+      if (retval) {
-+              intent_release(&it);
-               return retval;
--
-+      }
-       if (flags & MS_REMOUNT)
-               retval = do_remount(&nd, flags & ~MS_REMOUNT, mnt_flags,
-                                   data_page);
-@@ -736,6 +744,8 @@
-       else
-               retval = do_add_mount(&nd, type_page, flags, mnt_flags,
-                                     dev_name, data_page);
-+
-+      intent_release(&it);
-       path_release(&nd);
-       return retval;
- }
-@@ -901,6 +911,8 @@
- {
-       struct vfsmount *tmp;
-       struct nameidata new_nd, old_nd, parent_nd, root_parent, user_nd;
-+      struct lookup_intent new_it = { .it_op = IT_GETATTR };
-+      struct lookup_intent old_it = { .it_op = IT_GETATTR };
-       int error;
-       if (!capable(CAP_SYS_ADMIN))
-@@ -908,14 +920,14 @@
-       lock_kernel();
--      error = __user_walk(new_root, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &new_nd);
-+      error = __user_walk_it(new_root, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &new_nd, &new_it);
-       if (error)
-               goto out0;
-       error = -EINVAL;
-       if (!check_mnt(new_nd.mnt))
-               goto out1;
--      error = __user_walk(put_old, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &old_nd);
-+      error = __user_walk_it(put_old, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &old_nd, &old_it);
-       if (error)
-               goto out1;
-@@ -970,8 +982,10 @@
-       up(&old_nd.dentry->d_inode->i_zombie);
-       up_write(&current->namespace->sem);
-       path_release(&user_nd);
-+      intent_release(&old_it);
-       path_release(&old_nd);
- out1:
-+      intent_release(&new_it);
-       path_release(&new_nd);
- out0:
-       unlock_kernel();
-Index: linux-2.4.20/fs/open.c
-===================================================================
---- linux-2.4.20.orig/fs/open.c        Wed Mar 17 13:57:03 2004
-+++ linux-2.4.20/fs/open.c     Wed Mar 17 13:57:11 2004
-@@ -19,6 +19,8 @@
- #include <asm/uaccess.h>
- #define special_file(m) (S_ISCHR(m)||S_ISBLK(m)||S_ISFIFO(m)||S_ISSOCK(m))
-+extern int path_walk_it(const char *name, struct nameidata *nd,
-+                      struct lookup_intent *it);
- int vfs_statfs(struct super_block *sb, struct statfs *buf)
- {
-@@ -95,9 +97,10 @@
-       write_unlock(&files->file_lock);
- }
--int do_truncate(struct dentry *dentry, loff_t length)
-+int do_truncate(struct dentry *dentry, loff_t length, int called_from_open)
- {
-       struct inode *inode = dentry->d_inode;
-+      struct inode_operations *op = dentry->d_inode->i_op;
-       int error;
-       struct iattr newattrs;
-@@ -108,7 +111,13 @@
-       down(&inode->i_sem);
-       newattrs.ia_size = length;
-       newattrs.ia_valid = ATTR_SIZE | ATTR_CTIME;
--      error = notify_change(dentry, &newattrs);
-+      if (called_from_open)
-+              newattrs.ia_valid |= ATTR_FROM_OPEN;
-+      if (op->setattr_raw) {
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+      } else
-+              error = notify_change(dentry, &newattrs);
-       up(&inode->i_sem);
-       return error;
- }
-@@ -118,12 +127,13 @@
-       struct nameidata nd;
-       struct inode * inode;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       error = -EINVAL;
-       if (length < 0) /* sorry, but loff_t says... */
-               goto out;
--      error = user_path_walk(path, &nd);
-+      error = user_path_walk_it(path, &nd, &it);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-@@ -163,11 +173,13 @@
-       error = locks_verify_truncate(inode, NULL, length);
-       if (!error) {
-               DQUOT_INIT(inode);
--              error = do_truncate(nd.dentry, length);
-+              intent_release(&it);
-+              error = do_truncate(nd.dentry, length, 0);
-       }
-       put_write_access(inode);
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
-@@ -215,7 +227,7 @@
-       error = locks_verify_truncate(inode, file, length);
-       if (!error)
--              error = do_truncate(dentry, length);
-+              error = do_truncate(dentry, length, 0);
- out_putf:
-       fput(file);
- out:
-@@ -260,11 +272,13 @@
-       struct inode * inode;
-       struct iattr newattrs;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, NULL);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-+      /* this is safe without a Lustre lock because it only depends
-+         on the super block */
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto dput_and_out;
-@@ -279,11 +293,25 @@
-                       goto dput_and_out;
-               newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET;
--      } else {
-+      }
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto dput_and_out;
-+      }
-+
-+      error = -EPERM;
-+      if (!times) {
-               if (current->fsuid != inode->i_uid &&
-                   (error = permission(inode,MAY_WRITE)) != 0)
-                       goto dput_and_out;
-       }
-+
-       error = notify_change(nd.dentry, &newattrs);
- dput_and_out:
-       path_release(&nd);
-@@ -304,12 +332,14 @@
-       struct inode * inode;
-       struct iattr newattrs;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, NULL);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-+      /* this is safe without a Lustre lock because it only depends
-+         on the super block */
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto dput_and_out;
-@@ -324,7 +354,20 @@
-               newattrs.ia_atime = times[0].tv_sec;
-               newattrs.ia_mtime = times[1].tv_sec;
-               newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET;
--      } else {
-+      }
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto dput_and_out;
-+      }
-+
-+      error = -EPERM;
-+      if (!utimes) {
-               if (current->fsuid != inode->i_uid &&
-                   (error = permission(inode,MAY_WRITE)) != 0)
-                       goto dput_and_out;
-@@ -347,6 +390,7 @@
-       int old_fsuid, old_fsgid;
-       kernel_cap_t old_cap;
-       int res;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       if (mode & ~S_IRWXO)    /* where's F_OK, X_OK, W_OK, R_OK? */
-               return -EINVAL;
-@@ -364,13 +408,14 @@
-       else
-               current->cap_effective = current->cap_permitted;
--      res = user_path_walk(filename, &nd);
-+      res = user_path_walk_it(filename, &nd, &it);
-       if (!res) {
-               res = permission(nd.dentry->d_inode, mode);
-               /* SuS v2 requires we report a read only fs too */
-               if(!res && (mode & S_IWOTH) && IS_RDONLY(nd.dentry->d_inode)
-                  && !special_file(nd.dentry->d_inode->i_mode))
-                       res = -EROFS;
-+              intent_release(&it);
-               path_release(&nd);
-       }
-@@ -385,8 +430,9 @@
- {
-       int error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = __user_walk(filename,LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY,&nd);
-+      error = __user_walk_it(filename,LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY,&nd, &it);
-       if (error)
-               goto out;
-@@ -397,6 +443,7 @@
-       set_fs_pwd(current->fs, nd.mnt, nd.dentry);
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
-@@ -436,9 +483,10 @@
- {
-       int error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = __user_walk(filename, LOOKUP_POSITIVE | LOOKUP_FOLLOW |
--                    LOOKUP_DIRECTORY | LOOKUP_NOALT, &nd);
-+      error = __user_walk_it(filename, LOOKUP_POSITIVE | LOOKUP_FOLLOW |
-+                             LOOKUP_DIRECTORY | LOOKUP_NOALT, &nd, &it);
-       if (error)
-               goto out;
-@@ -454,39 +502,56 @@
-       set_fs_altroot();
-       error = 0;
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
- }
--asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
-+int chmod_common(struct dentry *dentry, mode_t mode)
- {
--      struct inode * inode;
--      struct dentry * dentry;
--      struct file * file;
--      int err = -EBADF;
-+      struct inode *inode = dentry->d_inode;
-       struct iattr newattrs;
-+      int err = -EROFS;
--      file = fget(fd);
--      if (!file)
-+      if (IS_RDONLY(inode))
-               goto out;
--      dentry = file->f_dentry;
--      inode = dentry->d_inode;
-+      if (inode->i_op->setattr_raw) {
-+              newattrs.ia_mode = mode;
-+              newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
-+              newattrs.ia_valid |= ATTR_RAW;
-+              err = inode->i_op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (err != -EOPNOTSUPP)
-+                      goto out;
-+      }
--      err = -EROFS;
--      if (IS_RDONLY(inode))
--              goto out_putf;
-       err = -EPERM;
-       if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
--              goto out_putf;
-+              goto out;
-+
-       if (mode == (mode_t) -1)
-               mode = inode->i_mode;
-       newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
-       newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
-       err = notify_change(dentry, &newattrs);
--out_putf:
-+out:
-+      return err;
-+}
-+
-+asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
-+{
-+      struct file * file;
-+      int err = -EBADF;
-+
-+      file = fget(fd);
-+      if (!file)
-+              goto out;
-+
-+      err = chmod_common(file->f_dentry, mode);
-+
-       fput(file);
- out:
-       return err;
-@@ -495,30 +560,14 @@
- asmlinkage long sys_chmod(const char * filename, mode_t mode)
- {
-       struct nameidata nd;
--      struct inode * inode;
-       int error;
--      struct iattr newattrs;
-       error = user_path_walk(filename, &nd);
-       if (error)
-               goto out;
--      inode = nd.dentry->d_inode;
--
--      error = -EROFS;
--      if (IS_RDONLY(inode))
--              goto dput_and_out;
--
--      error = -EPERM;
--      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
--              goto dput_and_out;
--      if (mode == (mode_t) -1)
--              mode = inode->i_mode;
--      newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
--      newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
--      error = notify_change(nd.dentry, &newattrs);
-+      error = chmod_common(nd.dentry, mode);
--dput_and_out:
-       path_release(&nd);
- out:
-       return error;
-@@ -538,6 +587,20 @@
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto out;
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = dentry->d_inode->i_op;
-+
-+              newattrs.ia_uid = user;
-+              newattrs.ia_gid = group;
-+              newattrs.ia_valid = ATTR_UID | ATTR_GID | ATTR_CTIME;
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      return error;
-+      }
-+
-       error = -EPERM;
-       if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-               goto out;
-@@ -642,8 +705,9 @@
- {
-       int namei_flags, error;
-       struct nameidata nd;
--      
--      flags &= ~O_DIRECT;
-+      struct lookup_intent it = { .it_op = IT_OPEN };
-+
-+      //flags &= ~O_DIRECT;
-       namei_flags = flags;
-       if ((namei_flags+1) & O_ACCMODE)
-@@ -651,14 +715,15 @@
-       if (namei_flags & O_TRUNC)
-               namei_flags |= 2;
--      error = open_namei(filename, namei_flags, mode, &nd);
--      if (!error)
--              return dentry_open(nd.dentry, nd.mnt, flags);
-+      error = open_namei_it(filename, namei_flags, mode, &nd, &it);
-+      if (error)
-+              return ERR_PTR(error);
--      return ERR_PTR(error);
-+      return dentry_open_it(nd.dentry, nd.mnt, flags, &it);
- }
--struct file *dentry_open(struct dentry *dentry, struct vfsmount *mnt, int flags)
-+struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-+                          int flags, struct lookup_intent *it)
- {
-       struct file * f;
-       struct inode *inode;
-@@ -695,12 +760,15 @@
-       }
-       if (f->f_op && f->f_op->open) {
-+              f->f_it = it;
-               error = f->f_op->open(inode,f);
-+              f->f_it = NULL;
-               if (error)
-                       goto cleanup_all;
-       }
-       f->f_flags &= ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
-+      intent_release(it);
-       return f;
- cleanup_all:
-@@ -715,11 +783,17 @@
- cleanup_file:
-       put_filp(f);
- cleanup_dentry:
-+      intent_release(it);
-       dput(dentry);
-       mntput(mnt);
-       return ERR_PTR(error);
- }
-+struct file *dentry_open(struct dentry *dentry, struct vfsmount *mnt, int flags)
-+{
-+      return dentry_open_it(dentry, mnt, flags, NULL);
-+}
-+
- /*
-  * Find an empty file descriptor entry, and mark it busy.
-  */
-Index: linux-2.4.20/fs/proc/base.c
-===================================================================
---- linux-2.4.20.orig/fs/proc/base.c   Wed Mar 17 13:57:05 2004
-+++ linux-2.4.20/fs/proc/base.c        Wed Mar 17 13:57:11 2004
-@@ -494,6 +494,9 @@
-       error = inode->u.proc_i.op.proc_get_link(inode, &nd->dentry, &nd->mnt);
-       nd->last_type = LAST_BIND;
-+
-+      if (nd->intent != NULL)
-+              nd->intent->d.lustre.it_int_flags |= IT_FL_FOLLOWED;
- out:
-       return error;
- }
-Index: linux-2.4.20/fs/stat.c
-===================================================================
---- linux-2.4.20.orig/fs/stat.c        Wed Mar 17 13:57:05 2004
-+++ linux-2.4.20/fs/stat.c     Wed Mar 17 13:58:01 2004
-@@ -17,10 +17,12 @@
-  * Revalidate the inode. This is required for proper NFS attribute caching.
-  */
- static __inline__ int
--do_revalidate(struct dentry *dentry)
-+do_revalidate(struct dentry *dentry, struct lookup_intent *it)
- {
-       struct inode * inode = dentry->d_inode;
--      if (inode->i_op && inode->i_op->revalidate)
-+      if (inode->i_op && inode->i_op->revalidate_it)
-+              return inode->i_op->revalidate_it(dentry, it);
-+      else if (inode->i_op && inode->i_op->revalidate)
-               return inode->i_op->revalidate(dentry);
-       return 0;
- }
-@@ -32,13 +34,13 @@
-       return inode->i_nlink;
- }
--static int do_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
-+static int do_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat, struct lookup_intent *it)
- {
-       int res = 0;
-       unsigned int blocks, indirect;
-       struct inode *inode = dentry->d_inode;
--      res = do_revalidate(dentry);
-+      res = do_revalidate(dentry, it);
-       if (res)
-               return res;
-@@ -111,10 +113,12 @@
- {
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = user_path_walk(name, &nd);
-+      error = user_path_walk_it(name, &nd, &it);
-       if (!error) {
--              error = do_getattr(nd.mnt, nd.dentry, stat);
-+              error = do_getattr(nd.mnt, nd.dentry, stat, &it);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -124,10 +128,12 @@
- {
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = user_path_walk_link(name, &nd);
-+      error = user_path_walk_link_it(name, &nd, &it);
-       if (!error) {
--              error = do_getattr(nd.mnt, nd.dentry, stat);
-+              error = do_getattr(nd.mnt, nd.dentry, stat, &it);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -139,7 +145,7 @@
-       int error = -EBADF;
-       if (f) {
--              error = do_getattr(f->f_vfsmnt, f->f_dentry, stat);
-+              error = do_getattr(f->f_vfsmnt, f->f_dentry, stat, NULL);
-               fput(f);
-       }
-       return error;
-@@ -286,7 +292,7 @@
-               error = -EINVAL;
-               if (inode->i_op && inode->i_op->readlink &&
--                  !(error = do_revalidate(nd.dentry))) {
-+                  !(error = do_revalidate(nd.dentry, NULL))) {
-                       UPDATE_ATIME(inode);
-                       error = inode->i_op->readlink(nd.dentry, buf, bufsiz);
-               }
-Index: linux-2.4.20/include/linux/dcache.h
-===================================================================
---- linux-2.4.20.orig/include/linux/dcache.h   Wed Mar 17 13:57:04 2004
-+++ linux-2.4.20/include/linux/dcache.h        Wed Mar 17 13:57:11 2004
-@@ -6,6 +6,51 @@
- #include <asm/atomic.h>
- #include <linux/mount.h>
- #include <linux/kernel.h>
-+#include <linux/string.h>
-+
-+#define IT_OPEN     0x0001
-+#define IT_CREAT    0x0002
-+#define IT_READDIR  0x0004
-+#define IT_GETATTR  0x0008
-+#define IT_LOOKUP   0x0010
-+#define IT_UNLINK   0x0020
-+#define IT_GETXATTR 0x0040
-+#define IT_EXEC     0x0080
-+#define IT_PIN      0x0100
-+
-+#define IT_FL_LOCKED   0x0001
-+#define IT_FL_FOLLOWED 0x0002 /* set by vfs_follow_link */
-+
-+#define INTENT_MAGIC 0x19620323
-+
-+
-+struct lustre_intent_data {
-+      int       it_disposition;
-+      int       it_status;
-+      __u64     it_lock_handle;
-+      void     *it_data;
-+      int       it_lock_mode;
-+      int it_int_flags;
-+};
-+struct lookup_intent {
-+      int     it_magic;
-+      void    (*it_op_release)(struct lookup_intent *);
-+      int     it_op;
-+      int     it_flags;
-+      int     it_create_mode;
-+      union {
-+              struct lustre_intent_data lustre;
-+      } d;
-+};
-+
-+static inline void intent_init(struct lookup_intent *it, int op, int flags)
-+{
-+      memset(it, 0, sizeof(*it));
-+      it->it_magic = INTENT_MAGIC;
-+      it->it_op = op;
-+      it->it_flags = flags;
-+}
-+
- /*
-  * linux/include/linux/dcache.h
-@@ -96,8 +141,22 @@
-       int (*d_delete)(struct dentry *);
-       void (*d_release)(struct dentry *);
-       void (*d_iput)(struct dentry *, struct inode *);
-+      int (*d_revalidate_it)(struct dentry *, int, struct lookup_intent *);
-+      void (*d_pin)(struct dentry *, struct vfsmount * , int);
-+      void (*d_unpin)(struct dentry *, struct vfsmount *, int);
- };
-+#define PIN(de,mnt,flag)  if (de && de->d_op && de->d_op->d_pin) \
-+                              de->d_op->d_pin(de, mnt, flag);
-+#define UNPIN(de,mnt,flag)  if (de && de->d_op && de->d_op->d_unpin) \
-+                              de->d_op->d_unpin(de, mnt, flag);
-+
-+
-+/* defined in fs/namei.c */
-+extern void intent_release(struct lookup_intent *it);
-+/* defined in fs/dcache.c */
-+extern void __d_rehash(struct dentry * entry, int lock);
-+
- /* the dentry parameter passed to d_hash and d_compare is the parent
-  * directory of the entries to be compared. It is used in case these
-  * functions need any directory specific information for determining
-@@ -129,6 +188,7 @@
-                                        * s_nfsd_free_path semaphore will be down
-                                        */
- #define DCACHE_REFERENCED     0x0008  /* Recently used, don't discard. */
-+#define DCACHE_LUSTRE_INVALID 0x0010  /* Lustre invalidated */
- extern spinlock_t dcache_lock;
-Index: linux-2.4.20/include/linux/fs.h
-===================================================================
---- linux-2.4.20.orig/include/linux/fs.h       Wed Mar 17 13:57:11 2004
-+++ linux-2.4.20/include/linux/fs.h    Wed Mar 17 13:57:11 2004
-@@ -73,6 +73,7 @@
- #define FMODE_READ 1
- #define FMODE_WRITE 2
-+#define FMODE_EXEC 4
- #define READ 0
- #define WRITE 1
-@@ -338,6 +339,9 @@
- #define ATTR_MTIME_SET        256
- #define ATTR_FORCE    512     /* Not a change, but a change it */
- #define ATTR_ATTR_FLAG        1024
-+#define ATTR_RAW      0x0800  /* file system, not vfs will massage attrs */
-+#define ATTR_FROM_OPEN        0x1000  /* called from open path, ie O_TRUNC */
-+#define ATTR_CTIME_SET        0x2000
- /*
-  * This is the Inode Attributes structure, used for notify_change().  It
-@@ -473,6 +477,7 @@
-       struct pipe_inode_info  *i_pipe;
-       struct block_device     *i_bdev;
-       struct char_device      *i_cdev;
-+      void                    *i_filterdata;
-       unsigned long           i_dnotify_mask; /* Directory notify events */
-       struct dnotify_struct   *i_dnotify; /* for directory notifications */
-@@ -575,6 +580,7 @@
-       /* needed for tty driver, and maybe others */
-       void                    *private_data;
-+      struct lookup_intent    *f_it;
-       /* preallocated helper kiobuf to speedup O_DIRECT */
-       struct kiobuf           *f_iobuf;
-@@ -702,6 +708,7 @@
-       struct qstr last;
-       unsigned int flags;
-       int last_type;
-+      struct lookup_intent *intent;
- };
- /*
-@@ -822,7 +829,8 @@
- extern int vfs_link(struct dentry *, struct inode *, struct dentry *);
- extern int vfs_rmdir(struct inode *, struct dentry *);
- extern int vfs_unlink(struct inode *, struct dentry *);
--extern int vfs_rename(struct inode *, struct dentry *, struct inode *, struct dentry *);
-+int vfs_rename(struct inode *old_dir, struct dentry *old_dentry,
-+             struct inode *new_dir, struct dentry *new_dentry);
- /*
-  * File types
-@@ -882,21 +890,32 @@
- struct inode_operations {
-       int (*create) (struct inode *,struct dentry *,int);
-+      int (*create_it) (struct inode *,struct dentry *,int, struct lookup_intent *);
-       struct dentry * (*lookup) (struct inode *,struct dentry *);
-+      struct dentry * (*lookup_it) (struct inode *,struct dentry *, struct lookup_intent *, int flags);
-       int (*link) (struct dentry *,struct inode *,struct dentry *);
-+      int (*link_raw) (struct nameidata *,struct nameidata *);
-       int (*unlink) (struct inode *,struct dentry *);
-+      int (*unlink_raw) (struct nameidata *);
-       int (*symlink) (struct inode *,struct dentry *,const char *);
-+      int (*symlink_raw) (struct nameidata *,const char *);
-       int (*mkdir) (struct inode *,struct dentry *,int);
-+      int (*mkdir_raw) (struct nameidata *,int);
-       int (*rmdir) (struct inode *,struct dentry *);
-+      int (*rmdir_raw) (struct nameidata *);
-       int (*mknod) (struct inode *,struct dentry *,int,int);
-+      int (*mknod_raw) (struct nameidata *,int,dev_t);
-       int (*rename) (struct inode *, struct dentry *,
-                       struct inode *, struct dentry *);
-+      int (*rename_raw) (struct nameidata *, struct nameidata *);
-       int (*readlink) (struct dentry *, char *,int);
-       int (*follow_link) (struct dentry *, struct nameidata *);
-       void (*truncate) (struct inode *);
-       int (*permission) (struct inode *, int);
-       int (*revalidate) (struct dentry *);
-+      int (*revalidate_it) (struct dentry *, struct lookup_intent *);
-       int (*setattr) (struct dentry *, struct iattr *);
-+      int (*setattr_raw) (struct inode *, struct iattr *);
-       int (*getattr) (struct dentry *, struct iattr *);
-       int (*setxattr) (struct dentry *, const char *, void *, size_t, int);
-       ssize_t (*getxattr) (struct dentry *, const char *, void *, size_t);
-@@ -1092,10 +1111,14 @@
- asmlinkage long sys_open(const char *, int, int);
- asmlinkage long sys_close(unsigned int);      /* yes, it's really unsigned */
--extern int do_truncate(struct dentry *, loff_t start);
-+extern int do_truncate(struct dentry *, loff_t start, int called_from_open);
- extern struct file *filp_open(const char *, int, int);
- extern struct file * dentry_open(struct dentry *, struct vfsmount *, int);
-+extern int open_namei_it(const char *filename, int namei_flags, int mode,
-+                       struct nameidata *nd, struct lookup_intent *it);
-+extern struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-+                          int flags, struct lookup_intent *it);
- extern int filp_close(struct file *, fl_owner_t id);
- extern char * getname(const char *);
-@@ -1386,6 +1409,7 @@
- extern loff_t default_llseek(struct file *file, loff_t offset, int origin);
- extern int FASTCALL(__user_walk(const char *, unsigned, struct nameidata *));
-+extern int FASTCALL(__user_walk_it(const char *, unsigned, struct nameidata *, struct lookup_intent *it));
- extern int FASTCALL(path_init(const char *, unsigned, struct nameidata *));
- extern int FASTCALL(path_walk(const char *, struct nameidata *));
- extern int FASTCALL(path_lookup(const char *, unsigned, struct nameidata *));
-@@ -1397,6 +1421,8 @@
- extern struct dentry * lookup_hash(struct qstr *, struct dentry *);
- #define user_path_walk(name,nd)        __user_walk(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd)
- #define user_path_walk_link(name,nd) __user_walk(name, LOOKUP_POSITIVE, nd)
-+#define user_path_walk_it(name,nd,it)  __user_walk_it(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd, it)
-+#define user_path_walk_link_it(name,nd,it) __user_walk_it(name, LOOKUP_POSITIVE, nd, it)
- extern void inode_init_once(struct inode *);
- extern void iput(struct inode *);
-@@ -1504,6 +1530,8 @@
- extern int vfs_readlink(struct dentry *, char *, int, const char *);
- extern int vfs_follow_link(struct nameidata *, const char *);
-+extern int vfs_follow_link_it(struct nameidata *, const char *,
-+                            struct lookup_intent *it);
- extern int page_readlink(struct dentry *, char *, int);
- extern int page_follow_link(struct dentry *, struct nameidata *);
- extern struct inode_operations page_symlink_inode_operations;
-Index: linux-2.4.20/include/linux/fs_struct.h
-===================================================================
---- linux-2.4.20.orig/include/linux/fs_struct.h        Wed Mar 17 13:57:02 2004
-+++ linux-2.4.20/include/linux/fs_struct.h     Wed Mar 17 13:57:11 2004
-@@ -37,10 +37,12 @@
-       write_lock(&fs->lock);
-       old_root = fs->root;
-       old_rootmnt = fs->rootmnt;
-+      PIN(dentry, mnt, 1);
-       fs->rootmnt = mntget(mnt);
-       fs->root = dget(dentry);
-       write_unlock(&fs->lock);
-       if (old_root) {
-+              UNPIN(old_root, old_rootmnt, 1);
-               dput(old_root);
-               mntput(old_rootmnt);
-       }
-@@ -60,10 +62,12 @@
-       write_lock(&fs->lock);
-       old_pwd = fs->pwd;
-       old_pwdmnt = fs->pwdmnt;
-+      PIN(dentry, mnt, 0);
-       fs->pwdmnt = mntget(mnt);
-       fs->pwd = dget(dentry);
-       write_unlock(&fs->lock);
-       if (old_pwd) {
-+              UNPIN(old_pwd, old_pwdmnt, 0);
-               dput(old_pwd);
-               mntput(old_pwdmnt);
-       }
-Index: linux-2.4.20/kernel/ksyms.c
-===================================================================
---- linux-2.4.20.orig/kernel/ksyms.c   Wed Mar 17 13:57:11 2004
-+++ linux-2.4.20/kernel/ksyms.c        Wed Mar 17 13:57:11 2004
-@@ -297,6 +297,7 @@
- EXPORT_SYMBOL(set_page_dirty);
- EXPORT_SYMBOL(vfs_readlink);
- EXPORT_SYMBOL(vfs_follow_link);
-+EXPORT_SYMBOL(vfs_follow_link_it);
- EXPORT_SYMBOL(page_readlink);
- EXPORT_SYMBOL(page_follow_link);
- EXPORT_SYMBOL(page_symlink_inode_operations);
-Index: linux-2.4.20/kernel/fork.c
-===================================================================
---- linux-2.4.20.orig/kernel/fork.c    Wed Mar 17 13:57:05 2004
-+++ linux-2.4.20/kernel/fork.c Wed Mar 17 13:57:11 2004
-@@ -440,10 +440,13 @@
-               fs->umask = old->umask;
-               read_lock(&old->lock);
-               fs->rootmnt = mntget(old->rootmnt);
-+              PIN(old->pwd, old->pwdmnt, 0);
-+              PIN(old->root, old->rootmnt, 1);
-               fs->root = dget(old->root);
-               fs->pwdmnt = mntget(old->pwdmnt);
-               fs->pwd = dget(old->pwd);
-               if (old->altroot) {
-+                      PIN(old->altroot, old->altrootmnt, 1);
-                       fs->altrootmnt = mntget(old->altrootmnt);
-                       fs->altroot = dget(old->altroot);
-               } else {
-Index: linux-2.4.20/kernel/exit.c
-===================================================================
---- linux-2.4.20.orig/kernel/exit.c    Wed Mar 17 13:57:05 2004
-+++ linux-2.4.20/kernel/exit.c Wed Mar 17 13:57:11 2004
-@@ -345,11 +345,14 @@
- {
-       /* No need to hold fs->lock if we are killing it */
-       if (atomic_dec_and_test(&fs->count)) {
-+              UNPIN(fs->pwd, fs->pwdmnt, 0);
-+              UNPIN(fs->root, fs->rootmnt, 1);
-               dput(fs->root);
-               mntput(fs->rootmnt);
-               dput(fs->pwd);
-               mntput(fs->pwdmnt);
-               if (fs->altroot) {
-+                      UNPIN(fs->altroot, fs->altrootmnt, 1);
-                       dput(fs->altroot);
-                       mntput(fs->altrootmnt);
-               }
diff --git a/lustre/kernel_patches/patches/vfs_intent-2.4.21-chaos.patch b/lustre/kernel_patches/patches/vfs_intent-2.4.21-chaos.patch
deleted file mode 100644 (file)
index 8ef6d8f..0000000
+++ /dev/null
@@ -1,1870 +0,0 @@
- fs/dcache.c               |   19 ++
- fs/exec.c                 |   17 +-
- fs/namei.c                |  295 +++++++++++++++++++++++++++++++++++++++-------
- fs/namespace.c            |   28 +++-
- fs/open.c                 |  172 +++++++++++++++++++-------
- fs/stat.c                 |   52 +++++---
- include/linux/dcache.h    |   60 +++++++++
- include/linux/fs.h        |   32 ++++
- include/linux/fs_struct.h |    4 
- kernel/exit.c             |    3 
- kernel/fork.c             |    3 
- kernel/ksyms.c            |    1 
- 12 files changed, 558 insertions(+), 128 deletions(-)
-
-Index: linux-ia64/fs/dcache.c
-===================================================================
---- linux-ia64.orig/fs/dcache.c        2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/fs/dcache.c     2004-03-17 16:05:28.000000000 -0800
-@@ -186,6 +186,13 @@ int d_invalidate(struct dentry * dentry)
-               spin_unlock(&dcache_lock);
-               return 0;
-       }
-+
-+      /* network invalidation by Lustre */
-+      if (dentry->d_flags & DCACHE_LUSTRE_INVALID) {
-+              spin_unlock(&dcache_lock);
-+              return 0;
-+      }
-+
-       /*
-        * Check whether to do a partial shrink_dcache
-        * to get rid of unused child entries.
-@@ -850,13 +857,19 @@ void d_delete(struct dentry * dentry)
-  * Adds a dentry to the hash according to its name.
-  */
-  
--void d_rehash(struct dentry * entry)
-+void __d_rehash(struct dentry * entry, int lock)
- {
-       struct list_head *list = d_hash(entry->d_parent, entry->d_name.hash);
-       if (!list_empty(&entry->d_hash)) BUG();
--      spin_lock(&dcache_lock);
-+      if (lock) spin_lock(&dcache_lock);
-       list_add(&entry->d_hash, list);
--      spin_unlock(&dcache_lock);
-+      if (lock) spin_unlock(&dcache_lock);
-+}
-+EXPORT_SYMBOL(__d_rehash);
-+
-+void d_rehash(struct dentry * entry)
-+{
-+      __d_rehash(entry, 1);
- }
- #define do_switch(x,y) do { \
-Index: linux-ia64/fs/exec.c
-===================================================================
---- linux-ia64.orig/fs/exec.c  2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/fs/exec.c       2004-03-17 16:05:28.000000000 -0800
-@@ -119,8 +119,10 @@ asmlinkage long sys_uselib(const char * 
-       struct file * file;
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_OPEN,
-+                                  .it_flags = FMODE_READ|FMODE_EXEC };
--      error = user_path_walk(library, &nd);
-+      error = user_path_walk_it(library, &nd, &it);
-       if (error)
-               goto out;
-@@ -132,7 +134,8 @@ asmlinkage long sys_uselib(const char * 
-       if (error)
-               goto exit;
--      file = dentry_open(nd.dentry, nd.mnt, O_RDONLY);
-+      file = dentry_open_it(nd.dentry, nd.mnt, O_RDONLY, &it);
-+      intent_release(&it);
-       error = PTR_ERR(file);
-       if (IS_ERR(file))
-               goto out;
-@@ -400,8 +403,10 @@ struct file *open_exec(const char *name)
-       struct inode *inode;
-       struct file *file;
-       int err = 0;
-+      struct lookup_intent it = { .it_op = IT_OPEN,
-+                                  .it_flags = FMODE_READ|FMODE_EXEC };
--      err = path_lookup(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd);
-+      err = path_lookup_it(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd, &it);
-       file = ERR_PTR(err);
-       if (!err) {
-               inode = nd.dentry->d_inode;
-@@ -413,7 +418,8 @@ struct file *open_exec(const char *name)
-                               err = -EACCES;
-                       file = ERR_PTR(err);
-                       if (!err) {
--                              file = dentry_open(nd.dentry, nd.mnt, O_RDONLY);
-+                              file = dentry_open_it(nd.dentry, nd.mnt, O_RDONLY, &it);
-+                              intent_release(&it);
-                               if (!IS_ERR(file)) {
-                                       err = deny_write_access(file);
-                                       if (err) {
-@@ -425,6 +431,7 @@ out:
-                               return file;
-                       }
-               }
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       goto out;
-@@ -1348,7 +1355,7 @@ int do_coredump(long signr, int exit_cod
-               goto close_fail;
-       if (!file->f_op->write)
-               goto close_fail;
--      if (do_truncate(file->f_dentry, 0) != 0)
-+      if (do_truncate(file->f_dentry, 0, 0) != 0)
-               goto close_fail;
-       retval = binfmt->core_dump(signr, regs, file);
-Index: linux-ia64/fs/namei.c
-===================================================================
---- linux-ia64.orig/fs/namei.c 2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/fs/namei.c      2004-03-17 16:06:13.000000000 -0800
-@@ -94,6 +94,13 @@
-  * XEmacs seems to be relying on it...
-  */
-+void intent_release(struct lookup_intent *it)
-+{
-+      if (it && it->it_op_release)
-+              it->it_op_release(it);
-+
-+}
-+
- /* In order to reduce some races, while at the same time doing additional
-  * checking and hopefully speeding things up, we copy filenames to the
-  * kernel data space before using them..
-@@ -260,10 +267,19 @@ void path_release(struct nameidata *nd)
-  * Internal lookup() using the new generic dcache.
-  * SMP-safe
-  */
--static struct dentry * cached_lookup(struct dentry * parent, struct qstr * name, int flags)
-+static struct dentry *cached_lookup(struct dentry *parent, struct qstr *name,
-+                                  int flags, struct lookup_intent *it)
- {
-       struct dentry * dentry = d_lookup(parent, name);
-+      if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if (!dentry->d_op->d_revalidate_it(dentry, flags, it) &&
-+                  !d_invalidate(dentry)) {
-+                      dput(dentry);
-+                      dentry = NULL;
-+              }
-+              return dentry;
-+      } else
-       if (dentry && dentry->d_op && dentry->d_op->d_revalidate) {
-               if (!dentry->d_op->d_revalidate(dentry, flags) && !d_invalidate(dentry)) {
-                       dput(dentry);
-@@ -281,11 +297,15 @@ static struct dentry * cached_lookup(str
-  * make sure that nobody added the entry to the dcache in the meantime..
-  * SMP-safe
-  */
--static struct dentry * real_lookup(struct dentry * parent, struct qstr * name, int flags)
-+static struct dentry *real_lookup(struct dentry *parent, struct qstr *name,
-+                                int flags, struct lookup_intent *it)
- {
-       struct dentry * result;
-       struct inode *dir = parent->d_inode;
-+      int counter = 0;
-+again:
-+      counter++;
-       down(&dir->i_sem);
-       /*
-        * First re-do the cached lookup just in case it was created
-@@ -300,6 +320,9 @@ static struct dentry * real_lookup(struc
-               result = ERR_PTR(-ENOMEM);
-               if (dentry) {
-                       lock_kernel();
-+                      if (dir->i_op->lookup_it)
-+                              result = dir->i_op->lookup_it(dir, dentry, it, flags);
-+                      else
-                       result = dir->i_op->lookup(dir, dentry);
-                       unlock_kernel();
-                       if (result)
-@@ -321,6 +344,15 @@ static struct dentry * real_lookup(struc
-                       dput(result);
-                       result = ERR_PTR(-ENOENT);
-               }
-+      } else if (result->d_op && result->d_op->d_revalidate_it) {
-+              if (!result->d_op->d_revalidate_it(result, flags, it) &&
-+                  !d_invalidate(result)) {
-+                      dput(result);
-+                      if (counter > 10)
-+                              result = ERR_PTR(-ESTALE);
-+                      if (!IS_ERR(result))
-+                              goto again;
-+              }
-       }
-       return result;
- }
-@@ -332,7 +364,8 @@ static struct dentry * real_lookup(struc
-  * Without that kind of total limit, nasty chains of consecutive
-  * symlinks can cause almost arbitrarily long lookups. 
-  */
--static inline int do_follow_link(struct dentry *dentry, struct nameidata *nd)
-+static inline int do_follow_link(struct dentry *dentry, struct nameidata *nd,
-+                               struct lookup_intent *it)
- {
-       int err;
-       if (current->link_count >= 8)
-@@ -346,10 +379,12 @@ static inline int do_follow_link(struct 
-       current->link_count++;
-       current->total_link_count++;
-       UPDATE_ATIME(dentry->d_inode);
-+      nd->intent = it;
-       err = dentry->d_inode->i_op->follow_link(dentry, nd);
-       current->link_count--;
-       return err;
- loop:
-+      intent_release(it);
-       path_release(nd);
-       return -ELOOP;
- }
-@@ -447,7 +482,8 @@ static inline void follow_dotdot(struct 
-  *
-  * We expect 'base' to be positive and a directory.
-  */
--int link_path_walk(const char * name, struct nameidata *nd)
-+int link_path_walk_it(const char *name, struct nameidata *nd,
-+                    struct lookup_intent *it)
- {
-       struct dentry *dentry;
-       struct inode *inode;
-@@ -524,12 +560,12 @@ int link_path_walk(const char * name, st
-                               break;
-               }
-               /* This does the actual lookups.. */
--              dentry = cached_lookup(nd->dentry, &this, LOOKUP_CONTINUE);
-+              dentry = cached_lookup(nd->dentry, &this, LOOKUP_CONTINUE, NULL);
-               if (!dentry) {
-                       err = -EWOULDBLOCKIO;
-                       if (atomic)
-                               break;
--                      dentry = real_lookup(nd->dentry, &this, LOOKUP_CONTINUE);
-+                      dentry = real_lookup(nd->dentry, &this, LOOKUP_CONTINUE, NULL);
-                       err = PTR_ERR(dentry);
-                       if (IS_ERR(dentry))
-                               break;
-@@ -547,7 +583,7 @@ int link_path_walk(const char * name, st
-                       goto out_dput;
-               if (inode->i_op->follow_link) {
--                      err = do_follow_link(dentry, nd);
-+                      err = do_follow_link(dentry, nd, NULL);
-                       dput(dentry);
-                       if (err)
-                               goto return_err;
-@@ -563,7 +599,7 @@ int link_path_walk(const char * name, st
-                       nd->dentry = dentry;
-               }
-               err = -ENOTDIR; 
--              if (!inode->i_op->lookup)
-+              if (!inode->i_op->lookup && !inode->i_op->lookup_it)
-                       break;
-               continue;
-               /* here ends the main loop */
-@@ -590,12 +626,12 @@ last_component:
-                       if (err < 0)
-                               break;
-               }
--              dentry = cached_lookup(nd->dentry, &this, 0);
-+              dentry = cached_lookup(nd->dentry, &this, 0, it);
-               if (!dentry) {
-                       err = -EWOULDBLOCKIO;
-                       if (atomic)
-                               break;
--                      dentry = real_lookup(nd->dentry, &this, 0);
-+                      dentry = real_lookup(nd->dentry, &this, 0, it);
-                       err = PTR_ERR(dentry);
-                       if (IS_ERR(dentry))
-                               break;
-@@ -605,7 +641,7 @@ last_component:
-               inode = dentry->d_inode;
-               if ((lookup_flags & LOOKUP_FOLLOW)
-                   && inode && inode->i_op && inode->i_op->follow_link) {
--                      err = do_follow_link(dentry, nd);
-+                      err = do_follow_link(dentry, nd, it);
-                       dput(dentry);
-                       if (err)
-                               goto return_err;
-@@ -619,7 +655,8 @@ last_component:
-                       goto no_inode;
-               if (lookup_flags & LOOKUP_DIRECTORY) {
-                       err = -ENOTDIR; 
--                      if (!inode->i_op || !inode->i_op->lookup)
-+                      if (!inode->i_op ||
-+                          (!inode->i_op->lookup && !inode->i_op->lookup_it))
-                               break;
-               }
-               goto return_base;
-@@ -637,12 +672,42 @@ return_reval:
-                       nd->last_type = LAST_DOT;
-               else if (this.len == 2 && this.name[1] == '.')
-                       nd->last_type = LAST_DOTDOT;
-+              else
-+                      goto return_base;
- return_reval:
-               /*
-                * We bypassed the ordinary revalidation routines.
-                * Check the cached dentry for staleness.
-                */
-               dentry = nd->dentry;
-+              if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+                      err = -ESTALE;
-+                      if (!dentry->d_op->d_revalidate_it(dentry, 0, it)) {
-+                              struct dentry *new;
-+                              err = permission(dentry->d_parent->d_inode,
-+                                               MAY_EXEC);
-+                              if (err)
-+                                      break;
-+                              new = real_lookup(dentry->d_parent,
-+                                                &dentry->d_name, 0, it);
-+                              if (IS_ERR(new)) {
-+                                      err = PTR_ERR(new);
-+                                      break;
-+                              }
-+                              d_invalidate(dentry);
-+                              dput(dentry);
-+                              nd->dentry = new;
-+                      }
-+                      if (!nd->dentry->d_inode)
-+                              goto no_inode;
-+                      if (lookup_flags & LOOKUP_DIRECTORY) {
-+                              err = -ENOTDIR; 
-+                              if (!nd->dentry->d_inode->i_op ||
-+                                  (!nd->dentry->d_inode->i_op->lookup &&
-+                                   !nd->dentry->d_inode->i_op->lookup_it))
-+                                      break;
-+                      }
-+              } else
-               if (dentry && dentry->d_op && dentry->d_op->d_revalidate) {
-                       err = -ESTALE;
-                       if (!dentry->d_op->d_revalidate(dentry, 0)) {
-@@ -656,15 +714,28 @@ out_dput:
-               dput(dentry);
-               break;
-       }
-+      if (err)
-+              intent_release(it);
-       path_release(nd);
- return_err:
-       return err;
- }
-+int link_path_walk(const char * name, struct nameidata *nd)
-+{
-+      return link_path_walk_it(name, nd, NULL);
-+}
-+
-+int path_walk_it(const char * name, struct nameidata *nd, struct lookup_intent *it)
-+{
-+      current->total_link_count = 0;
-+      return link_path_walk_it(name, nd, it);
-+}
-+
- int path_walk(const char * name, struct nameidata *nd)
- {
-       current->total_link_count = 0;
--      return link_path_walk(name, nd);
-+      return link_path_walk_it(name, nd, NULL);
- }
- /* SMP-safe */
-@@ -749,6 +820,17 @@ walk_init_root(const char *name, struct 
- }
- /* SMP-safe */
-+int path_lookup_it(const char *path, unsigned flags, struct nameidata *nd,
-+                 struct lookup_intent *it)
-+{
-+      int error = 0;
-+      if (path_init(path, flags, nd))
-+              error = path_walk_it(path, nd, it);
-+      return error;
-+}
-+
-+
-+/* SMP-safe */
- int path_lookup(const char *path, unsigned flags, struct nameidata *nd)
- {
-       int error = 0;
-@@ -763,6 +845,7 @@ int path_init(const char *name, unsigned
- {
-       nd->last_type = LAST_ROOT; /* if there are only slashes... */
-       nd->flags = flags;
-+      nd->intent = NULL;
-       if (*name=='/')
-               return walk_init_root(name,nd);
-       read_lock(&current->fs->lock);
-@@ -777,7 +860,8 @@ int path_init(const char *name, unsigned
-  * needs parent already locked. Doesn't follow mounts.
-  * SMP-safe.
-  */
--struct dentry * lookup_hash(struct qstr *name, struct dentry * base)
-+struct dentry * lookup_hash_it(struct qstr *name, struct dentry * base,
-+                             struct lookup_intent *it)
- {
-       struct dentry * dentry;
-       struct inode *inode;
-@@ -800,13 +884,16 @@ struct dentry * lookup_hash(struct qstr 
-                       goto out;
-       }
--      dentry = cached_lookup(base, name, 0);
-+      dentry = cached_lookup(base, name, 0, it);
-       if (!dentry) {
-               struct dentry *new = d_alloc(base, name);
-               dentry = ERR_PTR(-ENOMEM);
-               if (!new)
-                       goto out;
-               lock_kernel();
-+              if (inode->i_op->lookup_it)
-+                      dentry = inode->i_op->lookup_it(inode, new, it, 0);
-+              else
-               dentry = inode->i_op->lookup(inode, new);
-               unlock_kernel();
-               if (!dentry)
-@@ -818,6 +905,12 @@ out:
-       return dentry;
- }
-+struct dentry * lookup_hash(struct qstr *name, struct dentry * base)
-+{
-+      return lookup_hash_it(name, base, NULL);
-+}
-+
-+
- /* SMP-safe */
- struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
- {
-@@ -839,7 +932,7 @@ struct dentry * lookup_one_len(const cha
-       }
-       this.hash = end_name_hash(hash);
--      return lookup_hash(&this, base);
-+      return lookup_hash_it(&this, base, NULL);
- access:
-       return ERR_PTR(-EACCES);
- }
-@@ -870,6 +963,23 @@ int __user_walk(const char *name, unsign
-       return err;
- }
-+int __user_walk_it(const char *name, unsigned flags, struct nameidata *nd,
-+                 struct lookup_intent *it)
-+{
-+      char *tmp;
-+      int err;
-+
-+      tmp = getname(name);
-+      err = PTR_ERR(tmp);
-+      if (!IS_ERR(tmp)) {
-+              err = 0;
-+              if (path_init(tmp, flags, nd))
-+                      err = path_walk_it(tmp, nd, it);
-+              putname(tmp);
-+      }
-+      return err;
-+}
-+
- /*
-  * It's inline, so penalty for filesystems that don't use sticky bit is
-  * minimal.
-@@ -967,7 +1077,8 @@ static inline int lookup_flags(unsigned 
-       return retval;
- }
--int vfs_create(struct inode *dir, struct dentry *dentry, int mode)
-+static int vfs_create_it(struct inode *dir, struct dentry *dentry, int mode,
-+                       struct lookup_intent *it)
- {
-       int error;
-@@ -980,12 +1091,15 @@ int vfs_create(struct inode *dir, struct
-               goto exit_lock;
-       error = -EACCES;        /* shouldn't it be ENOSYS? */
--      if (!dir->i_op || !dir->i_op->create)
-+      if (!dir->i_op || (!dir->i_op->create && !dir->i_op->create_it))
-               goto exit_lock;
-       DQUOT_INIT(dir);
-       lock_kernel();
--      error = dir->i_op->create(dir, dentry, mode);
-+      if (dir->i_op->create_it)
-+              error = dir->i_op->create_it(dir, dentry, mode, it);
-+      else
-+              error = dir->i_op->create(dir, dentry, mode);
-       unlock_kernel();
- exit_lock:
-       up(&dir->i_zombie);
-@@ -994,6 +1108,11 @@ exit_lock:
-       return error;
- }
-+int vfs_create(struct inode *dir, struct dentry *dentry, int mode)
-+{
-+      return vfs_create_it(dir, dentry, mode, NULL);
-+}
-+
- /*
-  *    open_namei()
-  *
-@@ -1008,7 +1127,8 @@ exit_lock:
-  * for symlinks (where the permissions are checked later).
-  * SMP-safe
-  */
--int open_namei(const char * pathname, int flag, int mode, struct nameidata *nd)
-+int open_namei_it(const char *pathname, int flag, int mode,
-+                struct nameidata *nd, struct lookup_intent *it)
- {
-       int acc_mode, error = 0;
-       struct inode *inode;
-@@ -1018,11 +1138,14 @@ int open_namei(const char * pathname, in
-       acc_mode = ACC_MODE(flag);
-+      if (it)
-+              it->it_flags = flag;
-+
-       /*
-        * The simplest case - just a plain lookup.
-        */
-       if (!(flag & O_CREAT)) {
--              error = path_lookup(pathname, lookup_flags(flag), nd);
-+              error = path_lookup_it(pathname, lookup_flags(flag), nd, it);
-               if (error)
-                       return error;
-               dentry = nd->dentry;
-@@ -1032,6 +1155,10 @@ int open_namei(const char * pathname, in
-       /*
-        * Create - we need to know the parent.
-        */
-+      if (it) {
-+              it->it_create_mode = mode;
-+              it->it_op |= IT_CREAT;
-+      }
-       error = path_lookup(pathname, LOOKUP_PARENT, nd);
-       if (error)
-               return error;
-@@ -1047,7 +1174,7 @@ int open_namei(const char * pathname, in
-       dir = nd->dentry;
-       down(&dir->d_inode->i_sem);
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
- do_last:
-       error = PTR_ERR(dentry);
-@@ -1056,11 +1183,12 @@ do_last:
-               goto exit;
-       }
-+      it->it_create_mode = mode;
-       /* Negative dentry, just create the file */
-       if (!dentry->d_inode) {
-               if (!IS_POSIXACL(dir->d_inode))
-                       mode &= ~current->fs->umask;
--              error = vfs_create(dir->d_inode, dentry, mode);
-+              error = vfs_create_it(dir->d_inode, dentry, mode, it);
-               up(&dir->d_inode->i_sem);
-               dput(nd->dentry);
-               nd->dentry = dentry;
-@@ -1164,7 +1292,7 @@ ok:
-               if (!error) {
-                       DQUOT_INIT(inode);
-                       
--                      error = do_truncate(dentry, 0);
-+                      error = do_truncate(dentry, 0, 1);
-               }
-               put_write_access(inode);
-               if (error)
-@@ -1176,8 +1304,10 @@ ok:
-       return 0;
- exit_dput:
-+      intent_release(it);
-       dput(dentry);
- exit:
-+      intent_release(it);
-       path_release(nd);
-       return error;
-@@ -1196,7 +1326,10 @@ do_link:
-        * are done. Procfs-like symlinks just set LAST_BIND.
-        */
-       UPDATE_ATIME(dentry->d_inode);
-+      nd->intent = it;
-       error = dentry->d_inode->i_op->follow_link(dentry, nd);
-+      if (error)
-+              intent_release(it);
-       dput(dentry);
-       if (error)
-               return error;
-@@ -1218,13 +1351,20 @@ do_link:
-       }
-       dir = nd->dentry;
-       down(&dir->d_inode->i_sem);
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
-       putname(nd->last.name);
-       goto do_last;
- }
-+int open_namei(const char *pathname, int flag, int mode, struct nameidata *nd)
-+{
-+      return open_namei_it(pathname, flag, mode, nd, NULL);
-+}
-+
-+
- /* SMP-safe */
--static struct dentry *lookup_create(struct nameidata *nd, int is_dir)
-+static struct dentry *lookup_create(struct nameidata *nd, int is_dir,
-+                                  struct lookup_intent *it)
- {
-       struct dentry *dentry;
-@@ -1232,7 +1372,7 @@ static struct dentry *lookup_create(stru
-       dentry = ERR_PTR(-EEXIST);
-       if (nd->last_type != LAST_NORM)
-               goto fail;
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
-       if (IS_ERR(dentry))
-               goto fail;
-       if (!is_dir && nd->last.name[nd->last.len] && !dentry->d_inode)
-@@ -1288,7 +1428,20 @@ asmlinkage long sys_mknod(const char * f
-       error = path_lookup(tmp, LOOKUP_PARENT, &nd);
-       if (error)
-               goto out;
--      dentry = lookup_create(&nd, 0);
-+
-+      if (nd.last_type != LAST_NORM) {
-+              error = -EEXIST;
-+              goto out2;
-+      }
-+      if (nd.dentry->d_inode->i_op->mknod_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+              error = op->mknod_raw(&nd, mode, dev);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto out2;
-+      }
-+
-+      dentry = lookup_create(&nd, 0, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_POSIXACL(nd.dentry->d_inode))
-@@ -1310,6 +1463,7 @@ asmlinkage long sys_mknod(const char * f
-               dput(dentry);
-       }
-       up(&nd.dentry->d_inode->i_sem);
-+out2:
-       path_release(&nd);
- out:
-       putname(tmp);
-@@ -1357,7 +1511,18 @@ asmlinkage long sys_mkdir(const char * p
-               error = path_lookup(tmp, LOOKUP_PARENT, &nd);
-               if (error)
-                       goto out;
--              dentry = lookup_create(&nd, 1);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out2;
-+              }
-+              if (nd.dentry->d_inode->i_op->mkdir_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->mkdir_raw(&nd, mode);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out2;
-+              }
-+              dentry = lookup_create(&nd, 1, NULL);
-               error = PTR_ERR(dentry);
-               if (!IS_ERR(dentry)) {
-                       if (!IS_POSIXACL(nd.dentry->d_inode))
-@@ -1366,6 +1531,7 @@ asmlinkage long sys_mkdir(const char * p
-                       dput(dentry);
-               }
-               up(&nd.dentry->d_inode->i_sem);
-+out2:
-               path_release(&nd);
- out:
-               putname(tmp);
-@@ -1466,8 +1632,16 @@ asmlinkage long sys_rmdir(const char * p
-                       error = -EBUSY;
-                       goto exit1;
-       }
-+      if (nd.dentry->d_inode->i_op->rmdir_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              error = op->rmdir_raw(&nd);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit1;
-+      }
-       down(&nd.dentry->d_inode->i_sem);
--      dentry = lookup_hash(&nd.last, nd.dentry);
-+      dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-               error = vfs_rmdir(nd.dentry->d_inode, dentry);
-@@ -1525,8 +1699,15 @@ asmlinkage long sys_unlink(const char * 
-       error = -EISDIR;
-       if (nd.last_type != LAST_NORM)
-               goto exit1;
-+      if (nd.dentry->d_inode->i_op->unlink_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+              error = op->unlink_raw(&nd);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit1;
-+      }
-       down(&nd.dentry->d_inode->i_sem);
--      dentry = lookup_hash(&nd.last, nd.dentry);
-+      dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-               /* Why not before? Because we want correct error value */
-@@ -1593,15 +1774,27 @@ asmlinkage long sys_symlink(const char *
-               error = path_lookup(to, LOOKUP_PARENT, &nd);
-               if (error)
-                       goto out;
--              dentry = lookup_create(&nd, 0);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out2;
-+              }
-+              if (nd.dentry->d_inode->i_op->symlink_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->symlink_raw(&nd, from);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out2;
-+              }
-+              dentry = lookup_create(&nd, 0, NULL);
-               error = PTR_ERR(dentry);
-               if (!IS_ERR(dentry)) {
-                       error = vfs_symlink(nd.dentry->d_inode, dentry, from);
-                       dput(dentry);
-               }
-               up(&nd.dentry->d_inode->i_sem);
-+      out2:
-               path_release(&nd);
--out:
-+      out:
-               putname(to);
-       }
-       putname(from);
-@@ -1677,7 +1870,18 @@ asmlinkage long sys_link(const char * ol
-               error = -EXDEV;
-               if (old_nd.mnt != nd.mnt)
-                       goto out_release;
--              new_dentry = lookup_create(&nd, 0);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out_release;
-+              }
-+              if (nd.dentry->d_inode->i_op->link_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->link_raw(&old_nd, &nd);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out_release;
-+              }
-+              new_dentry = lookup_create(&nd, 0, NULL);
-               error = PTR_ERR(new_dentry);
-               if (!IS_ERR(new_dentry)) {
-                       error = vfs_link(old_nd.dentry, nd.dentry->d_inode, new_dentry);
-@@ -1721,7 +1925,7 @@ exit:
-  *       locking].
-  */
- int vfs_rename_dir(struct inode *old_dir, struct dentry *old_dentry,
--             struct inode *new_dir, struct dentry *new_dentry)
-+                 struct inode *new_dir, struct dentry *new_dentry)
- {
-       int error;
-       struct inode *target;
-@@ -1800,7 +2004,7 @@ out_unlock:
- }
- int vfs_rename_other(struct inode *old_dir, struct dentry *old_dentry,
--             struct inode *new_dir, struct dentry *new_dentry)
-+                   struct inode *new_dir, struct dentry *new_dentry)
- {
-       int error;
-@@ -1888,9 +2092,18 @@ static inline int do_rename(const char *
-       if (newnd.last_type != LAST_NORM)
-               goto exit2;
-+      if (old_dir->d_inode->i_op->rename_raw) {
-+              lock_kernel();
-+              error = old_dir->d_inode->i_op->rename_raw(&oldnd, &newnd);
-+              unlock_kernel();
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit2;
-+      }
-+
-       double_lock(new_dir, old_dir);
--      old_dentry = lookup_hash(&oldnd.last, old_dir);
-+      old_dentry = lookup_hash_it(&oldnd.last, old_dir, NULL);
-       error = PTR_ERR(old_dentry);
-       if (IS_ERR(old_dentry))
-               goto exit3;
-@@ -1906,16 +2119,16 @@ static inline int do_rename(const char *
-               if (newnd.last.name[newnd.last.len])
-                       goto exit4;
-       }
--      new_dentry = lookup_hash(&newnd.last, new_dir);
-+      new_dentry = lookup_hash_it(&newnd.last, new_dir, NULL);
-       error = PTR_ERR(new_dentry);
-       if (IS_ERR(new_dentry))
-               goto exit4;
-+
-       lock_kernel();
-       error = vfs_rename(old_dir->d_inode, old_dentry,
-                                  new_dir->d_inode, new_dentry);
-       unlock_kernel();
--
-       dput(new_dentry);
- exit4:
-       dput(old_dentry);
-@@ -1966,20 +2179,26 @@ out:
- }
- static inline int
--__vfs_follow_link(struct nameidata *nd, const char *link)
-+__vfs_follow_link(struct nameidata *nd, const char *link,
-+                struct lookup_intent *it)
- {
-       int res = 0;
-       char *name;
-       if (IS_ERR(link))
-               goto fail;
-+      if (it == NULL)
-+              it = nd->intent;
-+      else if (it != nd->intent)
-+              printk("it != nd->intent: tell phil@clusterfs.com\n");
-+
-       if (*link == '/') {
-               path_release(nd);
-               if (!walk_init_root(link, nd))
-                       /* weird __emul_prefix() stuff did it */
-                       goto out;
-       }
--      res = link_path_walk(link, nd);
-+      res = link_path_walk_it(link, nd, it);
- out:
-       if (current->link_count || res || nd->last_type!=LAST_NORM)
-               return res;
-@@ -2003,7 +2222,13 @@ fail:
- int vfs_follow_link(struct nameidata *nd, const char *link)
- {
--      return __vfs_follow_link(nd, link);
-+      return __vfs_follow_link(nd, link, NULL);
-+}
-+
-+int vfs_follow_link_it(struct nameidata *nd, const char *link,
-+                     struct lookup_intent *it)
-+{
-+      return __vfs_follow_link(nd, link, it);
- }
- /* get the link contents into pagecache */
-@@ -2045,7 +2270,7 @@ int page_follow_link(struct dentry *dent
- {
-       struct page *page = NULL;
-       char *s = page_getlink(dentry, &page);
--      int res = __vfs_follow_link(nd, s);
-+      int res = __vfs_follow_link(nd, s, NULL);
-       if (page) {
-               kunmap(page);
-               page_cache_release(page);
-Index: linux-ia64/fs/namespace.c
-===================================================================
---- linux-ia64.orig/fs/namespace.c     2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/fs/namespace.c  2004-03-17 16:05:28.000000000 -0800
-@@ -98,6 +98,7 @@ static void detach_mnt(struct vfsmount *
- {
-       old_nd->dentry = mnt->mnt_mountpoint;
-       old_nd->mnt = mnt->mnt_parent;
-+      UNPIN(old_nd->dentry, old_nd->mnt, 1);
-       mnt->mnt_parent = mnt;
-       mnt->mnt_mountpoint = mnt->mnt_root;
-       list_del_init(&mnt->mnt_child);
-@@ -109,6 +110,7 @@ static void attach_mnt(struct vfsmount *
- {
-       mnt->mnt_parent = mntget(nd->mnt);
-       mnt->mnt_mountpoint = dget(nd->dentry);
-+      PIN(nd->dentry, nd->mnt, 1);
-       list_add(&mnt->mnt_hash, mount_hashtable+hash(nd->mnt, nd->dentry));
-       list_add(&mnt->mnt_child, &nd->mnt->mnt_mounts);
-       nd->dentry->d_mounted++;
-@@ -488,14 +490,17 @@ static int do_loopback(struct nameidata 
- {
-       struct nameidata old_nd;
-       struct vfsmount *mnt = NULL;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int err = mount_is_safe(nd);
-       if (err)
-               return err;
-       if (!old_name || !*old_name)
-               return -EINVAL;
--      err = path_lookup(old_name, LOOKUP_POSITIVE|LOOKUP_FOLLOW, &old_nd);
--      if (err)
-+      err = path_lookup_it(old_name, LOOKUP_POSITIVE|LOOKUP_FOLLOW, &old_nd, &it);
-+      if (err) {
-+              intent_release(&it);
-               return err;
-+      }
-       down_write(&current->namespace->sem);
-       err = -EINVAL;
-@@ -518,6 +523,7 @@ static int do_loopback(struct nameidata 
-       }
-       up_write(&current->namespace->sem);
-+      intent_release(&it);
-       path_release(&old_nd);
-       return err;
- }
-@@ -701,6 +707,7 @@ long do_mount(char * dev_name, char * di
-                 unsigned long flags, void *data_page)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int retval = 0;
-       int mnt_flags = 0;
-@@ -725,10 +732,11 @@ long do_mount(char * dev_name, char * di
-       flags &= ~(MS_NOSUID|MS_NOEXEC|MS_NODEV);
-       /* ... and get the mountpoint */
--      retval = path_lookup(dir_name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd);
--      if (retval)
-+      retval = path_lookup_it(dir_name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd, &it);
-+      if (retval) {
-+              intent_release(&it);
-               return retval;
--
-+      }
-       if (flags & MS_REMOUNT)
-               retval = do_remount(&nd, flags & ~MS_REMOUNT, mnt_flags,
-                                   data_page);
-@@ -739,6 +747,8 @@ long do_mount(char * dev_name, char * di
-       else
-               retval = do_add_mount(&nd, type_page, flags, mnt_flags,
-                                     dev_name, data_page);
-+
-+      intent_release(&it);
-       path_release(&nd);
-       return retval;
- }
-@@ -904,6 +914,8 @@ asmlinkage long sys_pivot_root(const cha
- {
-       struct vfsmount *tmp;
-       struct nameidata new_nd, old_nd, parent_nd, root_parent, user_nd;
-+      struct lookup_intent new_it = { .it_op = IT_GETATTR };
-+      struct lookup_intent old_it = { .it_op = IT_GETATTR };
-       int error;
-       if (!capable(CAP_SYS_ADMIN))
-@@ -911,14 +923,14 @@ asmlinkage long sys_pivot_root(const cha
-       lock_kernel();
--      error = __user_walk(new_root, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &new_nd);
-+      error = __user_walk_it(new_root, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &new_nd, &new_it);
-       if (error)
-               goto out0;
-       error = -EINVAL;
-       if (!check_mnt(new_nd.mnt))
-               goto out1;
--      error = __user_walk(put_old, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &old_nd);
-+      error = __user_walk_it(put_old, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &old_nd, &old_it);
-       if (error)
-               goto out1;
-@@ -973,8 +985,10 @@ out2:
-       up(&old_nd.dentry->d_inode->i_zombie);
-       up_write(&current->namespace->sem);
-       path_release(&user_nd);
-+      intent_release(&old_it);
-       path_release(&old_nd);
- out1:
-+      intent_release(&new_it);
-       path_release(&new_nd);
- out0:
-       unlock_kernel();
-Index: linux-ia64/fs/open.c
-===================================================================
---- linux-ia64.orig/fs/open.c  2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/fs/open.c       2004-03-17 16:05:28.000000000 -0800
-@@ -19,6 +19,8 @@
- #include <asm/uaccess.h>
- #define special_file(m) (S_ISCHR(m)||S_ISBLK(m)||S_ISFIFO(m)||S_ISSOCK(m))
-+extern int path_walk_it(const char *name, struct nameidata *nd,
-+                      struct lookup_intent *it);
- int vfs_statfs(struct super_block *sb, struct statfs *buf)
- {
-@@ -95,9 +97,10 @@ void fd_install(unsigned int fd, struct 
-       write_unlock(&files->file_lock);
- }
--int do_truncate(struct dentry *dentry, loff_t length)
-+int do_truncate(struct dentry *dentry, loff_t length, int called_from_open)
- {
-       struct inode *inode = dentry->d_inode;
-+      struct inode_operations *op = dentry->d_inode->i_op;
-       int error;
-       struct iattr newattrs;
-@@ -109,7 +112,13 @@ int do_truncate(struct dentry *dentry, l
-       down(&inode->i_sem);
-       newattrs.ia_size = length;
-       newattrs.ia_valid = ATTR_SIZE | ATTR_CTIME;
--      error = notify_change(dentry, &newattrs);
-+      if (called_from_open)
-+              newattrs.ia_valid |= ATTR_FROM_OPEN;
-+      if (op->setattr_raw) {
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+      } else
-+              error = notify_change(dentry, &newattrs);
-       up(&inode->i_sem);
-       up_write(&inode->i_alloc_sem);
-       return error;
-@@ -120,12 +129,13 @@ static inline long do_sys_truncate(const
-       struct nameidata nd;
-       struct inode * inode;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       error = -EINVAL;
-       if (length < 0) /* sorry, but loff_t says... */
-               goto out;
--      error = user_path_walk(path, &nd);
-+      error = user_path_walk_it(path, &nd, &it);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-@@ -165,11 +175,13 @@ static inline long do_sys_truncate(const
-       error = locks_verify_truncate(inode, NULL, length);
-       if (!error) {
-               DQUOT_INIT(inode);
--              error = do_truncate(nd.dentry, length);
-+              intent_release(&it);
-+              error = do_truncate(nd.dentry, length, 0);
-       }
-       put_write_access(inode);
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
-@@ -217,7 +229,7 @@ static inline long do_sys_ftruncate(unsi
-       error = locks_verify_truncate(inode, file, length);
-       if (!error)
--              error = do_truncate(dentry, length);
-+              error = do_truncate(dentry, length, 0);
- out_putf:
-       fput(file);
- out:
-@@ -262,11 +274,13 @@ asmlinkage long sys_utime(char * filenam
-       struct inode * inode;
-       struct iattr newattrs;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, NULL);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-+      /* this is safe without a Lustre lock because it only depends
-+         on the super block */
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto dput_and_out;
-@@ -281,11 +295,25 @@ asmlinkage long sys_utime(char * filenam
-                       goto dput_and_out;
-               newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET;
--      } else {
-+      }
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto dput_and_out;
-+      }
-+
-+      error = -EPERM;
-+      if (!times) {
-               if (current->fsuid != inode->i_uid &&
-                   (error = permission(inode,MAY_WRITE)) != 0)
-                       goto dput_and_out;
-       }
-+
-       error = notify_change(nd.dentry, &newattrs);
- dput_and_out:
-       path_release(&nd);
-@@ -306,12 +334,14 @@ asmlinkage long sys_utimes(char * filena
-       struct inode * inode;
-       struct iattr newattrs;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, NULL);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-+      /* this is safe without a Lustre lock because it only depends
-+         on the super block */
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto dput_and_out;
-@@ -326,7 +356,20 @@ asmlinkage long sys_utimes(char * filena
-               newattrs.ia_atime = times[0].tv_sec;
-               newattrs.ia_mtime = times[1].tv_sec;
-               newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET;
--      } else {
-+      }
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto dput_and_out;
-+      }
-+
-+      error = -EPERM;
-+      if (!utimes) {
-               if (current->fsuid != inode->i_uid &&
-                   (error = permission(inode,MAY_WRITE)) != 0)
-                       goto dput_and_out;
-@@ -349,6 +392,7 @@ asmlinkage long sys_access(const char * 
-       int old_fsuid, old_fsgid;
-       kernel_cap_t old_cap;
-       int res;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       if (mode & ~S_IRWXO)    /* where's F_OK, X_OK, W_OK, R_OK? */
-               return -EINVAL;
-@@ -366,13 +410,14 @@ asmlinkage long sys_access(const char * 
-       else
-               current->cap_effective = current->cap_permitted;
--      res = user_path_walk(filename, &nd);
-+      res = user_path_walk_it(filename, &nd, &it);
-       if (!res) {
-               res = permission(nd.dentry->d_inode, mode);
-               /* SuS v2 requires we report a read only fs too */
-               if(!res && (mode & S_IWOTH) && IS_RDONLY(nd.dentry->d_inode)
-                  && !special_file(nd.dentry->d_inode->i_mode))
-                       res = -EROFS;
-+              intent_release(&it);
-               path_release(&nd);
-       }
-@@ -387,8 +432,9 @@ asmlinkage long sys_chdir(const char * f
- {
-       int error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = __user_walk(filename,LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY,&nd);
-+      error = __user_walk_it(filename,LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY,&nd, &it);
-       if (error)
-               goto out;
-@@ -399,6 +445,7 @@ asmlinkage long sys_chdir(const char * f
-       set_fs_pwd(current->fs, nd.mnt, nd.dentry);
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
-@@ -438,9 +485,10 @@ asmlinkage long sys_chroot(const char * 
- {
-       int error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = __user_walk(filename, LOOKUP_POSITIVE | LOOKUP_FOLLOW |
--                    LOOKUP_DIRECTORY | LOOKUP_NOALT, &nd);
-+      error = __user_walk_it(filename, LOOKUP_POSITIVE | LOOKUP_FOLLOW |
-+                             LOOKUP_DIRECTORY | LOOKUP_NOALT, &nd, &it);
-       if (error)
-               goto out;
-@@ -456,39 +504,56 @@ asmlinkage long sys_chroot(const char * 
-       set_fs_altroot();
-       error = 0;
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
- }
--asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
-+int chmod_common(struct dentry *dentry, mode_t mode)
- {
--      struct inode * inode;
--      struct dentry * dentry;
--      struct file * file;
--      int err = -EBADF;
-+      struct inode *inode = dentry->d_inode;
-       struct iattr newattrs;
-+      int err = -EROFS;
--      file = fget(fd);
--      if (!file)
-+      if (IS_RDONLY(inode))
-               goto out;
--      dentry = file->f_dentry;
--      inode = dentry->d_inode;
-+      if (inode->i_op->setattr_raw) {
-+              newattrs.ia_mode = mode;
-+              newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
-+              newattrs.ia_valid |= ATTR_RAW;
-+              err = inode->i_op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (err != -EOPNOTSUPP)
-+                      goto out;
-+      }
--      err = -EROFS;
--      if (IS_RDONLY(inode))
--              goto out_putf;
-       err = -EPERM;
-       if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
--              goto out_putf;
-+              goto out;
-+
-       if (mode == (mode_t) -1)
-               mode = inode->i_mode;
-       newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
-       newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
-       err = notify_change(dentry, &newattrs);
--out_putf:
-+out:
-+      return err;
-+}
-+
-+asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
-+{
-+      struct file * file;
-+      int err = -EBADF;
-+
-+      file = fget(fd);
-+      if (!file)
-+              goto out;
-+
-+      err = chmod_common(file->f_dentry, mode);
-+
-       fput(file);
- out:
-       return err;
-@@ -497,30 +562,14 @@ out:
- asmlinkage long sys_chmod(const char * filename, mode_t mode)
- {
-       struct nameidata nd;
--      struct inode * inode;
-       int error;
--      struct iattr newattrs;
-       error = user_path_walk(filename, &nd);
-       if (error)
-               goto out;
--      inode = nd.dentry->d_inode;
--
--      error = -EROFS;
--      if (IS_RDONLY(inode))
--              goto dput_and_out;
--      error = -EPERM;
--      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
--              goto dput_and_out;
-+      error = chmod_common(nd.dentry, mode);
--      if (mode == (mode_t) -1)
--              mode = inode->i_mode;
--      newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
--      newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
--      error = notify_change(nd.dentry, &newattrs);
--
--dput_and_out:
-       path_release(&nd);
- out:
-       return error;
-@@ -540,6 +589,20 @@ static int chown_common(struct dentry * 
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto out;
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = dentry->d_inode->i_op;
-+
-+              newattrs.ia_uid = user;
-+              newattrs.ia_gid = group;
-+              newattrs.ia_valid = ATTR_UID | ATTR_GID | ATTR_CTIME;
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      return error;
-+      }
-+
-       error = -EPERM;
-       if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-               goto out;
-@@ -644,6 +707,7 @@ struct file *filp_open(const char * file
- {
-       int namei_flags, error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_OPEN };
-       namei_flags = flags;
-       if ((namei_flags+1) & O_ACCMODE)
-@@ -651,14 +715,15 @@ struct file *filp_open(const char * file
-       if (namei_flags & O_TRUNC)
-               namei_flags |= 2;
--      error = open_namei(filename, namei_flags, mode, &nd);
--      if (!error)
--              return dentry_open(nd.dentry, nd.mnt, flags);
-+      error = open_namei_it(filename, namei_flags, mode, &nd, &it);
-+      if (error)
-+              return ERR_PTR(error);
--      return ERR_PTR(error);
-+      return dentry_open_it(nd.dentry, nd.mnt, flags, &it);
- }
--struct file *dentry_open(struct dentry *dentry, struct vfsmount *mnt, int flags)
-+struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-+                          int flags, struct lookup_intent *it)
- {
-       struct file * f;
-       struct inode *inode;
-@@ -695,7 +760,9 @@ struct file *dentry_open(struct dentry *
-       }
-       if (f->f_op && f->f_op->open) {
-+              f->f_it = it;
-               error = f->f_op->open(inode,f);
-+              f->f_it = NULL;
-               if (error)
-                       goto cleanup_all;
-       }
-@@ -708,6 +775,7 @@ struct file *dentry_open(struct dentry *
-                                       inode->i_mapping->a_ops->direct_sector_IO)))
-               goto cleanup_all;
-+      intent_release(it);
-       return f;
- cleanup_all:
-@@ -722,11 +790,17 @@ cleanup_all:
- cleanup_file:
-       put_filp(f);
- cleanup_dentry:
-+      intent_release(it);
-       dput(dentry);
-       mntput(mnt);
-       return ERR_PTR(error);
- }
-+struct file *dentry_open(struct dentry *dentry, struct vfsmount *mnt, int flags)
-+{
-+      return dentry_open_it(dentry, mnt, flags, NULL);
-+}
-+
- /*
-  * Find an empty file descriptor entry, and mark it busy.
-  */
-Index: linux-ia64/fs/stat.c
-===================================================================
---- linux-ia64.orig/fs/stat.c  2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/fs/stat.c       2004-03-17 16:06:13.000000000 -0800
-@@ -17,10 +17,12 @@
-  * Revalidate the inode. This is required for proper NFS attribute caching.
-  */
- static __inline__ int
--do_revalidate(struct dentry *dentry)
-+do_revalidate(struct dentry *dentry, struct lookup_intent *it)
- {
-       struct inode * inode = dentry->d_inode;
--      if (inode->i_op && inode->i_op->revalidate)
-+      if (inode->i_op && inode->i_op->revalidate_it)
-+              return inode->i_op->revalidate_it(dentry, it);
-+      else if (inode->i_op && inode->i_op->revalidate)
-               return inode->i_op->revalidate(dentry);
-       return 0;
- }
-@@ -143,13 +145,15 @@ static int cp_new_stat(struct inode * in
- asmlinkage long sys_stat(char * filename, struct __old_kernel_stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_old_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -159,13 +163,15 @@ asmlinkage long sys_stat(char * filename
- asmlinkage long sys_newstat(char * filename, struct stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -180,13 +186,15 @@ asmlinkage long sys_newstat(char * filen
- asmlinkage long sys_lstat(char * filename, struct __old_kernel_stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk_link(filename, &nd);
-+      error = user_path_walk_link_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_old_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -197,13 +205,15 @@ asmlinkage long sys_lstat(char * filenam
- asmlinkage long sys_newlstat(char * filename, struct stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk_link(filename, &nd);
-+      error = user_path_walk_link_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -224,7 +234,7 @@ asmlinkage long sys_fstat(unsigned int f
-       if (f) {
-               struct dentry * dentry = f->f_dentry;
--              err = do_revalidate(dentry);
-+              err = do_revalidate(dentry, NULL);
-               if (!err)
-                       err = cp_old_stat(dentry->d_inode, statbuf);
-               fput(f);
-@@ -243,7 +253,7 @@ asmlinkage long sys_newfstat(unsigned in
-       if (f) {
-               struct dentry * dentry = f->f_dentry;
--              err = do_revalidate(dentry);
-+              err = do_revalidate(dentry, NULL);
-               if (!err)
-                       err = cp_new_stat(dentry->d_inode, statbuf);
-               fput(f);
-@@ -265,7 +275,7 @@ asmlinkage long sys_readlink(const char 
-               error = -EINVAL;
-               if (inode->i_op && inode->i_op->readlink &&
--                  !(error = do_revalidate(nd.dentry))) {
-+                  !(error = do_revalidate(nd.dentry, NULL))) {
-                       UPDATE_ATIME(inode);
-                       error = inode->i_op->readlink(nd.dentry, buf, bufsiz);
-               }
-@@ -341,12 +351,14 @@ asmlinkage long sys_stat64(char * filena
- {
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat64(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -356,12 +368,14 @@ asmlinkage long sys_lstat64(char * filen
- {
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = user_path_walk_link(filename, &nd);
-+      error = user_path_walk_link_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat64(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -376,7 +390,7 @@ asmlinkage long sys_fstat64(unsigned lon
-       if (f) {
-               struct dentry * dentry = f->f_dentry;
--              err = do_revalidate(dentry);
-+              err = do_revalidate(dentry, NULL);
-               if (!err)
-                       err = cp_new_stat64(dentry->d_inode, statbuf);
-               fput(f);
-Index: linux-ia64/include/linux/dcache.h
-===================================================================
---- linux-ia64.orig/include/linux/dcache.h     2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/include/linux/dcache.h  2004-03-17 16:05:28.000000000 -0800
-@@ -6,6 +6,51 @@
- #include <asm/atomic.h>
- #include <linux/mount.h>
- #include <linux/kernel.h>
-+#include <linux/string.h>
-+
-+#define IT_OPEN     0x0001
-+#define IT_CREAT    0x0002
-+#define IT_READDIR  0x0004
-+#define IT_GETATTR  0x0008
-+#define IT_LOOKUP   0x0010
-+#define IT_UNLINK   0x0020
-+#define IT_GETXATTR 0x0040
-+#define IT_EXEC     0x0080
-+#define IT_PIN      0x0100
-+
-+#define IT_FL_LOCKED   0x0001
-+#define IT_FL_FOLLOWED 0x0002 /* set by vfs_follow_link */
-+
-+#define INTENT_MAGIC 0x19620323
-+
-+
-+struct lustre_intent_data {
-+      int       it_disposition;
-+      int       it_status;
-+      __u64     it_lock_handle;
-+      void     *it_data;
-+      int       it_lock_mode;
-+      int it_int_flags;
-+};
-+struct lookup_intent {
-+      int     it_magic;
-+      void    (*it_op_release)(struct lookup_intent *);
-+      int     it_op;
-+      int     it_flags;
-+      int     it_create_mode;
-+      union {
-+              struct lustre_intent_data lustre;
-+      } d;
-+};
-+
-+static inline void intent_init(struct lookup_intent *it, int op, int flags)
-+{
-+      memset(it, 0, sizeof(*it));
-+      it->it_magic = INTENT_MAGIC;
-+      it->it_op = op;
-+      it->it_flags = flags;
-+}
-+
- /*
-  * linux/include/linux/dcache.h
-@@ -96,8 +141,22 @@ struct dentry_operations {
-       int (*d_delete)(struct dentry *);
-       void (*d_release)(struct dentry *);
-       void (*d_iput)(struct dentry *, struct inode *);
-+      int (*d_revalidate_it)(struct dentry *, int, struct lookup_intent *);
-+      void (*d_pin)(struct dentry *, struct vfsmount * , int);
-+      void (*d_unpin)(struct dentry *, struct vfsmount *, int);
- };
-+#define PIN(de,mnt,flag)  if (de && de->d_op && de->d_op->d_pin) \
-+                              de->d_op->d_pin(de, mnt, flag);
-+#define UNPIN(de,mnt,flag)  if (de && de->d_op && de->d_op->d_unpin) \
-+                              de->d_op->d_unpin(de, mnt, flag);
-+
-+
-+/* defined in fs/namei.c */
-+extern void intent_release(struct lookup_intent *it);
-+/* defined in fs/dcache.c */
-+extern void __d_rehash(struct dentry * entry, int lock);
-+
- /* the dentry parameter passed to d_hash and d_compare is the parent
-  * directory of the entries to be compared. It is used in case these
-  * functions need any directory specific information for determining
-@@ -129,6 +188,7 @@ d_iput:            no              no              yes
-                                        * s_nfsd_free_path semaphore will be down
-                                        */
- #define DCACHE_REFERENCED     0x0008  /* Recently used, don't discard. */
-+#define DCACHE_LUSTRE_INVALID 0x0010  /* Lustre invalidated */
- extern spinlock_t dcache_lock;
-Index: linux-ia64/include/linux/fs.h
-===================================================================
---- linux-ia64.orig/include/linux/fs.h 2004-03-17 16:05:28.000000000 -0800
-+++ linux-ia64/include/linux/fs.h      2004-03-17 16:05:52.000000000 -0800
-@@ -73,6 +73,7 @@ extern int leases_enable, dir_notify_ena
- #define FMODE_READ 1
- #define FMODE_WRITE 2
-+#define FMODE_EXEC 4
- #define READ 0
- #define WRITE 1
-@@ -359,6 +360,9 @@ extern void set_bh_page(struct buffer_he
- #define ATTR_MTIME_SET        256
- #define ATTR_FORCE    512     /* Not a change, but a change it */
- #define ATTR_ATTR_FLAG        1024
-+#define ATTR_RAW      0x0800  /* file system, not vfs will massage attrs */
-+#define ATTR_FROM_OPEN        0x1000  /* called from open path, ie O_TRUNC */
-+#define ATTR_CTIME_SET        0x2000
- /*
-  * This is the Inode Attributes structure, used for notify_change().  It
-@@ -496,6 +500,7 @@ struct inode {
-       struct pipe_inode_info  *i_pipe;
-       struct block_device     *i_bdev;
-       struct char_device      *i_cdev;
-+      void                    *i_filterdata;
-       unsigned long           i_dnotify_mask; /* Directory notify events */
-       struct dnotify_struct   *i_dnotify; /* for directory notifications */
-@@ -598,6 +603,7 @@ struct file {
-       /* needed for tty driver, and maybe others */
-       void                    *private_data;
-+      struct lookup_intent    *f_it;
-       /* preallocated helper kiobuf to speedup O_DIRECT */
-       struct kiobuf           *f_iobuf;
-@@ -726,6 +732,7 @@ struct nameidata {
-       struct qstr last;
-       unsigned int flags;
-       int last_type;
-+      struct lookup_intent *intent;
- };
- /*
-@@ -846,7 +853,8 @@ extern int vfs_symlink(struct inode *, s
- extern int vfs_link(struct dentry *, struct inode *, struct dentry *);
- extern int vfs_rmdir(struct inode *, struct dentry *);
- extern int vfs_unlink(struct inode *, struct dentry *);
--extern int vfs_rename(struct inode *, struct dentry *, struct inode *, struct dentry *);
-+int vfs_rename(struct inode *old_dir, struct dentry *old_dentry,
-+             struct inode *new_dir, struct dentry *new_dentry);
- /*
-  * File types
-@@ -920,21 +928,32 @@ struct file_operations {
- struct inode_operations {
-       int (*create) (struct inode *,struct dentry *,int);
-+      int (*create_it) (struct inode *,struct dentry *,int, struct lookup_intent *);
-       struct dentry * (*lookup) (struct inode *,struct dentry *);
-+      struct dentry * (*lookup_it) (struct inode *,struct dentry *, struct lookup_intent *, int flags);
-       int (*link) (struct dentry *,struct inode *,struct dentry *);
-+      int (*link_raw) (struct nameidata *,struct nameidata *);
-       int (*unlink) (struct inode *,struct dentry *);
-+      int (*unlink_raw) (struct nameidata *);
-       int (*symlink) (struct inode *,struct dentry *,const char *);
-+      int (*symlink_raw) (struct nameidata *,const char *);
-       int (*mkdir) (struct inode *,struct dentry *,int);
-+      int (*mkdir_raw) (struct nameidata *,int);
-       int (*rmdir) (struct inode *,struct dentry *);
-+      int (*rmdir_raw) (struct nameidata *);
-       int (*mknod) (struct inode *,struct dentry *,int,int);
-+      int (*mknod_raw) (struct nameidata *,int,dev_t);
-       int (*rename) (struct inode *, struct dentry *,
-                       struct inode *, struct dentry *);
-+      int (*rename_raw) (struct nameidata *, struct nameidata *);
-       int (*readlink) (struct dentry *, char *,int);
-       int (*follow_link) (struct dentry *, struct nameidata *);
-       void (*truncate) (struct inode *);
-       int (*permission) (struct inode *, int);
-       int (*revalidate) (struct dentry *);
-+      int (*revalidate_it) (struct dentry *, struct lookup_intent *);
-       int (*setattr) (struct dentry *, struct iattr *);
-+      int (*setattr_raw) (struct inode *, struct iattr *);
-       int (*getattr) (struct dentry *, struct iattr *);
-       int (*setxattr) (struct dentry *, const char *, const void *, size_t, int);
-       ssize_t (*getxattr) (struct dentry *, const char *, void *, size_t);
-@@ -1131,10 +1150,14 @@ static inline int get_lease(struct inode
- asmlinkage long sys_open(const char *, int, int);
- asmlinkage long sys_close(unsigned int);      /* yes, it's really unsigned */
--extern int do_truncate(struct dentry *, loff_t start);
-+extern int do_truncate(struct dentry *, loff_t start, int called_from_open);
- extern struct file *filp_open(const char *, int, int);
- extern struct file * dentry_open(struct dentry *, struct vfsmount *, int);
-+extern int open_namei_it(const char *filename, int namei_flags, int mode,
-+                       struct nameidata *nd, struct lookup_intent *it);
-+extern struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-+                          int flags, struct lookup_intent *it);
- extern int filp_close(struct file *, fl_owner_t id);
- extern char * getname(const char *);
-@@ -1425,6 +1448,7 @@ typedef int (*read_actor_t)(read_descrip
- extern loff_t default_llseek(struct file *file, loff_t offset, int origin);
- extern int FASTCALL(__user_walk(const char *, unsigned, struct nameidata *));
-+extern int FASTCALL(__user_walk_it(const char *, unsigned, struct nameidata *, struct lookup_intent *it));
- extern int FASTCALL(path_init(const char *, unsigned, struct nameidata *));
- extern int FASTCALL(path_walk(const char *, struct nameidata *));
- extern int FASTCALL(path_lookup(const char *, unsigned, struct nameidata *));
-@@ -1436,6 +1460,8 @@ extern struct dentry * lookup_one_len(co
- extern struct dentry * lookup_hash(struct qstr *, struct dentry *);
- #define user_path_walk(name,nd)        __user_walk(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd)
- #define user_path_walk_link(name,nd) __user_walk(name, LOOKUP_POSITIVE, nd)
-+#define user_path_walk_it(name,nd,it)  __user_walk_it(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd, it)
-+#define user_path_walk_link_it(name,nd,it) __user_walk_it(name, LOOKUP_POSITIVE, nd, it)
- extern void inode_init_once(struct inode *);
- extern void iput(struct inode *);
-@@ -1599,6 +1625,8 @@ extern struct file_operations generic_ro
- extern int vfs_readlink(struct dentry *, char *, int, const char *);
- extern int vfs_follow_link(struct nameidata *, const char *);
-+extern int vfs_follow_link_it(struct nameidata *, const char *,
-+                            struct lookup_intent *it);
- extern int page_readlink(struct dentry *, char *, int);
- extern int page_follow_link(struct dentry *, struct nameidata *);
- extern struct inode_operations page_symlink_inode_operations;
-Index: linux-ia64/include/linux/fs_struct.h
-===================================================================
---- linux-ia64.orig/include/linux/fs_struct.h  2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/include/linux/fs_struct.h       2004-03-17 16:05:28.000000000 -0800
-@@ -37,10 +37,12 @@ static inline void set_fs_root(struct fs
-       write_lock(&fs->lock);
-       old_root = fs->root;
-       old_rootmnt = fs->rootmnt;
-+      PIN(dentry, mnt, 1);
-       fs->rootmnt = mntget(mnt);
-       fs->root = dget(dentry);
-       write_unlock(&fs->lock);
-       if (old_root) {
-+              UNPIN(old_root, old_rootmnt, 1);
-               dput(old_root);
-               mntput(old_rootmnt);
-       }
-@@ -60,10 +62,12 @@ static inline void set_fs_pwd(struct fs_
-       write_lock(&fs->lock);
-       old_pwd = fs->pwd;
-       old_pwdmnt = fs->pwdmnt;
-+      PIN(dentry, mnt, 0);
-       fs->pwdmnt = mntget(mnt);
-       fs->pwd = dget(dentry);
-       write_unlock(&fs->lock);
-       if (old_pwd) {
-+              UNPIN(old_pwd, old_pwdmnt, 0);
-               dput(old_pwd);
-               mntput(old_pwdmnt);
-       }
-Index: linux-ia64/kernel/exit.c
-===================================================================
---- linux-ia64.orig/kernel/exit.c      2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/kernel/exit.c   2004-03-17 16:05:28.000000000 -0800
-@@ -347,11 +347,14 @@ static inline void __put_fs_struct(struc
- {
-       /* No need to hold fs->lock if we are killing it */
-       if (atomic_dec_and_test(&fs->count)) {
-+              UNPIN(fs->pwd, fs->pwdmnt, 0);
-+              UNPIN(fs->root, fs->rootmnt, 1);
-               dput(fs->root);
-               mntput(fs->rootmnt);
-               dput(fs->pwd);
-               mntput(fs->pwdmnt);
-               if (fs->altroot) {
-+                      UNPIN(fs->altroot, fs->altrootmnt, 1);
-                       dput(fs->altroot);
-                       mntput(fs->altrootmnt);
-               }
-Index: linux-ia64/kernel/fork.c
-===================================================================
---- linux-ia64.orig/kernel/fork.c      2004-03-17 15:47:15.000000000 -0800
-+++ linux-ia64/kernel/fork.c   2004-03-17 16:05:28.000000000 -0800
-@@ -463,10 +463,13 @@ static inline struct fs_struct *__copy_f
-               fs->umask = old->umask;
-               read_lock(&old->lock);
-               fs->rootmnt = mntget(old->rootmnt);
-+              PIN(old->pwd, old->pwdmnt, 0);
-+              PIN(old->root, old->rootmnt, 1);
-               fs->root = dget(old->root);
-               fs->pwdmnt = mntget(old->pwdmnt);
-               fs->pwd = dget(old->pwd);
-               if (old->altroot) {
-+                      PIN(old->altroot, old->altrootmnt, 1);
-                       fs->altrootmnt = mntget(old->altrootmnt);
-                       fs->altroot = dget(old->altroot);
-               } else {
-Index: linux-ia64/kernel/ksyms.c
-===================================================================
---- linux-ia64.orig/kernel/ksyms.c     2004-03-17 16:05:28.000000000 -0800
-+++ linux-ia64/kernel/ksyms.c  2004-03-17 16:05:51.000000000 -0800
-@@ -318,6 +318,7 @@ EXPORT_SYMBOL(read_cache_page);
- EXPORT_SYMBOL(set_page_dirty);
- EXPORT_SYMBOL(vfs_readlink);
- EXPORT_SYMBOL(vfs_follow_link);
-+EXPORT_SYMBOL(vfs_follow_link_it);
- EXPORT_SYMBOL(page_readlink);
- EXPORT_SYMBOL(page_follow_link);
- EXPORT_SYMBOL(page_symlink_inode_operations);
diff --git a/lustre/kernel_patches/patches/vfs_intent-2.4.22-rh.patch b/lustre/kernel_patches/patches/vfs_intent-2.4.22-rh.patch
deleted file mode 100644 (file)
index 2d75566..0000000
+++ /dev/null
@@ -1,1829 +0,0 @@
- fs/dcache.c               |   19 ++
- fs/exec.c                 |   17 +-
- fs/namei.c                |  295 +++++++++++++++++++++++++++++++++++++++-------
- fs/namespace.c            |   28 +++-
- fs/open.c                 |  172 +++++++++++++++++++-------
- fs/stat.c                 |   52 +++++---
- include/linux/dcache.h    |   60 +++++++++
- include/linux/fs.h        |   32 ++++
- include/linux/fs_struct.h |    4 
- kernel/exit.c             |    3 
- kernel/fork.c             |    3 
- kernel/ksyms.c            |    1 
- 12 files changed, 558 insertions(+), 128 deletions(-)
-
---- linux-2.4.22-ac1/fs/dcache.c~vfs_intent-2.4.22-rh  2003-09-25 14:16:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/dcache.c        2003-09-25 14:42:46.000000000 +0400
-@@ -181,6 +181,13 @@ int d_invalidate(struct dentry * dentry)
-               spin_unlock(&dcache_lock);
-               return 0;
-       }
-+
-+      /* network invalidation by Lustre */
-+      if (dentry->d_flags & DCACHE_LUSTRE_INVALID) {
-+              spin_unlock(&dcache_lock);
-+              return 0;
-+      }
-+
-       /*
-        * Check whether to do a partial shrink_dcache
-        * to get rid of unused child entries.
-@@ -833,13 +840,19 @@ void d_delete(struct dentry * dentry)
-  * Adds a dentry to the hash according to its name.
-  */
-  
--void d_rehash(struct dentry * entry)
-+void __d_rehash(struct dentry * entry, int lock)
- {
-       struct list_head *list = d_hash(entry->d_parent, entry->d_name.hash);
-       if (!list_empty(&entry->d_hash)) BUG();
--      spin_lock(&dcache_lock);
-+      if (lock) spin_lock(&dcache_lock);
-       list_add(&entry->d_hash, list);
--      spin_unlock(&dcache_lock);
-+      if (lock) spin_unlock(&dcache_lock);
-+}
-+EXPORT_SYMBOL(__d_rehash);
-+
-+void d_rehash(struct dentry * entry)
-+{
-+      __d_rehash(entry, 1);
- }
- #define do_switch(x,y) do { \
---- linux-2.4.22-ac1/fs/exec.c~vfs_intent-2.4.22-rh    2003-09-25 14:16:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/exec.c  2003-09-25 14:42:46.000000000 +0400
-@@ -115,8 +115,10 @@ asmlinkage long sys_uselib(const char * 
-       struct file * file;
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_OPEN,
-+                                  .it_flags = FMODE_READ|FMODE_EXEC };
--      error = user_path_walk(library, &nd);
-+      error = user_path_walk_it(library, &nd, &it);
-       if (error)
-               goto out;
-@@ -128,7 +130,8 @@ asmlinkage long sys_uselib(const char * 
-       if (error)
-               goto exit;
--      file = dentry_open(nd.dentry, nd.mnt, O_RDONLY);
-+      file = dentry_open_it(nd.dentry, nd.mnt, O_RDONLY, &it);
-+      intent_release(&it);
-       error = PTR_ERR(file);
-       if (IS_ERR(file))
-               goto out;
-@@ -390,8 +393,10 @@ struct file *open_exec(const char *name)
-       struct inode *inode;
-       struct file *file;
-       int err = 0;
-+      struct lookup_intent it = { .it_op = IT_OPEN,
-+                                  .it_flags = FMODE_READ|FMODE_EXEC };
--      err = path_lookup(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd);
-+      err = path_lookup_it(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd, &it);
-       file = ERR_PTR(err);
-       if (!err) {
-               inode = nd.dentry->d_inode;
-@@ -403,7 +408,8 @@ struct file *open_exec(const char *name)
-                               err = -EACCES;
-                       file = ERR_PTR(err);
-                       if (!err) {
--                              file = dentry_open(nd.dentry, nd.mnt, O_RDONLY);
-+                              file = dentry_open_it(nd.dentry, nd.mnt, O_RDONLY, &it);
-+                              intent_release(&it);
-                               if (!IS_ERR(file)) {
-                                       err = deny_write_access(file);
-                                       if (err) {
-@@ -415,6 +421,7 @@ out:
-                               return file;
-                       }
-               }
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       goto out;
-@@ -1322,7 +1329,7 @@ int do_coredump(long signr, int exit_cod
-               goto close_fail;
-       if (!file->f_op->write)
-               goto close_fail;
--      if (do_truncate(file->f_dentry, 0) != 0)
-+      if (do_truncate(file->f_dentry, 0, 0) != 0)
-               goto close_fail;
-       retval = binfmt->core_dump(signr, regs, file);
---- linux-2.4.22-ac1/fs/namei.c~vfs_intent-2.4.22-rh   2003-09-25 14:16:23.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/namei.c 2003-09-25 14:44:40.000000000 +0400
-@@ -94,6 +94,13 @@
-  * XEmacs seems to be relying on it...
-  */
-+void intent_release(struct lookup_intent *it)
-+{
-+      if (it && it->it_op_release)
-+              it->it_op_release(it);
-+
-+}
-+
- /* In order to reduce some races, while at the same time doing additional
-  * checking and hopefully speeding things up, we copy filenames to the
-  * kernel data space before using them..
-@@ -260,10 +267,19 @@ void path_release(struct nameidata *nd)
-  * Internal lookup() using the new generic dcache.
-  * SMP-safe
-  */
--static struct dentry * cached_lookup(struct dentry * parent, struct qstr * name, int flags)
-+static struct dentry *cached_lookup(struct dentry *parent, struct qstr *name,
-+                                  int flags, struct lookup_intent *it)
- {
-       struct dentry * dentry = d_lookup(parent, name);
-+      if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+              if (!dentry->d_op->d_revalidate_it(dentry, flags, it) &&
-+                  !d_invalidate(dentry)) {
-+                      dput(dentry);
-+                      dentry = NULL;
-+              }
-+              return dentry;
-+      } else
-       if (dentry && dentry->d_op && dentry->d_op->d_revalidate) {
-               if (!dentry->d_op->d_revalidate(dentry, flags) && !d_invalidate(dentry)) {
-                       dput(dentry);
-@@ -281,11 +297,15 @@ static struct dentry * cached_lookup(str
-  * make sure that nobody added the entry to the dcache in the meantime..
-  * SMP-safe
-  */
--static struct dentry * real_lookup(struct dentry * parent, struct qstr * name, int flags)
-+static struct dentry *real_lookup(struct dentry *parent, struct qstr *name,
-+                                int flags, struct lookup_intent *it)
- {
-       struct dentry * result;
-       struct inode *dir = parent->d_inode;
-+      int counter = 0;
-+again:
-+      counter++;
-       down(&dir->i_sem);
-       /*
-        * First re-do the cached lookup just in case it was created
-@@ -300,6 +320,9 @@ static struct dentry * real_lookup(struc
-               result = ERR_PTR(-ENOMEM);
-               if (dentry) {
-                       lock_kernel();
-+                      if (dir->i_op->lookup_it)
-+                              result = dir->i_op->lookup_it(dir, dentry, it, flags);
-+                      else
-                       result = dir->i_op->lookup(dir, dentry);
-                       unlock_kernel();
-                       if (result)
-@@ -321,6 +344,15 @@ static struct dentry * real_lookup(struc
-                       dput(result);
-                       result = ERR_PTR(-ENOENT);
-               }
-+      } else if (result->d_op && result->d_op->d_revalidate_it) {
-+              if (!result->d_op->d_revalidate_it(result, flags, it) &&
-+                  !d_invalidate(result)) {
-+                      dput(result);
-+                      if (counter > 10)
-+                              result = ERR_PTR(-ESTALE);
-+                      if (!IS_ERR(result))
-+                              goto again;
-+              }
-       }
-       return result;
- }
-@@ -332,7 +364,8 @@ static struct dentry * real_lookup(struc
-  * Without that kind of total limit, nasty chains of consecutive
-  * symlinks can cause almost arbitrarily long lookups. 
-  */
--static inline int do_follow_link(struct dentry *dentry, struct nameidata *nd)
-+static inline int do_follow_link(struct dentry *dentry, struct nameidata *nd,
-+                               struct lookup_intent *it)
- {
-       int err;
-       if (current->link_count >= 5)
-@@ -346,10 +379,12 @@ static inline int do_follow_link(struct 
-       current->link_count++;
-       current->total_link_count++;
-       UPDATE_ATIME(dentry->d_inode);
-+      nd->intent = it;
-       err = dentry->d_inode->i_op->follow_link(dentry, nd);
-       current->link_count--;
-       return err;
- loop:
-+      intent_release(it);
-       path_release(nd);
-       return -ELOOP;
- }
-@@ -447,7 +482,8 @@ static inline void follow_dotdot(struct 
-  *
-  * We expect 'base' to be positive and a directory.
-  */
--int link_path_walk(const char * name, struct nameidata *nd)
-+int link_path_walk_it(const char *name, struct nameidata *nd,
-+                    struct lookup_intent *it)
- {
-       struct dentry *dentry;
-       struct inode *inode;
-@@ -520,9 +556,9 @@ int link_path_walk(const char * name, st
-                               break;
-               }
-               /* This does the actual lookups.. */
--              dentry = cached_lookup(nd->dentry, &this, LOOKUP_CONTINUE);
-+              dentry = cached_lookup(nd->dentry, &this, LOOKUP_CONTINUE, NULL);
-               if (!dentry) {
--                      dentry = real_lookup(nd->dentry, &this, LOOKUP_CONTINUE);
-+                      dentry = real_lookup(nd->dentry, &this, LOOKUP_CONTINUE, NULL);
-                       err = PTR_ERR(dentry);
-                       if (IS_ERR(dentry))
-                               break;
-@@ -540,7 +576,7 @@ int link_path_walk(const char * name, st
-                       goto out_dput;
-               if (inode->i_op->follow_link) {
--                      err = do_follow_link(dentry, nd);
-+                      err = do_follow_link(dentry, nd, NULL);
-                       dput(dentry);
-                       if (err)
-                               goto return_err;
-@@ -556,7 +592,7 @@ int link_path_walk(const char * name, st
-                       nd->dentry = dentry;
-               }
-               err = -ENOTDIR; 
--              if (!inode->i_op->lookup)
-+              if (!inode->i_op->lookup && !inode->i_op->lookup_it)
-                       break;
-               continue;
-               /* here ends the main loop */
-@@ -583,9 +619,9 @@ last_component:
-                       if (err < 0)
-                               break;
-               }
--              dentry = cached_lookup(nd->dentry, &this, 0);
-+              dentry = cached_lookup(nd->dentry, &this, 0, it);
-               if (!dentry) {
--                      dentry = real_lookup(nd->dentry, &this, 0);
-+                      dentry = real_lookup(nd->dentry, &this, 0, it);
-                       err = PTR_ERR(dentry);
-                       if (IS_ERR(dentry))
-                               break;
-@@ -595,7 +631,7 @@ last_component:
-               inode = dentry->d_inode;
-               if ((lookup_flags & LOOKUP_FOLLOW)
-                   && inode && inode->i_op && inode->i_op->follow_link) {
--                      err = do_follow_link(dentry, nd);
-+                      err = do_follow_link(dentry, nd, it);
-                       dput(dentry);
-                       if (err)
-                               goto return_err;
-@@ -609,7 +645,8 @@ last_component:
-                       goto no_inode;
-               if (lookup_flags & LOOKUP_DIRECTORY) {
-                       err = -ENOTDIR; 
--                      if (!inode->i_op || !inode->i_op->lookup)
-+                      if (!inode->i_op ||
-+                          (!inode->i_op->lookup && !inode->i_op->lookup_it))
-                               break;
-               }
-               goto return_base;
-@@ -635,6 +672,32 @@ return_reval:
-                * Check the cached dentry for staleness.
-                */
-               dentry = nd->dentry;
-+              if (dentry && dentry->d_op && dentry->d_op->d_revalidate_it) {
-+                      err = -ESTALE;
-+                      if (!dentry->d_op->d_revalidate_it(dentry, 0, it)) {
-+                              struct dentry *new;
-+                              err = permission(dentry->d_parent->d_inode,
-+                                               MAY_EXEC);
-+                              if (err)
-+                                      break;
-+                              new = real_lookup(dentry->d_parent,
-+                                                &dentry->d_name, 0, it);
-+                              if (IS_ERR(new)) {
-+                                      err = PTR_ERR(new);
-+                                      break;
-+                              }
-+                              d_invalidate(dentry);
-+                              dput(dentry);
-+                              nd->dentry = new;
-+                      }
-+                      if (lookup_flags & LOOKUP_DIRECTORY) {
-+                              err = -ENOTDIR; 
-+                              if (!nd->dentry->d_inode->i_op ||
-+                                  (!nd->dentry->d_inode->i_op->lookup &&
-+                                   !nd->dentry->d_inode->i_op->lookup_it))
-+                                      break;
-+                      }
-+              } else
-               if (dentry && dentry->d_sb
-                   && (dentry->d_sb->s_type->fs_flags & FS_ALWAYS_REVAL)) {
-                       err = -ESTALE;
-@@ -649,15 +705,28 @@ out_dput:
-               dput(dentry);
-               break;
-       }
-+      if (err)
-+              intent_release(it);
-       path_release(nd);
- return_err:
-       return err;
- }
-+int link_path_walk(const char * name, struct nameidata *nd)
-+{
-+      return link_path_walk_it(name, nd, NULL);
-+}
-+
-+int path_walk_it(const char * name, struct nameidata *nd, struct lookup_intent *it)
-+{
-+      current->total_link_count = 0;
-+      return link_path_walk_it(name, nd, it);
-+}
-+
- int path_walk(const char * name, struct nameidata *nd)
- {
-       current->total_link_count = 0;
--      return link_path_walk(name, nd);
-+      return link_path_walk_it(name, nd, NULL);
- }
- /* SMP-safe */
-@@ -742,6 +811,17 @@ walk_init_root(const char *name, struct 
- }
- /* SMP-safe */
-+int path_lookup_it(const char *path, unsigned flags, struct nameidata *nd,
-+                 struct lookup_intent *it)
-+{
-+      int error = 0;
-+      if (path_init(path, flags, nd))
-+              error = path_walk_it(path, nd, it);
-+      return error;
-+}
-+
-+
-+/* SMP-safe */
- int path_lookup(const char *path, unsigned flags, struct nameidata *nd)
- {
-       int error = 0;
-@@ -756,6 +836,7 @@ int path_init(const char *name, unsigned
- {
-       nd->last_type = LAST_ROOT; /* if there are only slashes... */
-       nd->flags = flags;
-+      nd->intent = NULL;
-       if (*name=='/')
-               return walk_init_root(name,nd);
-       read_lock(&current->fs->lock);
-@@ -770,7 +851,8 @@ int path_init(const char *name, unsigned
-  * needs parent already locked. Doesn't follow mounts.
-  * SMP-safe.
-  */
--struct dentry * lookup_hash(struct qstr *name, struct dentry * base)
-+struct dentry * lookup_hash_it(struct qstr *name, struct dentry * base,
-+                             struct lookup_intent *it)
- {
-       struct dentry * dentry;
-       struct inode *inode;
-@@ -793,13 +875,16 @@ struct dentry * lookup_hash(struct qstr 
-                       goto out;
-       }
--      dentry = cached_lookup(base, name, 0);
-+      dentry = cached_lookup(base, name, 0, it);
-       if (!dentry) {
-               struct dentry *new = d_alloc(base, name);
-               dentry = ERR_PTR(-ENOMEM);
-               if (!new)
-                       goto out;
-               lock_kernel();
-+              if (inode->i_op->lookup_it)
-+                      dentry = inode->i_op->lookup_it(inode, new, it, 0);
-+              else
-               dentry = inode->i_op->lookup(inode, new);
-               unlock_kernel();
-               if (!dentry)
-@@ -811,6 +896,12 @@ out:
-       return dentry;
- }
-+struct dentry * lookup_hash(struct qstr *name, struct dentry * base)
-+{
-+      return lookup_hash_it(name, base, NULL);
-+}
-+
-+
- /* SMP-safe */
- struct dentry * lookup_one_len(const char * name, struct dentry * base, int len)
- {
-@@ -832,7 +923,7 @@ struct dentry * lookup_one_len(const cha
-       }
-       this.hash = end_name_hash(hash);
--      return lookup_hash(&this, base);
-+      return lookup_hash_it(&this, base, NULL);
- access:
-       return ERR_PTR(-EACCES);
- }
-@@ -863,6 +954,23 @@ int __user_walk(const char *name, unsign
-       return err;
- }
-+int __user_walk_it(const char *name, unsigned flags, struct nameidata *nd,
-+                 struct lookup_intent *it)
-+{
-+      char *tmp;
-+      int err;
-+
-+      tmp = getname(name);
-+      err = PTR_ERR(tmp);
-+      if (!IS_ERR(tmp)) {
-+              err = 0;
-+              if (path_init(tmp, flags, nd))
-+                      err = path_walk_it(tmp, nd, it);
-+              putname(tmp);
-+      }
-+      return err;
-+}
-+
- /*
-  * It's inline, so penalty for filesystems that don't use sticky bit is
-  * minimal.
-@@ -958,7 +1066,8 @@ static inline int lookup_flags(unsigned 
-       return retval;
- }
--int vfs_create(struct inode *dir, struct dentry *dentry, int mode)
-+static int vfs_create_it(struct inode *dir, struct dentry *dentry, int mode,
-+                       struct lookup_intent *it)
- {
-       int error;
-@@ -971,12 +1080,15 @@ int vfs_create(struct inode *dir, struct
-               goto exit_lock;
-       error = -EACCES;        /* shouldn't it be ENOSYS? */
--      if (!dir->i_op || !dir->i_op->create)
-+      if (!dir->i_op || (!dir->i_op->create && !dir->i_op->create_it))
-               goto exit_lock;
-       DQUOT_INIT(dir);
-       lock_kernel();
--      error = dir->i_op->create(dir, dentry, mode);
-+      if (dir->i_op->create_it)
-+              error = dir->i_op->create_it(dir, dentry, mode, it);
-+      else
-+              error = dir->i_op->create(dir, dentry, mode);
-       unlock_kernel();
- exit_lock:
-       up(&dir->i_zombie);
-@@ -985,6 +1097,11 @@ exit_lock:
-       return error;
- }
-+int vfs_create(struct inode *dir, struct dentry *dentry, int mode)
-+{
-+      return vfs_create_it(dir, dentry, mode, NULL);
-+}
-+
- /*
-  *    open_namei()
-  *
-@@ -999,7 +1116,8 @@ exit_lock:
-  * for symlinks (where the permissions are checked later).
-  * SMP-safe
-  */
--int open_namei(const char * pathname, int flag, int mode, struct nameidata *nd)
-+int open_namei_it(const char *pathname, int flag, int mode,
-+                struct nameidata *nd, struct lookup_intent *it)
- {
-       int acc_mode, error = 0;
-       struct inode *inode;
-@@ -1009,11 +1127,14 @@ int open_namei(const char * pathname, in
-       acc_mode = ACC_MODE(flag);
-+      if (it)
-+              it->it_flags = flag;
-+
-       /*
-        * The simplest case - just a plain lookup.
-        */
-       if (!(flag & O_CREAT)) {
--              error = path_lookup(pathname, lookup_flags(flag), nd);
-+              error = path_lookup_it(pathname, lookup_flags(flag), nd, it);
-               if (error)
-                       return error;
-               dentry = nd->dentry;
-@@ -1023,6 +1144,10 @@ int open_namei(const char * pathname, in
-       /*
-        * Create - we need to know the parent.
-        */
-+      if (it) {
-+              it->it_create_mode = mode;
-+              it->it_op |= IT_CREAT;
-+      }
-       error = path_lookup(pathname, LOOKUP_PARENT, nd);
-       if (error)
-               return error;
-@@ -1038,7 +1163,7 @@ int open_namei(const char * pathname, in
-       dir = nd->dentry;
-       down(&dir->d_inode->i_sem);
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
- do_last:
-       error = PTR_ERR(dentry);
-@@ -1047,10 +1172,11 @@ do_last:
-               goto exit;
-       }
-+      it->it_create_mode = mode;
-       /* Negative dentry, just create the file */
-       if (!dentry->d_inode) {
--              error = vfs_create(dir->d_inode, dentry,
--                                 mode & ~current->fs->umask);
-+              error = vfs_create_it(dir->d_inode, dentry,
-+                                 mode & ~current->fs->umask, it);
-               up(&dir->d_inode->i_sem);
-               dput(nd->dentry);
-               nd->dentry = dentry;
-@@ -1154,7 +1280,7 @@ ok:
-               if (!error) {
-                       DQUOT_INIT(inode);
-                       
--                      error = do_truncate(dentry, 0);
-+                      error = do_truncate(dentry, 0, 1);
-               }
-               put_write_access(inode);
-               if (error)
-@@ -1166,8 +1292,10 @@ ok:
-       return 0;
- exit_dput:
-+      intent_release(it);
-       dput(dentry);
- exit:
-+      intent_release(it);
-       path_release(nd);
-       return error;
-@@ -1186,7 +1314,10 @@ do_link:
-        * are done. Procfs-like symlinks just set LAST_BIND.
-        */
-       UPDATE_ATIME(dentry->d_inode);
-+      nd->intent = it;
-       error = dentry->d_inode->i_op->follow_link(dentry, nd);
-+      if (error)
-+              intent_release(it);
-       dput(dentry);
-       if (error)
-               return error;
-@@ -1208,13 +1339,20 @@ do_link:
-       }
-       dir = nd->dentry;
-       down(&dir->d_inode->i_sem);
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
-       putname(nd->last.name);
-       goto do_last;
- }
-+int open_namei(const char *pathname, int flag, int mode, struct nameidata *nd)
-+{
-+      return open_namei_it(pathname, flag, mode, nd, NULL);
-+}
-+
-+
- /* SMP-safe */
--static struct dentry *lookup_create(struct nameidata *nd, int is_dir)
-+static struct dentry *lookup_create(struct nameidata *nd, int is_dir,
-+                                  struct lookup_intent *it)
- {
-       struct dentry *dentry;
-@@ -1222,7 +1360,7 @@ static struct dentry *lookup_create(stru
-       dentry = ERR_PTR(-EEXIST);
-       if (nd->last_type != LAST_NORM)
-               goto fail;
--      dentry = lookup_hash(&nd->last, nd->dentry);
-+      dentry = lookup_hash_it(&nd->last, nd->dentry, it);
-       if (IS_ERR(dentry))
-               goto fail;
-       if (!is_dir && nd->last.name[nd->last.len] && !dentry->d_inode)
-@@ -1278,7 +1416,20 @@ asmlinkage long sys_mknod(const char * f
-       error = path_lookup(tmp, LOOKUP_PARENT, &nd);
-       if (error)
-               goto out;
--      dentry = lookup_create(&nd, 0);
-+
-+      if (nd.last_type != LAST_NORM) {
-+              error = -EEXIST;
-+              goto out2;
-+      }
-+      if (nd.dentry->d_inode->i_op->mknod_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+              error = op->mknod_raw(&nd, mode, dev);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto out2;
-+      }
-+
-+      dentry = lookup_create(&nd, 0, NULL);
-       error = PTR_ERR(dentry);
-       mode &= ~current->fs->umask;
-@@ -1299,6 +1446,7 @@ asmlinkage long sys_mknod(const char * f
-               dput(dentry);
-       }
-       up(&nd.dentry->d_inode->i_sem);
-+out2:
-       path_release(&nd);
- out:
-       putname(tmp);
-@@ -1346,7 +1494,20 @@ asmlinkage long sys_mkdir(const char * p
-               error = path_lookup(tmp, LOOKUP_PARENT, &nd);
-               if (error)
-                       goto out;
--              dentry = lookup_create(&nd, 1);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out2;
-+              }
-+              if (nd.dentry->d_inode->i_op->mkdir_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->mkdir_raw(&nd, mode);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out2;
-+              }
-+              dentry = lookup_create(&nd, 1, NULL);
-               error = PTR_ERR(dentry);
-               if (!IS_ERR(dentry)) {
-                       error = vfs_mkdir(nd.dentry->d_inode, dentry,
-@@ -1354,6 +1509,7 @@ asmlinkage long sys_mkdir(const char * p
-                       dput(dentry);
-               }
-               up(&nd.dentry->d_inode->i_sem);
-+out2:
-               path_release(&nd);
- out:
-               putname(tmp);
-@@ -1454,8 +1610,16 @@ asmlinkage long sys_rmdir(const char * p
-                       error = -EBUSY;
-                       goto exit1;
-       }
-+      if (nd.dentry->d_inode->i_op->rmdir_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              error = op->rmdir_raw(&nd);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit1;
-+      }
-       down(&nd.dentry->d_inode->i_sem);
--      dentry = lookup_hash(&nd.last, nd.dentry);
-+      dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-               error = vfs_rmdir(nd.dentry->d_inode, dentry);
-@@ -1513,8 +1677,15 @@ asmlinkage long sys_unlink(const char * 
-       error = -EISDIR;
-       if (nd.last_type != LAST_NORM)
-               goto exit1;
-+      if (nd.dentry->d_inode->i_op->unlink_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+              error = op->unlink_raw(&nd);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit1;
-+      }
-       down(&nd.dentry->d_inode->i_sem);
--      dentry = lookup_hash(&nd.last, nd.dentry);
-+      dentry = lookup_hash_it(&nd.last, nd.dentry, NULL);
-       error = PTR_ERR(dentry);
-       if (!IS_ERR(dentry)) {
-               /* Why not before? Because we want correct error value */
-@@ -1581,15 +1752,27 @@ asmlinkage long sys_symlink(const char *
-               error = path_lookup(to, LOOKUP_PARENT, &nd);
-               if (error)
-                       goto out;
--              dentry = lookup_create(&nd, 0);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out2;
-+              }
-+              if (nd.dentry->d_inode->i_op->symlink_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->symlink_raw(&nd, from);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out2;
-+              }
-+              dentry = lookup_create(&nd, 0, NULL);
-               error = PTR_ERR(dentry);
-               if (!IS_ERR(dentry)) {
-                       error = vfs_symlink(nd.dentry->d_inode, dentry, from);
-                       dput(dentry);
-               }
-               up(&nd.dentry->d_inode->i_sem);
-+      out2:
-               path_release(&nd);
--out:
-+      out:
-               putname(to);
-       }
-       putname(from);
-@@ -1665,7 +1844,18 @@ asmlinkage long sys_link(const char * ol
-               error = -EXDEV;
-               if (old_nd.mnt != nd.mnt)
-                       goto out_release;
--              new_dentry = lookup_create(&nd, 0);
-+              if (nd.last_type != LAST_NORM) {
-+                      error = -EEXIST;
-+                      goto out2;
-+              }
-+              if (nd.dentry->d_inode->i_op->link_raw) {
-+                      struct inode_operations *op = nd.dentry->d_inode->i_op;
-+                      error = op->link_raw(&old_nd, &nd);
-+                      /* the file system wants to use normal vfs path now */
-+                      if (error != -EOPNOTSUPP)
-+                              goto out_release;
-+              }
-+              new_dentry = lookup_create(&nd, 0, NULL);
-               error = PTR_ERR(new_dentry);
-               if (!IS_ERR(new_dentry)) {
-                       error = vfs_link(old_nd.dentry, nd.dentry->d_inode, new_dentry);
-@@ -1709,7 +1895,7 @@ exit:
-  *       locking].
-  */
- int vfs_rename_dir(struct inode *old_dir, struct dentry *old_dentry,
--             struct inode *new_dir, struct dentry *new_dentry)
-+                 struct inode *new_dir, struct dentry *new_dentry)
- {
-       int error;
-       struct inode *target;
-@@ -1788,7 +1974,7 @@ out_unlock:
- }
- int vfs_rename_other(struct inode *old_dir, struct dentry *old_dentry,
--             struct inode *new_dir, struct dentry *new_dentry)
-+                   struct inode *new_dir, struct dentry *new_dentry)
- {
-       int error;
-@@ -1876,9 +2062,18 @@ static inline int do_rename(const char *
-       if (newnd.last_type != LAST_NORM)
-               goto exit2;
-+      if (old_dir->d_inode->i_op->rename_raw) {
-+              lock_kernel();
-+              error = old_dir->d_inode->i_op->rename_raw(&oldnd, &newnd);
-+              unlock_kernel();
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto exit2;
-+      }
-+
-       double_lock(new_dir, old_dir);
--      old_dentry = lookup_hash(&oldnd.last, old_dir);
-+      old_dentry = lookup_hash_it(&oldnd.last, old_dir, NULL);
-       error = PTR_ERR(old_dentry);
-       if (IS_ERR(old_dentry))
-               goto exit3;
-@@ -1894,16 +2089,16 @@ static inline int do_rename(const char *
-               if (newnd.last.name[newnd.last.len])
-                       goto exit4;
-       }
--      new_dentry = lookup_hash(&newnd.last, new_dir);
-+      new_dentry = lookup_hash_it(&newnd.last, new_dir, NULL);
-       error = PTR_ERR(new_dentry);
-       if (IS_ERR(new_dentry))
-               goto exit4;
-+
-       lock_kernel();
-       error = vfs_rename(old_dir->d_inode, old_dentry,
-                                  new_dir->d_inode, new_dentry);
-       unlock_kernel();
--
-       dput(new_dentry);
- exit4:
-       dput(old_dentry);
-@@ -1954,20 +2149,26 @@ out:
- }
- static inline int
--__vfs_follow_link(struct nameidata *nd, const char *link)
-+__vfs_follow_link(struct nameidata *nd, const char *link,
-+                struct lookup_intent *it)
- {
-       int res = 0;
-       char *name;
-       if (IS_ERR(link))
-               goto fail;
-+      if (it == NULL)
-+              it = nd->intent;
-+      else if (it != nd->intent)
-+              printk("it != nd->intent: tell phil@clusterfs.com\n");
-+
-       if (*link == '/') {
-               path_release(nd);
-               if (!walk_init_root(link, nd))
-                       /* weird __emul_prefix() stuff did it */
-                       goto out;
-       }
--      res = link_path_walk(link, nd);
-+      res = link_path_walk_it(link, nd, it);
- out:
-       if (current->link_count || res || nd->last_type!=LAST_NORM)
-               return res;
-@@ -1991,7 +2192,13 @@ fail:
- int vfs_follow_link(struct nameidata *nd, const char *link)
- {
--      return __vfs_follow_link(nd, link);
-+      return __vfs_follow_link(nd, link, NULL);
-+}
-+
-+int vfs_follow_link_it(struct nameidata *nd, const char *link,
-+                     struct lookup_intent *it)
-+{
-+      return __vfs_follow_link(nd, link, it);
- }
- /* get the link contents into pagecache */
-@@ -2033,7 +2240,7 @@ int page_follow_link(struct dentry *dent
- {
-       struct page *page = NULL;
-       char *s = page_getlink(dentry, &page);
--      int res = __vfs_follow_link(nd, s);
-+      int res = __vfs_follow_link(nd, s, NULL);
-       if (page) {
-               kunmap(page);
-               page_cache_release(page);
---- linux-2.4.22-ac1/fs/namespace.c~vfs_intent-2.4.22-rh       2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/namespace.c     2003-09-25 14:42:46.000000000 +0400
-@@ -98,6 +98,7 @@ static void detach_mnt(struct vfsmount *
- {
-       old_nd->dentry = mnt->mnt_mountpoint;
-       old_nd->mnt = mnt->mnt_parent;
-+      UNPIN(old_nd->dentry, old_nd->mnt, 1);
-       mnt->mnt_parent = mnt;
-       mnt->mnt_mountpoint = mnt->mnt_root;
-       list_del_init(&mnt->mnt_child);
-@@ -109,6 +110,7 @@ static void attach_mnt(struct vfsmount *
- {
-       mnt->mnt_parent = mntget(nd->mnt);
-       mnt->mnt_mountpoint = dget(nd->dentry);
-+      PIN(nd->dentry, nd->mnt, 1);
-       list_add(&mnt->mnt_hash, mount_hashtable+hash(nd->mnt, nd->dentry));
-       list_add(&mnt->mnt_child, &nd->mnt->mnt_mounts);
-       nd->dentry->d_mounted++;
-@@ -488,14 +490,17 @@ static int do_loopback(struct nameidata 
- {
-       struct nameidata old_nd;
-       struct vfsmount *mnt = NULL;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int err = mount_is_safe(nd);
-       if (err)
-               return err;
-       if (!old_name || !*old_name)
-               return -EINVAL;
--      err = path_lookup(old_name, LOOKUP_POSITIVE|LOOKUP_FOLLOW, &old_nd);
--      if (err)
-+      err = path_lookup_it(old_name, LOOKUP_POSITIVE|LOOKUP_FOLLOW, &old_nd, &it);
-+      if (err) {
-+              intent_release(&it);
-               return err;
-+      }
-       down_write(&current->namespace->sem);
-       err = -EINVAL;
-@@ -518,6 +523,7 @@ static int do_loopback(struct nameidata 
-       }
-       up_write(&current->namespace->sem);
-+      intent_release(&it);
-       path_release(&old_nd);
-       return err;
- }
-@@ -701,6 +707,7 @@ long do_mount(char * dev_name, char * di
-                 unsigned long flags, void *data_page)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int retval = 0;
-       int mnt_flags = 0;
-@@ -725,9 +732,11 @@ long do_mount(char * dev_name, char * di
-       flags &= ~(MS_NOSUID|MS_NOEXEC|MS_NODEV);
-       /* ... and get the mountpoint */
--      retval = path_lookup(dir_name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd);
--      if (retval)
-+      retval = path_lookup_it(dir_name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, &nd, &it);
-+      if (retval) {
-+              intent_release(&it);
-               return retval;
-+      }
-
-       if (flags & MS_REMOUNT)
-               retval = do_remount(&nd, flags & ~MS_REMOUNT, mnt_flags,
-@@ -739,6 +747,8 @@ long do_mount(char * dev_name, char * di
-       else
-               retval = do_add_mount(&nd, type_page, flags, mnt_flags,
-                                     dev_name, data_page);
-+
-+      intent_release(&it);
-       path_release(&nd);
-       return retval;
- }
-@@ -904,6 +914,8 @@ asmlinkage long sys_pivot_root(const cha
- {
-       struct vfsmount *tmp;
-       struct nameidata new_nd, old_nd, parent_nd, root_parent, user_nd;
-+      struct lookup_intent new_it = { .it_op = IT_GETATTR };
-+      struct lookup_intent old_it = { .it_op = IT_GETATTR };
-       int error;
-       if (!capable(CAP_SYS_ADMIN))
-@@ -911,14 +923,14 @@ asmlinkage long sys_pivot_root(const cha
-       lock_kernel();
--      error = __user_walk(new_root, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &new_nd);
-+      error = __user_walk_it(new_root, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &new_nd, &new_it);
-       if (error)
-               goto out0;
-       error = -EINVAL;
-       if (!check_mnt(new_nd.mnt))
-               goto out1;
--      error = __user_walk(put_old, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &old_nd);
-+      error = __user_walk_it(put_old, LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY, &old_nd, &old_it);
-       if (error)
-               goto out1;
-@@ -973,8 +985,10 @@ out2:
-       up(&old_nd.dentry->d_inode->i_zombie);
-       up_write(&current->namespace->sem);
-       path_release(&user_nd);
-+      intent_release(&old_it);
-       path_release(&old_nd);
- out1:
-+      intent_release(&new_it);
-       path_release(&new_nd);
- out0:
-       unlock_kernel();
---- linux-2.4.22-ac1/fs/open.c~vfs_intent-2.4.22-rh    2003-08-25 15:44:43.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/open.c  2003-09-25 14:42:46.000000000 +0400
-@@ -19,6 +19,8 @@
- #include <asm/uaccess.h>
- #define special_file(m) (S_ISCHR(m)||S_ISBLK(m)||S_ISFIFO(m)||S_ISSOCK(m))
-+extern int path_walk_it(const char *name, struct nameidata *nd,
-+                      struct lookup_intent *it);
- int vfs_statfs(struct super_block *sb, struct statfs *buf)
- {
-@@ -95,9 +97,10 @@ void fd_install(unsigned int fd, struct 
-       write_unlock(&files->file_lock);
- }
--int do_truncate(struct dentry *dentry, loff_t length)
-+int do_truncate(struct dentry *dentry, loff_t length, int called_from_open)
- {
-       struct inode *inode = dentry->d_inode;
-+      struct inode_operations *op = dentry->d_inode->i_op;
-       int error;
-       struct iattr newattrs;
-@@ -109,7 +112,13 @@ int do_truncate(struct dentry *dentry, l
-       down(&inode->i_sem);
-       newattrs.ia_size = length;
-       newattrs.ia_valid = ATTR_SIZE | ATTR_CTIME;
--      error = notify_change(dentry, &newattrs);
-+      if (called_from_open)
-+              newattrs.ia_valid |= ATTR_FROM_OPEN;
-+      if (op->setattr_raw) {
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+      } else
-+              error = notify_change(dentry, &newattrs);
-       up(&inode->i_sem);
-       up_write(&inode->i_alloc_sem);
-       return error;
-@@ -120,12 +129,13 @@ static inline long do_sys_truncate(const
-       struct nameidata nd;
-       struct inode * inode;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       error = -EINVAL;
-       if (length < 0) /* sorry, but loff_t says... */
-               goto out;
--      error = user_path_walk(path, &nd);
-+      error = user_path_walk_it(path, &nd, &it);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-@@ -165,11 +175,13 @@ static inline long do_sys_truncate(const
-       error = locks_verify_truncate(inode, NULL, length);
-       if (!error) {
-               DQUOT_INIT(inode);
--              error = do_truncate(nd.dentry, length);
-+              intent_release(&it);
-+              error = do_truncate(nd.dentry, length, 0);
-       }
-       put_write_access(inode);
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
-@@ -217,7 +229,7 @@ static inline long do_sys_ftruncate(unsi
-       error = locks_verify_truncate(inode, file, length);
-       if (!error)
--              error = do_truncate(dentry, length);
-+              error = do_truncate(dentry, length, 0);
- out_putf:
-       fput(file);
- out:
-@@ -262,11 +274,13 @@ asmlinkage long sys_utime(char * filenam
-       struct inode * inode;
-       struct iattr newattrs;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, NULL);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-+      /* this is safe without a Lustre lock because it only depends
-+         on the super block */
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto dput_and_out;
-@@ -281,11 +295,25 @@ asmlinkage long sys_utime(char * filenam
-                       goto dput_and_out;
-               newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET;
--      } else {
-+      }
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto dput_and_out;
-+      }
-+
-+      error = -EPERM;
-+      if (!times) {
-               if (current->fsuid != inode->i_uid &&
-                   (error = permission(inode,MAY_WRITE)) != 0)
-                       goto dput_and_out;
-       }
-+
-       error = notify_change(nd.dentry, &newattrs);
- dput_and_out:
-       path_release(&nd);
-@@ -306,12 +334,14 @@ asmlinkage long sys_utimes(char * filena
-       struct inode * inode;
-       struct iattr newattrs;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, NULL);
-       if (error)
-               goto out;
-       inode = nd.dentry->d_inode;
-+      /* this is safe without a Lustre lock because it only depends
-+         on the super block */
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto dput_and_out;
-@@ -326,7 +356,20 @@ asmlinkage long sys_utimes(char * filena
-               newattrs.ia_atime = times[0].tv_sec;
-               newattrs.ia_mtime = times[1].tv_sec;
-               newattrs.ia_valid |= ATTR_ATIME_SET | ATTR_MTIME_SET;
--      } else {
-+      }
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = nd.dentry->d_inode->i_op;
-+
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      goto dput_and_out;
-+      }
-+
-+      error = -EPERM;
-+      if (!utimes) {
-               if (current->fsuid != inode->i_uid &&
-                   (error = permission(inode,MAY_WRITE)) != 0)
-                       goto dput_and_out;
-@@ -349,6 +392,7 @@ asmlinkage long sys_access(const char * 
-       int old_fsuid, old_fsgid;
-       kernel_cap_t old_cap;
-       int res;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       if (mode & ~S_IRWXO)    /* where's F_OK, X_OK, W_OK, R_OK? */
-               return -EINVAL;
-@@ -366,13 +410,14 @@ asmlinkage long sys_access(const char * 
-       else
-               current->cap_effective = current->cap_permitted;
--      res = user_path_walk(filename, &nd);
-+      res = user_path_walk_it(filename, &nd, &it);
-       if (!res) {
-               res = permission(nd.dentry->d_inode, mode);
-               /* SuS v2 requires we report a read only fs too */
-               if(!res && (mode & S_IWOTH) && IS_RDONLY(nd.dentry->d_inode)
-                  && !special_file(nd.dentry->d_inode->i_mode))
-                       res = -EROFS;
-+              intent_release(&it);
-               path_release(&nd);
-       }
-@@ -387,8 +432,9 @@ asmlinkage long sys_chdir(const char * f
- {
-       int error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = __user_walk(filename,LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY,&nd);
-+      error = __user_walk_it(filename,LOOKUP_POSITIVE|LOOKUP_FOLLOW|LOOKUP_DIRECTORY,&nd, &it);
-       if (error)
-               goto out;
-@@ -399,6 +445,7 @@ asmlinkage long sys_chdir(const char * f
-       set_fs_pwd(current->fs, nd.mnt, nd.dentry);
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
-@@ -438,9 +485,10 @@ asmlinkage long sys_chroot(const char * 
- {
-       int error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = __user_walk(filename, LOOKUP_POSITIVE | LOOKUP_FOLLOW |
--                    LOOKUP_DIRECTORY | LOOKUP_NOALT, &nd);
-+      error = __user_walk_it(filename, LOOKUP_POSITIVE | LOOKUP_FOLLOW |
-+                             LOOKUP_DIRECTORY | LOOKUP_NOALT, &nd, &it);
-       if (error)
-               goto out;
-@@ -456,39 +504,56 @@ asmlinkage long sys_chroot(const char * 
-       set_fs_altroot();
-       error = 0;
- dput_and_out:
-+      intent_release(&it);
-       path_release(&nd);
- out:
-       return error;
- }
--asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
-+int chmod_common(struct dentry *dentry, mode_t mode)
- {
--      struct inode * inode;
--      struct dentry * dentry;
--      struct file * file;
--      int err = -EBADF;
-+      struct inode *inode = dentry->d_inode;
-       struct iattr newattrs;
-+      int err = -EROFS;
--      file = fget(fd);
--      if (!file)
-+      if (IS_RDONLY(inode))
-               goto out;
--      dentry = file->f_dentry;
--      inode = dentry->d_inode;
-+      if (inode->i_op->setattr_raw) {
-+              newattrs.ia_mode = mode;
-+              newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
-+              newattrs.ia_valid |= ATTR_RAW;
-+              err = inode->i_op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (err != -EOPNOTSUPP)
-+                      goto out;
-+      }
--      err = -EROFS;
--      if (IS_RDONLY(inode))
--              goto out_putf;
-       err = -EPERM;
-       if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
--              goto out_putf;
-+              goto out;
-+
-       if (mode == (mode_t) -1)
-               mode = inode->i_mode;
-       newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
-       newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
-       err = notify_change(dentry, &newattrs);
--out_putf:
-+out:
-+      return err;
-+}
-+
-+asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
-+{
-+      struct file * file;
-+      int err = -EBADF;
-+
-+      file = fget(fd);
-+      if (!file)
-+              goto out;
-+
-+      err = chmod_common(file->f_dentry, mode);
-+
-       fput(file);
- out:
-       return err;
-@@ -497,30 +562,14 @@ out:
- asmlinkage long sys_chmod(const char * filename, mode_t mode)
- {
-       struct nameidata nd;
--      struct inode * inode;
-       int error;
--      struct iattr newattrs;
-       error = user_path_walk(filename, &nd);
-       if (error)
-               goto out;
--      inode = nd.dentry->d_inode;
--
--      error = -EROFS;
--      if (IS_RDONLY(inode))
--              goto dput_and_out;
--      error = -EPERM;
--      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
--              goto dput_and_out;
-+      error = chmod_common(nd.dentry, mode);
--      if (mode == (mode_t) -1)
--              mode = inode->i_mode;
--      newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
--      newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
--      error = notify_change(nd.dentry, &newattrs);
--
--dput_and_out:
-       path_release(&nd);
- out:
-       return error;
-@@ -540,6 +589,20 @@ static int chown_common(struct dentry * 
-       error = -EROFS;
-       if (IS_RDONLY(inode))
-               goto out;
-+
-+      if (inode->i_op->setattr_raw) {
-+              struct inode_operations *op = dentry->d_inode->i_op;
-+
-+              newattrs.ia_uid = user;
-+              newattrs.ia_gid = group;
-+              newattrs.ia_valid = ATTR_UID | ATTR_GID | ATTR_CTIME;
-+              newattrs.ia_valid |= ATTR_RAW;
-+              error = op->setattr_raw(inode, &newattrs);
-+              /* the file system wants to use normal vfs path now */
-+              if (error != -EOPNOTSUPP)
-+                      return error;
-+      }
-+
-       error = -EPERM;
-       if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-               goto out;
-@@ -644,6 +707,7 @@ struct file *filp_open(const char * file
- {
-       int namei_flags, error;
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_OPEN };
-       namei_flags = flags;
-       if ((namei_flags+1) & O_ACCMODE)
-@@ -651,14 +715,15 @@ struct file *filp_open(const char * file
-       if (namei_flags & O_TRUNC)
-               namei_flags |= 2;
--      error = open_namei(filename, namei_flags, mode, &nd);
--      if (!error)
--              return dentry_open(nd.dentry, nd.mnt, flags);
-+      error = open_namei_it(filename, namei_flags, mode, &nd, &it);
-+      if (error)
-+              return ERR_PTR(error);
--      return ERR_PTR(error);
-+      return dentry_open_it(nd.dentry, nd.mnt, flags, &it);
- }
--struct file *dentry_open(struct dentry *dentry, struct vfsmount *mnt, int flags)
-+struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-+                          int flags, struct lookup_intent *it)
- {
-       struct file * f;
-       struct inode *inode;
-@@ -695,12 +760,15 @@ struct file *dentry_open(struct dentry *
-       }
-       if (f->f_op && f->f_op->open) {
-+              f->f_it = it;
-               error = f->f_op->open(inode,f);
-+              f->f_it = NULL;
-               if (error)
-                       goto cleanup_all;
-       }
-       f->f_flags &= ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
-+      intent_release(it);
-       return f;
- cleanup_all:
-@@ -715,11 +783,17 @@ cleanup_all:
- cleanup_file:
-       put_filp(f);
- cleanup_dentry:
-+      intent_release(it);
-       dput(dentry);
-       mntput(mnt);
-       return ERR_PTR(error);
- }
-+struct file *dentry_open(struct dentry *dentry, struct vfsmount *mnt, int flags)
-+{
-+      return dentry_open_it(dentry, mnt, flags, NULL);
-+}
-+
- /*
-  * Find an empty file descriptor entry, and mark it busy.
-  */
---- linux-2.4.22-ac1/fs/stat.c~vfs_intent-2.4.22-rh    2003-09-25 14:16:27.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/stat.c  2003-09-25 14:42:46.000000000 +0400
-@@ -17,10 +17,12 @@
-  * Revalidate the inode. This is required for proper NFS attribute caching.
-  */
- static __inline__ int
--do_revalidate(struct dentry *dentry)
-+do_revalidate(struct dentry *dentry, struct lookup_intent *it)
- {
-       struct inode * inode = dentry->d_inode;
--      if (inode->i_op && inode->i_op->revalidate)
-+      if (inode->i_op && inode->i_op->revalidate_it)
-+              return inode->i_op->revalidate_it(dentry, it);
-+      else if (inode->i_op && inode->i_op->revalidate)
-               return inode->i_op->revalidate(dentry);
-       return 0;
- }
-@@ -143,13 +147,15 @@ static int cp_new_stat(struct inode * in
- asmlinkage long sys_stat(char * filename, struct __old_kernel_stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_old_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -159,13 +165,15 @@ asmlinkage long sys_stat(char * filename
- asmlinkage long sys_newstat(char * filename, struct stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -180,13 +188,15 @@ asmlinkage long sys_newstat(char * filen
- asmlinkage long sys_lstat(char * filename, struct __old_kernel_stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk_link(filename, &nd);
-+      error = user_path_walk_link_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_old_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -197,13 +207,15 @@ asmlinkage long sys_lstat(char * filenam
- asmlinkage long sys_newlstat(char * filename, struct stat * statbuf)
- {
-       struct nameidata nd;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
-       int error;
--      error = user_path_walk_link(filename, &nd);
-+      error = user_path_walk_link_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -224,7 +236,7 @@ asmlinkage long sys_fstat(unsigned int f
-       if (f) {
-               struct dentry * dentry = f->f_dentry;
--              err = do_revalidate(dentry);
-+              err = do_revalidate(dentry, NULL);
-               if (!err)
-                       err = cp_old_stat(dentry->d_inode, statbuf);
-               fput(f);
-@@ -243,7 +255,7 @@ asmlinkage long sys_newfstat(unsigned in
-       if (f) {
-               struct dentry * dentry = f->f_dentry;
--              err = do_revalidate(dentry);
-+              err = do_revalidate(dentry, NULL);
-               if (!err)
-                       err = cp_new_stat(dentry->d_inode, statbuf);
-               fput(f);
-@@ -265,7 +277,7 @@ asmlinkage long sys_readlink(const char 
-               error = -EINVAL;
-               if (inode->i_op && inode->i_op->readlink &&
--                  !(error = do_revalidate(nd.dentry))) {
-+                  !(error = do_revalidate(nd.dentry, NULL))) {
-                       UPDATE_ATIME(inode);
-                       error = inode->i_op->readlink(nd.dentry, buf, bufsiz);
-               }
-@@ -341,12 +353,14 @@ asmlinkage long sys_stat64(char * filena
- {
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = user_path_walk(filename, &nd);
-+      error = user_path_walk_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat64(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -356,12 +370,14 @@ asmlinkage long sys_lstat64(char * filen
- {
-       struct nameidata nd;
-       int error;
-+      struct lookup_intent it = { .it_op = IT_GETATTR };
--      error = user_path_walk_link(filename, &nd);
-+      error = user_path_walk_link_it(filename, &nd, &it);
-       if (!error) {
--              error = do_revalidate(nd.dentry);
-+              error = do_revalidate(nd.dentry, &it);
-               if (!error)
-                       error = cp_new_stat64(nd.dentry->d_inode, statbuf);
-+              intent_release(&it);
-               path_release(&nd);
-       }
-       return error;
-@@ -376,7 +392,7 @@ asmlinkage long sys_fstat64(unsigned lon
-       if (f) {
-               struct dentry * dentry = f->f_dentry;
--              err = do_revalidate(dentry);
-+              err = do_revalidate(dentry, NULL);
-               if (!err)
-                       err = cp_new_stat64(dentry->d_inode, statbuf);
-               fput(f);
---- linux-2.4.22-ac1/include/linux/dcache.h~vfs_intent-2.4.22-rh       2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/dcache.h     2003-09-25 14:42:46.000000000 +0400
-@@ -6,6 +6,51 @@
- #include <asm/atomic.h>
- #include <linux/mount.h>
- #include <linux/kernel.h>
-+#include <linux/string.h>
-+
-+#define IT_OPEN     0x0001
-+#define IT_CREAT    0x0002
-+#define IT_READDIR  0x0004
-+#define IT_GETATTR  0x0008
-+#define IT_LOOKUP   0x0010
-+#define IT_UNLINK   0x0020
-+#define IT_GETXATTR 0x0040
-+#define IT_EXEC     0x0080
-+#define IT_PIN      0x0100
-+
-+#define IT_FL_LOCKED   0x0001
-+#define IT_FL_FOLLOWED 0x0002 /* set by vfs_follow_link */
-+
-+#define INTENT_MAGIC 0x19620323
-+
-+
-+struct lustre_intent_data {
-+      int       it_disposition;
-+      int       it_status;
-+      __u64     it_lock_handle;
-+      void     *it_data;
-+      int       it_lock_mode;
-+      int it_int_flags;
-+};
-+struct lookup_intent {
-+      int     it_magic;
-+      void    (*it_op_release)(struct lookup_intent *);
-+      int     it_op;
-+      int     it_flags;
-+      int     it_create_mode;
-+      union {
-+              struct lustre_intent_data lustre;
-+      } d;
-+};
-+
-+static inline void intent_init(struct lookup_intent *it, int op, int flags)
-+{
-+      memset(it, 0, sizeof(*it));
-+      it->it_magic = INTENT_MAGIC;
-+      it->it_op = op;
-+      it->it_flags = flags;
-+}
-+
- /*
-  * linux/include/linux/dcache.h
-@@ -95,8 +140,22 @@ struct dentry_operations {
-       int (*d_delete)(struct dentry *);
-       void (*d_release)(struct dentry *);
-       void (*d_iput)(struct dentry *, struct inode *);
-+      int (*d_revalidate_it)(struct dentry *, int, struct lookup_intent *);
-+      void (*d_pin)(struct dentry *, struct vfsmount * , int);
-+      void (*d_unpin)(struct dentry *, struct vfsmount *, int);
- };
-+#define PIN(de,mnt,flag)  if (de && de->d_op && de->d_op->d_pin) \
-+                              de->d_op->d_pin(de, mnt, flag);
-+#define UNPIN(de,mnt,flag)  if (de && de->d_op && de->d_op->d_unpin) \
-+                              de->d_op->d_unpin(de, mnt, flag);
-+
-+
-+/* defined in fs/namei.c */
-+extern void intent_release(struct lookup_intent *it);
-+/* defined in fs/dcache.c */
-+extern void __d_rehash(struct dentry * entry, int lock);
-+
- /* the dentry parameter passed to d_hash and d_compare is the parent
-  * directory of the entries to be compared. It is used in case these
-  * functions need any directory specific information for determining
-@@ -128,6 +187,7 @@ d_iput:            no              no              yes
-                                        * s_nfsd_free_path semaphore will be down
-                                        */
- #define DCACHE_REFERENCED     0x0008  /* Recently used, don't discard. */
-+#define DCACHE_LUSTRE_INVALID 0x0010  /* Lustre invalidated */
- extern spinlock_t dcache_lock;
---- linux-2.4.22-ac1/include/linux/fs.h~vfs_intent-2.4.22-rh   2003-09-25 14:39:01.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/fs.h 2003-09-25 14:42:46.000000000 +0400
-@@ -73,6 +73,7 @@ extern int leases_enable, dir_notify_ena
- #define FMODE_READ 1
- #define FMODE_WRITE 2
-+#define FMODE_EXEC 4
- #define READ 0
- #define WRITE 1
-@@ -343,6 +344,9 @@ extern void set_bh_page(struct buffer_he
- #define ATTR_MTIME_SET        256
- #define ATTR_FORCE    512     /* Not a change, but a change it */
- #define ATTR_ATTR_FLAG        1024
-+#define ATTR_RAW      0x0800  /* file system, not vfs will massage attrs */
-+#define ATTR_FROM_OPEN        0x1000  /* called from open path, ie O_TRUNC */
-+#define ATTR_CTIME_SET        0x2000
- /*
-  * This is the Inode Attributes structure, used for notify_change().  It
-@@ -481,6 +485,7 @@ struct inode {
-       struct pipe_inode_info  *i_pipe;
-       struct block_device     *i_bdev;
-       struct char_device      *i_cdev;
-+      void                    *i_filterdata;
-       unsigned long           i_dnotify_mask; /* Directory notify events */
-       struct dnotify_struct   *i_dnotify; /* for directory notifications */
-@@ -583,6 +588,7 @@ struct file {
-       /* needed for tty driver, and maybe others */
-       void                    *private_data;
-+      struct lookup_intent    *f_it;
-       /* preallocated helper kiobuf to speedup O_DIRECT */
-       struct kiobuf           *f_iobuf;
-@@ -703,6 +709,7 @@ struct nameidata {
-       struct qstr last;
-       unsigned int flags;
-       int last_type;
-+      struct lookup_intent *intent;
- };
- /*
-@@ -823,7 +830,8 @@ extern int vfs_symlink(struct inode *, s
- extern int vfs_link(struct dentry *, struct inode *, struct dentry *);
- extern int vfs_rmdir(struct inode *, struct dentry *);
- extern int vfs_unlink(struct inode *, struct dentry *);
--extern int vfs_rename(struct inode *, struct dentry *, struct inode *, struct dentry *);
-+int vfs_rename(struct inode *old_dir, struct dentry *old_dentry,
-+             struct inode *new_dir, struct dentry *new_dentry);
- /*
-  * File types
-@@ -883,21 +891,32 @@ struct file_operations {
- struct inode_operations {
-       int (*create) (struct inode *,struct dentry *,int);
-+      int (*create_it) (struct inode *,struct dentry *,int, struct lookup_intent *);
-       struct dentry * (*lookup) (struct inode *,struct dentry *);
-+      struct dentry * (*lookup_it) (struct inode *,struct dentry *, struct lookup_intent *, int flags);
-       int (*link) (struct dentry *,struct inode *,struct dentry *);
-+      int (*link_raw) (struct nameidata *,struct nameidata *);
-       int (*unlink) (struct inode *,struct dentry *);
-+      int (*unlink_raw) (struct nameidata *);
-       int (*symlink) (struct inode *,struct dentry *,const char *);
-+      int (*symlink_raw) (struct nameidata *,const char *);
-       int (*mkdir) (struct inode *,struct dentry *,int);
-+      int (*mkdir_raw) (struct nameidata *,int);
-       int (*rmdir) (struct inode *,struct dentry *);
-+      int (*rmdir_raw) (struct nameidata *);
-       int (*mknod) (struct inode *,struct dentry *,int,int);
-+      int (*mknod_raw) (struct nameidata *,int,dev_t);
-       int (*rename) (struct inode *, struct dentry *,
-                       struct inode *, struct dentry *);
-+      int (*rename_raw) (struct nameidata *, struct nameidata *);
-       int (*readlink) (struct dentry *, char *,int);
-       int (*follow_link) (struct dentry *, struct nameidata *);
-       void (*truncate) (struct inode *);
-       int (*permission) (struct inode *, int);
-       int (*revalidate) (struct dentry *);
-+      int (*revalidate_it) (struct dentry *, struct lookup_intent *);
-       int (*setattr) (struct dentry *, struct iattr *);
-+      int (*setattr_raw) (struct inode *, struct iattr *);
-       int (*getattr) (struct dentry *, struct iattr *);
-       int (*setxattr) (struct dentry *, const char *, void *, size_t, int);
-       ssize_t (*getxattr) (struct dentry *, const char *, void *, size_t);
-@@ -1094,10 +1113,14 @@ static inline int get_lease(struct inode
- asmlinkage long sys_open(const char *, int, int);
- asmlinkage long sys_close(unsigned int);      /* yes, it's really unsigned */
--extern int do_truncate(struct dentry *, loff_t start);
-+extern int do_truncate(struct dentry *, loff_t start, int called_from_open);
- extern struct file *filp_open(const char *, int, int);
- extern struct file * dentry_open(struct dentry *, struct vfsmount *, int);
-+extern int open_namei_it(const char *filename, int namei_flags, int mode,
-+                       struct nameidata *nd, struct lookup_intent *it);
-+extern struct file *dentry_open_it(struct dentry *dentry, struct vfsmount *mnt,
-+                          int flags, struct lookup_intent *it);
- extern int filp_close(struct file *, fl_owner_t id);
- extern char * getname(const char *);
-@@ -1388,6 +1411,7 @@ typedef int (*read_actor_t)(read_descrip
- extern loff_t default_llseek(struct file *file, loff_t offset, int origin);
- extern int FASTCALL(__user_walk(const char *, unsigned, struct nameidata *));
-+extern int FASTCALL(__user_walk_it(const char *, unsigned, struct nameidata *, struct lookup_intent *it));
- extern int FASTCALL(path_init(const char *, unsigned, struct nameidata *));
- extern int FASTCALL(path_walk(const char *, struct nameidata *));
- extern int FASTCALL(path_lookup(const char *, unsigned, struct nameidata *));
-@@ -1399,6 +1423,8 @@ extern struct dentry * lookup_one_len(co
- extern struct dentry * lookup_hash(struct qstr *, struct dentry *);
- #define user_path_walk(name,nd)        __user_walk(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd)
- #define user_path_walk_link(name,nd) __user_walk(name, LOOKUP_POSITIVE, nd)
-+#define user_path_walk_it(name,nd,it)  __user_walk_it(name, LOOKUP_FOLLOW|LOOKUP_POSITIVE, nd, it)
-+#define user_path_walk_link_it(name,nd,it) __user_walk_it(name, LOOKUP_POSITIVE, nd, it)
- extern void inode_init_once(struct inode *);
- extern void iput(struct inode *);
-@@ -1538,6 +1564,8 @@ extern struct file_operations generic_ro
- extern int vfs_readlink(struct dentry *, char *, int, const char *);
- extern int vfs_follow_link(struct nameidata *, const char *);
-+extern int vfs_follow_link_it(struct nameidata *, const char *,
-+                            struct lookup_intent *it);
- extern int page_readlink(struct dentry *, char *, int);
- extern int page_follow_link(struct dentry *, struct nameidata *);
- extern struct inode_operations page_symlink_inode_operations;
---- linux-2.4.22-ac1/include/linux/fs_struct.h~vfs_intent-2.4.22-rh    2003-09-25 14:16:24.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/fs_struct.h  2003-09-25 14:42:46.000000000 +0400
-@@ -37,10 +37,12 @@ static inline void set_fs_root(struct fs
-       write_lock(&fs->lock);
-       old_root = fs->root;
-       old_rootmnt = fs->rootmnt;
-+      PIN(dentry, mnt, 1);
-       fs->rootmnt = mntget(mnt);
-       fs->root = dget(dentry);
-       write_unlock(&fs->lock);
-       if (old_root) {
-+              UNPIN(old_root, old_rootmnt, 1);
-               dput(old_root);
-               mntput(old_rootmnt);
-       }
-@@ -60,10 +62,12 @@ static inline void set_fs_pwd(struct fs_
-       write_lock(&fs->lock);
-       old_pwd = fs->pwd;
-       old_pwdmnt = fs->pwdmnt;
-+      PIN(dentry, mnt, 0);
-       fs->pwdmnt = mntget(mnt);
-       fs->pwd = dget(dentry);
-       write_unlock(&fs->lock);
-       if (old_pwd) {
-+              UNPIN(old_pwd, old_pwdmnt, 0);
-               dput(old_pwd);
-               mntput(old_pwdmnt);
-       }
---- linux-2.4.22-ac1/kernel/exit.c~vfs_intent-2.4.22-rh        2003-09-25 14:16:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/kernel/exit.c      2003-09-25 14:42:46.000000000 +0400
-@@ -342,11 +342,14 @@ static inline void __put_fs_struct(struc
- {
-       /* No need to hold fs->lock if we are killing it */
-       if (atomic_dec_and_test(&fs->count)) {
-+              UNPIN(fs->pwd, fs->pwdmnt, 0);
-+              UNPIN(fs->root, fs->rootmnt, 1);
-               dput(fs->root);
-               mntput(fs->rootmnt);
-               dput(fs->pwd);
-               mntput(fs->pwdmnt);
-               if (fs->altroot) {
-+                      UNPIN(fs->altroot, fs->altrootmnt, 1);
-                       dput(fs->altroot);
-                       mntput(fs->altrootmnt);
-               }
---- linux-2.4.22-ac1/kernel/fork.c~vfs_intent-2.4.22-rh        2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/kernel/fork.c      2003-09-25 14:42:46.000000000 +0400
-@@ -457,10 +457,13 @@ static inline struct fs_struct *__copy_f
-               fs->umask = old->umask;
-               read_lock(&old->lock);
-               fs->rootmnt = mntget(old->rootmnt);
-+              PIN(old->pwd, old->pwdmnt, 0);
-+              PIN(old->root, old->rootmnt, 1);
-               fs->root = dget(old->root);
-               fs->pwdmnt = mntget(old->pwdmnt);
-               fs->pwd = dget(old->pwd);
-               if (old->altroot) {
-+                      PIN(old->altroot, old->altrootmnt, 1);
-                       fs->altrootmnt = mntget(old->altrootmnt);
-                       fs->altroot = dget(old->altroot);
-               } else {
---- linux-2.4.22-ac1/kernel/ksyms.c~vfs_intent-2.4.22-rh       2003-09-25 14:39:02.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/kernel/ksyms.c     2003-09-25 14:42:46.000000000 +0400
-@@ -295,6 +295,7 @@ EXPORT_SYMBOL(read_cache_page);
- EXPORT_SYMBOL(set_page_dirty);
- EXPORT_SYMBOL(vfs_readlink);
- EXPORT_SYMBOL(vfs_follow_link);
-+EXPORT_SYMBOL(vfs_follow_link_it);
- EXPORT_SYMBOL(page_readlink);
- EXPORT_SYMBOL(page_follow_link);
- EXPORT_SYMBOL(page_symlink_inode_operations);
-
-_
index e00f2f3..3057402 100644 (file)
@@ -121,9 +121,9 @@ Index: linux-2.6.9-5.0.3.EL/fs/namei.c
 +      struct dentry *dentry = nd->dentry;
 +      int err, counter = 0;
 +
++ revalidate_again:
 +      if (!dentry->d_op || !dentry->d_op->d_revalidate)
 +              return 0;
-+ revalidate_again:
 +      if (!dentry->d_op->d_revalidate(dentry, nd)) {
 +              struct dentry *new;
 +              if ((err = permission(dentry->d_parent->d_inode, MAY_EXEC, nd)))
diff --git a/lustre/kernel_patches/patches/x86-fpu-crash.patch b/lustre/kernel_patches/patches/x86-fpu-crash.patch
deleted file mode 100644 (file)
index ce6b830..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-# This is a BitKeeper generated diff -Nru style patch.
-#
-# ChangeSet
-#   2004/06/14 16:05:28-03:00 marcelo@logos.cnet 
-#     Alexander Nyberg/Andi/Sergey: Fix x86 "clear_cpu()" macro.
-#   
-#   Linus's 2.6 changelog:
-#                                                                                         
-#   Fix x86 "clear_cpu()" macro.
-#                                                                                         
-#   We need to clear all exceptions before synchronizing
-#   with the FPU, since we aren't ready to handle a FP
-#   exception here and we're getting rid of all FP state.
-#                                                                                         
-#   Special thanks to Alexander Nyberg for reports and
-#   testing. Alternate patches by Sergey Vlasov and Andi
-#   Kleen, who both worked on this.
-#                                                                                         
-#   Signed-off-by: Linus Torvalds <torvalds@osdl.org>
-# 
-# include/asm-i386/i387.h
-#   2004/06/14 16:04:08-03:00 marcelo@logos.cnet +1 -1
-#   Alexander Nyberg/Andi/Sergey: Fix x86 "clear_cpu()" macro.
-# 
-diff -Nru a/include/asm-i386/i387.h b/include/asm-i386/i387.h
---- a/include/asm-i386/i387.h  2004-06-16 11:49:16 -07:00
-+++ b/include/asm-i386/i387.h  2004-06-16 11:49:16 -07:00
-@@ -34,7 +34,7 @@
- #define clear_fpu( tsk ) do { \
-       if ( tsk->flags & PF_USEDFPU ) { \
--              asm volatile("fwait"); \
-+              asm volatile("fnclex ; fwait"); \
-               tsk->flags &= ~PF_USEDFPU; \
-               stts(); \
-       } \
diff --git a/lustre/kernel_patches/patches/xattr-0.8.54-2.4.22-rh.patch b/lustre/kernel_patches/patches/xattr-0.8.54-2.4.22-rh.patch
deleted file mode 100644 (file)
index 39d40ec..0000000
+++ /dev/null
@@ -1,5396 +0,0 @@
- Documentation/Configure.help  |   66 ++
- arch/alpha/defconfig          |    7 
- arch/alpha/kernel/entry.S     |   12 
- arch/arm/defconfig            |    7 
- arch/arm/kernel/calls.S       |   24 
- arch/i386/defconfig           |    7 
- arch/ia64/defconfig           |    7 
- arch/m68k/defconfig           |    7 
- arch/mips/defconfig           |    7 
- arch/mips64/defconfig         |    7 
- arch/ppc/defconfig            |   14 
- arch/ppc64/kernel/misc.S      |    2 
- arch/s390/defconfig           |    7 
- arch/s390/kernel/entry.S      |   24 
- arch/s390x/defconfig          |    7 
- arch/s390x/kernel/entry.S     |   24 
- arch/s390x/kernel/wrapper32.S |   90 +++
- arch/sparc/defconfig          |    7 
- arch/sparc64/defconfig        |    7 
- fs/Config.in                  |   14 
- fs/Makefile                   |    3 
- fs/ext2/Makefile              |    4 
- fs/ext2/file.c                |    5 
- fs/ext2/ialloc.c              |    2 
- fs/ext2/inode.c               |   34 -
- fs/ext2/namei.c               |   14 
- fs/ext2/super.c               |   29 
- fs/ext2/symlink.c             |   14 
- fs/ext2/xattr.c               | 1212 +++++++++++++++++++++++++++++++++++++++++
- fs/ext2/xattr_user.c          |  103 +++
- fs/ext3/Makefile              |   10 
- fs/ext3/ext3-exports.c        |   13 
- fs/ext3/file.c                |    5 
- fs/ext3/ialloc.c              |    2 
- fs/ext3/inode.c               |   35 -
- fs/ext3/namei.c               |   21 
- fs/ext3/super.c               |   37 +
- fs/ext3/symlink.c             |   14 
- fs/ext3/xattr.c               | 1225 ++++++++++++++++++++++++++++++++++++++++++
- fs/ext3/xattr_user.c          |  111 +++
- fs/jfs/jfs_xattr.h            |    6 
- fs/jfs/xattr.c                |    6 
- fs/mbcache.c                  |  648 ++++++++++++++++++++++
- include/asm-arm/unistd.h      |    2 
- include/asm-ppc64/unistd.h    |    2 
- include/asm-s390/unistd.h     |   13 
- include/asm-s390x/unistd.h    |   13 
- include/linux/cache_def.h     |   15 
- include/linux/errno.h         |    4 
- include/linux/ext2_fs.h       |   31 -
- include/linux/ext2_xattr.h    |  157 +++++
- include/linux/ext3_fs.h       |   31 -
- include/linux/ext3_jbd.h      |    8 
- include/linux/ext3_xattr.h    |  157 +++++
- include/linux/fs.h            |    2 
- include/linux/mbcache.h       |   69 ++
- kernel/ksyms.c                |    4 
- mm/vmscan.c                   |   35 +
- 58 files changed, 4306 insertions(+), 137 deletions(-)
-
---- linux-2.4.22-ac1/arch/alpha/defconfig~xattr-0.8.54-2.4.22-rh       2003-06-13 18:51:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/alpha/defconfig       2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_ALPHA=y
- # CONFIG_UID16 is not set
- # CONFIG_RWSEM_GENERIC_SPINLOCK is not set
---- linux-2.4.22-ac1/arch/alpha/kernel/entry.S~xattr-0.8.54-2.4.22-rh  2003-09-25 14:16:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/alpha/kernel/entry.S  2003-09-25 23:57:02.000000000 +0400
-@@ -1158,6 +1158,18 @@ sys_call_table:
-       .quad sys_readahead
-       .quad sys_ni_syscall                    /* 380, sys_security */
-       .quad sys_tkill
-+      .quad sys_setxattr
-+      .quad sys_lsetxattr
-+      .quad sys_fsetxattr
-+      .quad sys_getxattr                      /* 385 */
-+      .quad sys_lgetxattr
-+      .quad sys_fgetxattr
-+      .quad sys_listxattr
-+      .quad sys_llistxattr
-+      .quad sys_flistxattr                    /* 390 */
-+      .quad sys_removexattr
-+      .quad sys_lremovexattr
-+      .quad sys_fremovexattr
- /* Remember to update everything, kids.  */
- .ifne (. - sys_call_table) - (NR_SYSCALLS * 8)
---- linux-2.4.22-ac1/arch/arm/defconfig~xattr-0.8.54-2.4.22-rh 2001-05-20 04:43:05.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/arm/defconfig 2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_ARM=y
- # CONFIG_EISA is not set
- # CONFIG_SBUS is not set
---- linux-2.4.22-ac1/arch/arm/kernel/calls.S~xattr-0.8.54-2.4.22-rh    2003-08-25 15:44:39.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/arm/kernel/calls.S    2003-09-26 00:00:10.000000000 +0400
-@@ -240,18 +240,18 @@ __syscall_start:
-               .long   SYMBOL_NAME(sys_ni_syscall) /* Security */
-               .long   SYMBOL_NAME(sys_gettid)
- /* 225 */     .long   SYMBOL_NAME(sys_readahead)
--              .long   SYMBOL_NAME(sys_ni_syscall) /* setxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* lsetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* fsetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* getxattr */
--/* 230 */     .long   SYMBOL_NAME(sys_ni_syscall) /* lgetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* fgetxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* listxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* llistxattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* flistxattr */
--/* 235 */     .long   SYMBOL_NAME(sys_ni_syscall) /* removexattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* lremovexattr */
--              .long   SYMBOL_NAME(sys_ni_syscall) /* fremovexattr */
-+              .long   SYMBOL_NAME(sys_setxattr)
-+              .long   SYMBOL_NAME(sys_lsetxattr)
-+              .long   SYMBOL_NAME(sys_fsetxattr)
-+              .long   SYMBOL_NAME(sys_getxattr)
-+/* 230 */     .long   SYMBOL_NAME(sys_lgetxattr)
-+              .long   SYMBOL_NAME(sys_fgetxattr)
-+              .long   SYMBOL_NAME(sys_listxattr)
-+              .long   SYMBOL_NAME(sys_llistxattr)
-+              .long   SYMBOL_NAME(sys_flistxattr)
-+/* 235 */     .long   SYMBOL_NAME(sys_removexattr)
-+              .long   SYMBOL_NAME(sys_lremovexattr)
-+              .long   SYMBOL_NAME(sys_fremovexattr)
-               .long   SYMBOL_NAME(sys_tkill)
-               .long   SYMBOL_NAME(sys_ni_syscall) /* sendfile64 */
- /* 240 */     .long   SYMBOL_NAME(sys_ni_syscall) /* futex */
---- linux-2.4.22-ac1/arch/i386/defconfig~xattr-0.8.54-2.4.22-rh        2003-09-25 14:16:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/i386/defconfig        2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_X86=y
- CONFIG_ISA=y
- # CONFIG_SBUS is not set
---- linux-2.4.22-ac1/arch/ia64/defconfig~xattr-0.8.54-2.4.22-rh        2003-08-25 15:44:39.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/ia64/defconfig        2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- #
- # Code maturity level options
---- linux-2.4.22-ac1/arch/m68k/defconfig~xattr-0.8.54-2.4.22-rh        2000-06-19 23:56:08.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/m68k/defconfig        2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_UID16=y
- #
---- linux-2.4.22-ac1/arch/mips64/defconfig~xattr-0.8.54-2.4.22-rh      2003-08-25 15:44:40.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/mips64/defconfig      2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_MIPS=y
- # CONFIG_MIPS32 is not set
- CONFIG_MIPS64=y
---- linux-2.4.22-ac1/arch/mips/defconfig~xattr-0.8.54-2.4.22-rh        2003-08-25 15:44:39.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/mips/defconfig        2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_MIPS=y
- CONFIG_MIPS32=y
- # CONFIG_MIPS64 is not set
---- linux-2.4.22-ac1/arch/ppc64/kernel/misc.S~xattr-0.8.54-2.4.22-rh   2003-08-25 15:44:40.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/ppc64/kernel/misc.S   2003-09-25 23:57:02.000000000 +0400
-@@ -805,6 +805,7 @@ _GLOBAL(sys_call_table32)
-       .llong .sys_gettid              /* 207 */
- #if 0 /* Reserved syscalls */
-       .llong .sys_tkill               /* 208 */
-+#endif
-       .llong .sys_setxattr
-       .llong .sys_lsetxattr   /* 210 */
-       .llong .sys_fsetxattr
-@@ -817,6 +818,7 @@ _GLOBAL(sys_call_table32)
-       .llong .sys_removexattr
-       .llong .sys_lremovexattr
-       .llong .sys_fremovexattr        /* 220 */
-+#if 0 /* Reserved syscalls */
-       .llong .sys_futex
- #endif
-       .llong .sys_perfmonctl   /* Put this here for now ... */
---- linux-2.4.22-ac1/arch/ppc/defconfig~xattr-0.8.54-2.4.22-rh 2003-06-13 18:51:31.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/ppc/defconfig 2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_UID16 is not set
- # CONFIG_RWSEM_GENERIC_SPINLOCK is not set
- CONFIG_RWSEM_XCHGADD_ALGORITHM=y
---- linux-2.4.22-ac1/arch/s390/defconfig~xattr-0.8.54-2.4.22-rh        2003-09-25 14:16:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/s390/defconfig        2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_ISA is not set
- # CONFIG_EISA is not set
- # CONFIG_MCA is not set
---- linux-2.4.22-ac1/arch/s390/kernel/entry.S~xattr-0.8.54-2.4.22-rh   2003-09-25 14:16:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/s390/kernel/entry.S   2003-09-25 23:57:02.000000000 +0400
-@@ -559,18 +559,18 @@ sys_call_table:
-         .long  sys_fcntl64 
-       .long  sys_readahead
-       .long  sys_ni_syscall
--      .long  sys_ni_syscall            /* 224 - reserved for setxattr  */
--      .long  sys_ni_syscall            /* 225 - reserved for lsetxattr */
--      .long  sys_ni_syscall            /* 226 - reserved for fsetxattr */
--      .long  sys_ni_syscall            /* 227 - reserved for getxattr  */
--      .long  sys_ni_syscall            /* 228 - reserved for lgetxattr */
--      .long  sys_ni_syscall            /* 229 - reserved for fgetxattr */
--      .long  sys_ni_syscall            /* 230 - reserved for listxattr */
--      .long  sys_ni_syscall            /* 231 - reserved for llistxattr */
--      .long  sys_ni_syscall            /* 232 - reserved for flistxattr */
--      .long  sys_ni_syscall            /* 233 - reserved for removexattr */
--      .long  sys_ni_syscall            /* 234 - reserved for lremovexattr */
--      .long  sys_ni_syscall            /* 235 - reserved for fremovexattr */
-+      .long  sys_setxattr
-+      .long  sys_lsetxattr            /* 225 */
-+      .long  sys_fsetxattr
-+      .long  sys_getxattr
-+      .long  sys_lgetxattr
-+      .long  sys_fgetxattr
-+      .long  sys_listxattr            /* 230 */
-+      .long  sys_llistxattr
-+      .long  sys_flistxattr
-+      .long  sys_removexattr
-+      .long  sys_lremovexattr
-+      .long  sys_fremovexattr         /* 235 */
-       .long  sys_gettid
-       .long  sys_tkill
-       .rept  255-237
---- linux-2.4.22-ac1/arch/s390x/defconfig~xattr-0.8.54-2.4.22-rh       2003-09-25 14:16:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/s390x/defconfig       2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- # CONFIG_ISA is not set
- # CONFIG_EISA is not set
- # CONFIG_MCA is not set
---- linux-2.4.22-ac1/arch/s390x/kernel/entry.S~xattr-0.8.54-2.4.22-rh  2003-09-25 14:16:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/s390x/kernel/entry.S  2003-09-25 23:57:02.000000000 +0400
-@@ -591,18 +591,18 @@ sys_call_table:
-       .long  SYSCALL(sys_ni_syscall,sys32_fcntl64_wrapper)
-       .long  SYSCALL(sys_readahead,sys32_readahead)
-       .long  SYSCALL(sys_ni_syscall,sys_ni_syscall)
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 224 - reserved for setxattr  */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 225 - reserved for lsetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 226 - reserved for fsetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 227 - reserved for getxattr  */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 228 - reserved for lgetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 229 - reserved for fgetxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 230 - reserved for listxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 231 - reserved for llistxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 232 - reserved for flistxattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 233 - reserved for removexattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 234 - reserved for lremovexattr */
--      .long  SYSCALL(sys_ni_syscall,sys_ni_syscall) /* 235 - reserved for fremovexattr */
-+      .long  SYSCALL(sys_setxattr,sys32_setxattr_wrapper)
-+      .long  SYSCALL(sys_lsetxattr,sys32_lsetxattr_wrapper)   /* 225 */
-+      .long  SYSCALL(sys_fsetxattr,sys32_fsetxattr_wrapper)
-+      .long  SYSCALL(sys_getxattr,sys32_getxattr_wrapper)
-+      .long  SYSCALL(sys_lgetxattr,sys32_lgetxattr_wrapper)
-+      .long  SYSCALL(sys_fgetxattr,sys32_fgetxattr_wrapper)
-+      .long  SYSCALL(sys_listxattr,sys32_listxattr_wrapper)   /* 230 */
-+      .long  SYSCALL(sys_llistxattr,sys32_llistxattr_wrapper)
-+      .long  SYSCALL(sys_flistxattr,sys32_flistxattr_wrapper)
-+      .long  SYSCALL(sys_removexattr,sys32_removexattr_wrapper)
-+      .long  SYSCALL(sys_lremovexattr,sys32_lremovexattr_wrapper)
-+      .long  SYSCALL(sys_fremovexattr,sys32_fremovexattr_wrapper)/* 235 */
-       .long  SYSCALL(sys_gettid,sys_gettid)
-       .long  SYSCALL(sys_tkill,sys_tkill)
-       .rept  255-237
---- linux-2.4.22-ac1/arch/s390x/kernel/wrapper32.S~xattr-0.8.54-2.4.22-rh      2003-08-25 15:44:40.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/s390x/kernel/wrapper32.S      2003-09-26 00:05:14.000000000 +0400
-@@ -1097,6 +1097,96 @@ sys32_fstat64_wrapper:
-       llgtr   %r3,%r3                 # struct stat64 *
-       llgfr   %r4,%r4                 # long
-       jg      sys32_fstat64           # branch to system call
-+ 
-+      .globl  sys32_setxattr_wrapper
-+sys32_setxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_setxattr
-+
-+      .globl  sys32_lsetxattr_wrapper
-+sys32_lsetxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_lsetxattr
-+
-+      .globl  sys32_fsetxattr_wrapper
-+sys32_fsetxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      lgfr    %r6,%r6                 # int
-+      jg      sys_fsetxattr
-+
-+      .globl  sys32_getxattr_wrapper
-+sys32_getxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_getxattr
-+
-+      .globl  sys32_lgetxattr_wrapper
-+sys32_lgetxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_lgetxattr
-+
-+      .globl  sys32_fgetxattr_wrapper
-+sys32_fgetxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgtr   %r4,%r4                 # void *
-+      llgfr   %r5,%r5                 # size_t
-+      jg      sys_fgetxattr
-+ 
-+      .globl  sys32_listxattr_wrapper
-+sys32_listxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_listxattr
-+
-+      .globl  sys32_llistxattr_wrapper
-+sys32_llistxattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_llistxattr
-+
-+      .globl  sys32_flistxattr_wrapper
-+sys32_flistxattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      llgfr   %r4,%r4                 # size_t
-+      jg      sys_flistxattr
-+
-+      .globl  sys32_removexattr_wrapper
-+sys32_removexattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_removexattr
-+
-+      .globl  sys32_lremovexattr_wrapper
-+sys32_lremovexattr_wrapper:
-+      llgtr   %r2,%r2                 # char *
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_lremovexattr
-+
-+      .globl  sys32_fremovexattr_wrapper
-+sys32_fremovexattr_wrapper:
-+      lgfr    %r2,%r2                 # int
-+      llgtr   %r3,%r3                 # char *
-+      jg      sys_fremovexattr
-       .globl  sys32_stime_wrapper
- sys32_stime_wrapper:
---- linux-2.4.22-ac1/arch/sparc64/defconfig~xattr-0.8.54-2.4.22-rh     2003-08-25 15:44:40.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/sparc64/defconfig     2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- #
- # Code maturity level options
---- linux-2.4.22-ac1/arch/sparc/defconfig~xattr-0.8.54-2.4.22-rh       2002-08-03 04:39:43.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/arch/sparc/defconfig       2003-09-25 23:57:02.000000000 +0400
-@@ -1,6 +1,13 @@
- #
- # Automatically generated make config: don't edit
- #
-+CONFIG_EXT3_FS_XATTR=y
-+# CONFIG_EXT3_FS_XATTR_SHARING is not set
-+# CONFIG_EXT3_FS_XATTR_USER is not set
-+# CONFIG_EXT2_FS_XATTR is not set
-+# CONFIG_EXT2_FS_XATTR_SHARING is not set
-+# CONFIG_EXT2_FS_XATTR_USER is not set
-+# CONFIG_FS_MBCACHE is not set
- CONFIG_UID16=y
- CONFIG_HIGHMEM=y
---- linux-2.4.22-ac1/Documentation/Configure.help~xattr-0.8.54-2.4.22-rh       2003-09-25 14:16:30.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/Documentation/Configure.help       2003-09-25 23:57:02.000000000 +0400
-@@ -16145,6 +16145,39 @@ CONFIG_EXT2_FS
-   be compiled as a module, and so this could be dangerous.  Most
-   everyone wants to say Y here.
-+Ext2 extended attributes
-+CONFIG_EXT2_FS_XATTR
-+  Extended attributes are name:value pairs associated with inodes by
-+  the kernel or by users (see the attr(5) manual page, or visit
-+  <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext2 extended attribute block sharing
-+CONFIG_EXT2_FS_XATTR_SHARING
-+  This options enables code for sharing identical extended attribute
-+  blocks among multiple inodes.
-+
-+  Usually, say Y.
-+
-+Ext2 extended user attributes
-+CONFIG_EXT2_FS_XATTR_USER
-+  This option enables extended user attributes on ext2. Processes can
-+  associate extended user attributes with inodes to store additional
-+  information such as the character encoding of files, etc. (see the
-+  attr(5) manual page, or visit <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext2 trusted extended attributes
-+CONFIG_EXT2_FS_XATTR_TRUSTED
-+  This option enables extended attributes on ext2 that are accessible
-+  (and visible) only to users capable of CAP_SYS_ADMIN. Usually this
-+  is only the super user. Trusted extended attributes are meant for
-+  implementing system/security services.
-+
-+  If unsure, say N.
-+
- Ext3 journalling file system support (EXPERIMENTAL)
- CONFIG_EXT3_FS
-   This is the journalling version of the Second extended file system
-@@ -16177,6 +16210,39 @@ CONFIG_EXT3_FS
-   of your root partition (the one containing the directory /) cannot
-   be compiled as a module, and so this may be dangerous.
-+Ext3 extended attributes
-+CONFIG_EXT3_FS_XATTR
-+  Extended attributes are name:value pairs associated with inodes by
-+  the kernel or by users (see the attr(5) manual page, or visit
-+  <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext3 extended attribute block sharing
-+CONFIG_EXT3_FS_XATTR_SHARING
-+  This options enables code for sharing identical extended attribute
-+  blocks among multiple inodes.
-+
-+  Usually, say Y.
-+
-+Ext3 extended user attributes
-+CONFIG_EXT3_FS_XATTR_USER
-+  This option enables extended user attributes on ext3. Processes can
-+  associate extended user attributes with inodes to store additional
-+  information such as the character encoding of files, etc. (see the
-+  attr(5) manual page, or visit <http://acl.bestbits.at/> for details).
-+
-+  If unsure, say N.
-+
-+Ext3 trusted extended attributes
-+CONFIG_EXT3_FS_XATTR_TRUSTED
-+  This option enables extended attributes on ext3 that are accessible
-+  (and visible) only to users capable of CAP_SYS_ADMIN. Usually this
-+  is only the super user. Trusted extended attributes are meant for
-+  implementing system/security services.
-+
-+  If unsure, say N.
-+
- Journal Block Device support (JBD for ext3) (EXPERIMENTAL)
- CONFIG_JBD
-   This is a generic journalling layer for block devices.  It is
---- linux-2.4.22-ac1/fs/Config.in~xattr-0.8.54-2.4.22-rh       2003-09-25 14:16:23.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/Config.in       2003-09-25 23:57:02.000000000 +0400
-@@ -29,6 +29,11 @@ dep_mbool '  Debug Befs' CONFIG_BEFS_DEB
- dep_tristate 'BFS file system support (EXPERIMENTAL)' CONFIG_BFS_FS $CONFIG_EXPERIMENTAL
- tristate 'Ext3 journalling file system support' CONFIG_EXT3_FS
-+dep_mbool '  Ext3 extended attributes' CONFIG_EXT3_FS_XATTR $CONFIG_EXT3_FS
-+dep_bool '    Ext3 extended attribute block sharing' \
-+    CONFIG_EXT3_FS_XATTR_SHARING $CONFIG_EXT3_FS_XATTR
-+dep_bool '    Ext3 extended user attributes' \
-+    CONFIG_EXT3_FS_XATTR_USER $CONFIG_EXT3_FS_XATTR
- # CONFIG_JBD could be its own option (even modular), but until there are
- # other users than ext3, we will simply make it be the same as CONFIG_EXT3_FS
- # dep_tristate '  Journal Block Device support (JBD for ext3)' CONFIG_JBD $CONFIG_EXT3_FS
-@@ -88,6 +93,11 @@ dep_mbool '  QNX4FS write support (DANGE
- tristate 'ROM file system support' CONFIG_ROMFS_FS
- tristate 'Second extended fs support' CONFIG_EXT2_FS
-+dep_mbool '  Ext2 extended attributes' CONFIG_EXT2_FS_XATTR $CONFIG_EXT2_FS
-+dep_bool '    Ext2 extended attribute block sharing' \
-+    CONFIG_EXT2_FS_XATTR_SHARING $CONFIG_EXT2_FS_XATTR
-+dep_bool '    Ext2 extended user attributes' \
-+    CONFIG_EXT2_FS_XATTR_USER $CONFIG_EXT2_FS_XATTR
- tristate 'System V/Xenix/V7/Coherent file system support' CONFIG_SYSV_FS
-@@ -164,6 +174,10 @@ else
-    define_tristate CONFIG_ZISOFS_FS n
- fi
-+# Meta block cache for Extended Attributes (ext2/ext3)
-+#tristate 'Meta block cache' CONFIG_FS_MBCACHE
-+define_tristate CONFIG_FS_MBCACHE y 
-+
- mainmenu_option next_comment
- comment 'Partition Types'
- source fs/partitions/Config.in
---- linux-2.4.22-ac1/fs/ext2/file.c~xattr-0.8.54-2.4.22-rh     2001-10-11 19:05:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext2/file.c     2003-09-25 23:57:02.000000000 +0400
-@@ -20,6 +20,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/sched.h>
- /*
-@@ -51,4 +52,8 @@ struct file_operations ext2_file_operati
- struct inode_operations ext2_file_inode_operations = {
-       truncate:       ext2_truncate,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- linux-2.4.22-ac1/fs/ext2/ialloc.c~xattr-0.8.54-2.4.22-rh   2003-06-13 18:51:37.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext2/ialloc.c   2003-09-25 23:57:02.000000000 +0400
-@@ -15,6 +15,7 @@
- #include <linux/config.h>
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/locks.h>
- #include <linux/quotaops.h>
-@@ -167,6 +168,7 @@ void ext2_free_inode (struct inode * ino
-        */
-       if (!is_bad_inode(inode)) {
-               /* Quota is already initialized in iput() */
-+              ext2_xattr_delete_inode(inode);
-               DQUOT_FREE_INODE(inode);
-               DQUOT_DROP(inode);
-       }
---- linux-2.4.22-ac1/fs/ext2/inode.c~xattr-0.8.54-2.4.22-rh    2003-06-13 18:51:37.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext2/inode.c    2003-09-25 23:57:02.000000000 +0400
-@@ -39,6 +39,18 @@ MODULE_LICENSE("GPL");
- static int ext2_update_inode(struct inode * inode, int do_sync);
- /*
-+ * Test whether an inode is a fast symlink.
-+ */
-+static inline int ext2_inode_is_fast_symlink(struct inode *inode)
-+{
-+      int ea_blocks = inode->u.ext2_i.i_file_acl ?
-+              (inode->i_sb->s_blocksize >> 9) : 0;
-+
-+      return (S_ISLNK(inode->i_mode) &&
-+              inode->i_blocks - ea_blocks == 0);
-+}
-+
-+/*
-  * Called at each iput()
-  */
- void ext2_put_inode (struct inode * inode)
-@@ -53,9 +65,7 @@ void ext2_delete_inode (struct inode * i
- {
-       lock_kernel();
--      if (is_bad_inode(inode) ||
--          inode->i_ino == EXT2_ACL_IDX_INO ||
--          inode->i_ino == EXT2_ACL_DATA_INO)
-+      if (is_bad_inode(inode))
-               goto no_delete;
-       inode->u.ext2_i.i_dtime = CURRENT_TIME;
-       mark_inode_dirty(inode);
-@@ -801,6 +811,8 @@ void ext2_truncate (struct inode * inode
-       if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
-           S_ISLNK(inode->i_mode)))
-               return;
-+      if (ext2_inode_is_fast_symlink(inode))
-+              return;
-       if (IS_APPEND(inode) || IS_IMMUTABLE(inode))
-               return;
-@@ -903,8 +915,7 @@ void ext2_read_inode (struct inode * ino
-       unsigned long offset;
-       struct ext2_group_desc * gdp;
--      if ((inode->i_ino != EXT2_ROOT_INO && inode->i_ino != EXT2_ACL_IDX_INO &&
--           inode->i_ino != EXT2_ACL_DATA_INO &&
-+      if ((inode->i_ino != EXT2_ROOT_INO &&
-            inode->i_ino < EXT2_FIRST_INO(inode->i_sb)) ||
-           inode->i_ino > le32_to_cpu(inode->i_sb->u.ext2_sb.s_es->s_inodes_count)) {
-               ext2_error (inode->i_sb, "ext2_read_inode",
-@@ -989,10 +1000,7 @@ void ext2_read_inode (struct inode * ino
-       for (block = 0; block < EXT2_N_BLOCKS; block++)
-               inode->u.ext2_i.i_data[block] = raw_inode->i_block[block];
--      if (inode->i_ino == EXT2_ACL_IDX_INO ||
--          inode->i_ino == EXT2_ACL_DATA_INO)
--              /* Nothing to do */ ;
--      else if (S_ISREG(inode->i_mode)) {
-+      if (S_ISREG(inode->i_mode)) {
-               inode->i_op = &ext2_file_inode_operations;
-               inode->i_fop = &ext2_file_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-@@ -1001,15 +1009,17 @@ void ext2_read_inode (struct inode * ino
-               inode->i_fop = &ext2_dir_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-       } else if (S_ISLNK(inode->i_mode)) {
--              if (!inode->i_blocks)
-+              if (ext2_inode_is_fast_symlink(inode))
-                       inode->i_op = &ext2_fast_symlink_inode_operations;
-               else {
--                      inode->i_op = &page_symlink_inode_operations;
-+                      inode->i_op = &ext2_symlink_inode_operations;
-                       inode->i_mapping->a_ops = &ext2_aops;
-               }
--      } else 
-+      } else {
-+              inode->i_op = &ext2_special_inode_operations;
-               init_special_inode(inode, inode->i_mode,
-                                  le32_to_cpu(raw_inode->i_block[0]));
-+      }
-       brelse (bh);
-       inode->i_attr_flags = 0;
-       ext2_set_inode_flags(inode);
---- linux-2.4.22-ac1/fs/ext2/Makefile~xattr-0.8.54-2.4.22-rh   2001-10-11 19:05:18.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext2/Makefile   2003-09-25 23:57:02.000000000 +0400
-@@ -13,4 +13,8 @@ obj-y    := balloc.o bitmap.o dir.o file
-               ioctl.o namei.o super.o symlink.o
- obj-m    := $(O_TARGET)
-+export-objs += xattr.o
-+obj-$(CONFIG_EXT2_FS_XATTR) += xattr.o
-+obj-$(CONFIG_EXT2_FS_XATTR_USER) += xattr_user.o
-+
- include $(TOPDIR)/Rules.make
---- linux-2.4.22-ac1/fs/ext2/namei.c~xattr-0.8.54-2.4.22-rh    2001-10-04 09:57:36.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext2/namei.c    2003-09-25 23:57:02.000000000 +0400
-@@ -31,6 +31,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/pagemap.h>
- /*
-@@ -136,7 +137,7 @@ static int ext2_symlink (struct inode * 
-       if (l > sizeof (inode->u.ext2_i.i_data)) {
-               /* slow symlink */
--              inode->i_op = &page_symlink_inode_operations;
-+              inode->i_op = &ext2_symlink_inode_operations;
-               inode->i_mapping->a_ops = &ext2_aops;
-               err = block_symlink(inode, symname, l);
-               if (err)
-@@ -345,4 +346,15 @@ struct inode_operations ext2_dir_inode_o
-       rmdir:          ext2_rmdir,
-       mknod:          ext2_mknod,
-       rename:         ext2_rename,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
-+};
-+
-+struct inode_operations ext2_special_inode_operations = {
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- linux-2.4.22-ac1/fs/ext2/super.c~xattr-0.8.54-2.4.22-rh    2002-11-29 02:53:15.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/ext2/super.c    2003-09-25 23:57:02.000000000 +0400
-@@ -21,6 +21,7 @@
- #include <linux/string.h>
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- #include <linux/slab.h>
- #include <linux/init.h>
- #include <linux/locks.h>
-@@ -125,6 +126,7 @@ void ext2_put_super (struct super_block 
-       int db_count;
-       int i;
-+      ext2_xattr_put_super(sb);
-       if (!(sb->s_flags & MS_RDONLY)) {
-               struct ext2_super_block *es = EXT2_SB(sb)->s_es;
-@@ -175,6 +177,13 @@ static int parse_options (char * options
-            this_char = strtok (NULL, ",")) {
-               if ((value = strchr (this_char, '=')) != NULL)
-                       *value++ = 0;
-+#ifdef CONFIG_EXT2_FS_XATTR_USER
-+              if (!strcmp (this_char, "user_xattr"))
-+                      set_opt (*mount_options, XATTR_USER);
-+              else if (!strcmp (this_char, "nouser_xattr"))
-+                      clear_opt (*mount_options, XATTR_USER);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -424,6 +433,9 @@ struct super_block * ext2_read_super (st
-           blocksize = BLOCK_SIZE;
-       sb->u.ext2_sb.s_mount_opt = 0;
-+#ifdef CONFIG_EXT2_FS_XATTR_USER
-+      /* set_opt (sb->u.ext2_sb.s_mount_opt, XATTR_USER); */
-+#endif
-       if (!parse_options ((char *) data, &sb_block, &resuid, &resgid,
-           &sb->u.ext2_sb.s_mount_opt)) {
-               return NULL;
-@@ -813,12 +825,27 @@ static DECLARE_FSTYPE_DEV(ext2_fs_type, 
- static int __init init_ext2_fs(void)
- {
--        return register_filesystem(&ext2_fs_type);
-+      int error = init_ext2_xattr();
-+      if (error)
-+              return error;
-+      error = init_ext2_xattr_user();
-+      if (error)
-+              goto fail;
-+      error = register_filesystem(&ext2_fs_type);
-+      if (!error)
-+              return 0;
-+
-+      exit_ext2_xattr_user();
-+fail:
-+      exit_ext2_xattr();
-+      return error;
- }
- static void __exit exit_ext2_fs(void)
- {
-       unregister_filesystem(&ext2_fs_type);
-+      exit_ext2_xattr_user();
-+      exit_ext2_xattr();
- }
- EXPORT_NO_SYMBOLS;
---- linux-2.4.22-ac1/fs/ext2/symlink.c~xattr-0.8.54-2.4.22-rh  2000-09-28 00:41:33.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext2/symlink.c  2003-09-25 23:57:02.000000000 +0400
-@@ -19,6 +19,7 @@
- #include <linux/fs.h>
- #include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
- static int ext2_readlink(struct dentry *dentry, char *buffer, int buflen)
- {
-@@ -32,7 +33,20 @@ static int ext2_follow_link(struct dentr
-       return vfs_follow_link(nd, s);
- }
-+struct inode_operations ext2_symlink_inode_operations = {
-+      readlink:       page_readlink,
-+      follow_link:    page_follow_link,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
-+};
-+
- struct inode_operations ext2_fast_symlink_inode_operations = {
-       readlink:       ext2_readlink,
-       follow_link:    ext2_follow_link,
-+      setxattr:       ext2_setxattr,
-+      getxattr:       ext2_getxattr,
-+      listxattr:      ext2_listxattr,
-+      removexattr:    ext2_removexattr,
- };
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/ext2/xattr.c    2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,1212 @@
-+/*
-+ * linux/fs/ext2/xattr.c
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ *
-+ * Fix by Harrison Xing <harrison@mountainviewdata.com>.
-+ * Extended attributes for symlinks and special files added per
-+ *  suggestion of Luka Renko <luka.renko@hermes.si>.
-+ */
-+
-+/*
-+ * Extended attributes are stored on disk blocks allocated outside of
-+ * any inode. The i_file_acl field is then made to point to this allocated
-+ * block. If all extended attributes of an inode are identical, these
-+ * inodes may share the same extended attribute block. Such situations
-+ * are automatically detected by keeping a cache of recent attribute block
-+ * numbers and hashes over the block's contents in memory.
-+ *
-+ *
-+ * Extended attribute block layout:
-+ *
-+ *   +------------------+
-+ *   | header           |
-+ *   | entry 1          | |
-+ *   | entry 2          | | growing downwards
-+ *   | entry 3          | v
-+ *   | four null bytes  |
-+ *   | . . .            |
-+ *   | value 1          | ^
-+ *   | value 3          | | growing upwards
-+ *   | value 2          | |
-+ *   +------------------+
-+ *
-+ * The block header is followed by multiple entry descriptors. These entry
-+ * descriptors are variable in size, and alligned to EXT2_XATTR_PAD
-+ * byte boundaries. The entry descriptors are sorted by attribute name,
-+ * so that two extended attribute blocks can be compared efficiently.
-+ *
-+ * Attribute values are aligned to the end of the block, stored in
-+ * no specific order. They are also padded to EXT2_XATTR_PAD byte
-+ * boundaries. No additional gaps are left between them.
-+ *
-+ * Locking strategy
-+ * ----------------
-+ * The VFS already holds the BKL and the inode->i_sem semaphore when any of
-+ * the xattr inode operations are called, so we are guaranteed that only one
-+ * processes accesses extended attributes of an inode at any time.
-+ *
-+ * For writing we also grab the ext2_xattr_sem semaphore. This ensures that
-+ * only a single process is modifying an extended attribute block, even
-+ * if the block is shared among inodes.
-+ *
-+ * Note for porting to 2.5
-+ * -----------------------
-+ * The BKL will no longer be held in the xattr inode operations.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/locks.h>
-+#include <linux/slab.h>
-+#include <linux/fs.h>
-+#include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
-+#include <linux/mbcache.h>
-+#include <linux/quotaops.h>
-+#include <asm/semaphore.h>
-+#include <linux/compatmac.h>
-+
-+/* These symbols may be needed by a module. */
-+EXPORT_SYMBOL(ext2_xattr_register);
-+EXPORT_SYMBOL(ext2_xattr_unregister);
-+EXPORT_SYMBOL(ext2_xattr_get);
-+EXPORT_SYMBOL(ext2_xattr_list);
-+EXPORT_SYMBOL(ext2_xattr_set);
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+# define mark_buffer_dirty(bh) mark_buffer_dirty(bh, 1)
-+#endif
-+
-+#define HDR(bh) ((struct ext2_xattr_header *)((bh)->b_data))
-+#define ENTRY(ptr) ((struct ext2_xattr_entry *)(ptr))
-+#define FIRST_ENTRY(bh) ENTRY(HDR(bh)+1)
-+#define IS_LAST_ENTRY(entry) (*(__u32 *)(entry) == 0)
-+
-+#ifdef EXT2_XATTR_DEBUG
-+# define ea_idebug(inode, f...) do { \
-+              printk(KERN_DEBUG "inode %s:%ld: ", \
-+                      kdevname(inode->i_dev), inode->i_ino); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+# define ea_bdebug(bh, f...) do { \
-+              printk(KERN_DEBUG "block %s:%ld: ", \
-+                      kdevname(bh->b_dev), bh->b_blocknr); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+#else
-+# define ea_idebug(f...)
-+# define ea_bdebug(f...)
-+#endif
-+
-+static int ext2_xattr_set2(struct inode *, struct buffer_head *,
-+                         struct ext2_xattr_header *);
-+
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+
-+static int ext2_xattr_cache_insert(struct buffer_head *);
-+static struct buffer_head *ext2_xattr_cache_find(struct inode *,
-+                                               struct ext2_xattr_header *);
-+static void ext2_xattr_cache_remove(struct buffer_head *);
-+static void ext2_xattr_rehash(struct ext2_xattr_header *,
-+                            struct ext2_xattr_entry *);
-+
-+static struct mb_cache *ext2_xattr_cache;
-+
-+#else
-+# define ext2_xattr_cache_insert(bh) 0
-+# define ext2_xattr_cache_find(inode, header) NULL
-+# define ext2_xattr_cache_remove(bh) while(0) {}
-+# define ext2_xattr_rehash(header, entry) while(0) {}
-+#endif
-+
-+/*
-+ * If a file system does not share extended attributes among inodes,
-+ * we should not need the ext2_xattr_sem semaphore. However, the
-+ * filesystem may still contain shared blocks, so we always take
-+ * the lock.
-+ */
-+
-+DECLARE_MUTEX(ext2_xattr_sem);
-+
-+static inline int
-+ext2_xattr_new_block(struct inode *inode, int * errp, int force)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      int goal = le32_to_cpu(EXT2_SB(sb)->s_es->s_first_data_block) +
-+              EXT2_I(inode)->i_block_group * EXT2_BLOCKS_PER_GROUP(sb);
-+
-+      /* How can we enforce the allocation? */
-+      int block = ext2_new_block(inode, goal, 0, 0, errp);
-+#ifdef OLD_QUOTAS
-+      if (!*errp)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#endif
-+      return block;
-+}
-+
-+static inline int
-+ext2_xattr_quota_alloc(struct inode *inode, int force)
-+{
-+      /* How can we enforce the allocation? */
-+#ifdef OLD_QUOTAS
-+      int error = DQUOT_ALLOC_BLOCK(inode->i_sb, inode, 1);
-+      if (!error)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#else
-+      int error = DQUOT_ALLOC_BLOCK(inode, 1);
-+#endif
-+      return error;
-+}
-+
-+#ifdef OLD_QUOTAS
-+
-+static inline void
-+ext2_xattr_quota_free(struct inode *inode)
-+{
-+      DQUOT_FREE_BLOCK(inode->i_sb, inode, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+static inline void
-+ext2_xattr_free_block(struct inode * inode, unsigned long block)
-+{
-+      ext2_free_blocks(inode, block, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+#else
-+# define ext2_xattr_quota_free(inode) \
-+      DQUOT_FREE_BLOCK(inode, 1)
-+# define ext2_xattr_free_block(inode, block) \
-+      ext2_free_blocks(inode, block, 1)
-+#endif
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,18)
-+
-+static inline struct buffer_head *
-+sb_bread(struct super_block *sb, int block)
-+{
-+      return bread(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+static inline struct buffer_head *
-+sb_getblk(struct super_block *sb, int block)
-+{
-+      return getblk(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+#endif
-+
-+struct ext2_xattr_handler *ext2_xattr_handlers[EXT2_XATTR_INDEX_MAX];
-+rwlock_t ext2_handler_lock = RW_LOCK_UNLOCKED;
-+
-+int
-+ext2_xattr_register(int name_index, struct ext2_xattr_handler *handler)
-+{
-+      int error = -EINVAL;
-+
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              write_lock(&ext2_handler_lock);
-+              if (!ext2_xattr_handlers[name_index-1]) {
-+                      ext2_xattr_handlers[name_index-1] = handler;
-+                      error = 0;
-+              }
-+              write_unlock(&ext2_handler_lock);
-+      }
-+      return error;
-+}
-+
-+void
-+ext2_xattr_unregister(int name_index, struct ext2_xattr_handler *handler)
-+{
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              write_lock(&ext2_handler_lock);
-+              ext2_xattr_handlers[name_index-1] = NULL;
-+              write_unlock(&ext2_handler_lock);
-+      }
-+}
-+
-+static inline const char *
-+strcmp_prefix(const char *a, const char *a_prefix)
-+{
-+      while (*a_prefix && *a == *a_prefix) {
-+              a++;
-+              a_prefix++;
-+      }
-+      return *a_prefix ? NULL : a;
-+}
-+
-+/*
-+ * Decode the extended attribute name, and translate it into
-+ * the name_index and name suffix.
-+ */
-+static struct ext2_xattr_handler *
-+ext2_xattr_resolve_name(const char **name)
-+{
-+      struct ext2_xattr_handler *handler = NULL;
-+      int i;
-+
-+      if (!*name)
-+              return NULL;
-+      read_lock(&ext2_handler_lock);
-+      for (i=0; i<EXT2_XATTR_INDEX_MAX; i++) {
-+              if (ext2_xattr_handlers[i]) {
-+                      const char *n = strcmp_prefix(*name,
-+                              ext2_xattr_handlers[i]->prefix);
-+                      if (n) {
-+                              handler = ext2_xattr_handlers[i];
-+                              *name = n;
-+                              break;
-+                      }
-+              }
-+      }
-+      read_unlock(&ext2_handler_lock);
-+      return handler;
-+}
-+
-+static inline struct ext2_xattr_handler *
-+ext2_xattr_handler(int name_index)
-+{
-+      struct ext2_xattr_handler *handler = NULL;
-+      if (name_index > 0 && name_index <= EXT2_XATTR_INDEX_MAX) {
-+              read_lock(&ext2_handler_lock);
-+              handler = ext2_xattr_handlers[name_index-1];
-+              read_unlock(&ext2_handler_lock);
-+      }
-+      return handler;
-+}
-+
-+/*
-+ * Inode operation getxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext2_getxattr(struct dentry *dentry, const char *name,
-+            void *buffer, size_t size)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->get(inode, name, buffer, size);
-+}
-+
-+/*
-+ * Inode operation listxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext2_listxattr(struct dentry *dentry, char *buffer, size_t size)
-+{
-+      return ext2_xattr_list(dentry->d_inode, buffer, size);
-+}
-+
-+/*
-+ * Inode operation setxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext2_setxattr(struct dentry *dentry, const char *name,
-+            const void *value, size_t size, int flags)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      if (size == 0)
-+              value = "";  /* empty EA, do not remove */
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, value, size, flags);
-+}
-+
-+/*
-+ * Inode operation removexattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext2_removexattr(struct dentry *dentry, const char *name)
-+{
-+      struct ext2_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext2_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, NULL, 0, XATTR_REPLACE);
-+}
-+
-+/*
-+ * ext2_xattr_get()
-+ *
-+ * Copy an extended attribute into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext2_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_entry *entry;
-+      unsigned int block, size;
-+      char *end;
-+      int name_len, error;
-+
-+      ea_idebug(inode, "name=%d.%s, buffer=%p, buffer_size=%ld",
-+                name_index, name, buffer, (long)buffer_size);
-+
-+      if (name == NULL)
-+              return -EINVAL;
-+      if (!EXT2_I(inode)->i_file_acl)
-+              return -ENOATTR;
-+      block = EXT2_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext2_error(inode->i_sb, "ext2_xattr_get",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* find named attribute */
-+      name_len = strlen(name);
-+
-+      error = -ERANGE;
-+      if (name_len > 255)
-+              goto cleanup;
-+      entry = FIRST_ENTRY(bh);
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              if (name_index == entry->e_name_index &&
-+                  name_len == entry->e_name_len &&
-+                  memcmp(name, entry->e_name, name_len) == 0)
-+                      goto found;
-+              entry = next;
-+      }
-+      /* Check the remaining name entries */
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              entry = next;
-+      }
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      error = -ENOATTR;
-+      goto cleanup;
-+found:
-+      /* check the buffer size */
-+      if (entry->e_value_block != 0)
-+              goto bad_block;
-+      size = le32_to_cpu(entry->e_value_size);
-+      if (size > inode->i_sb->s_blocksize ||
-+          le16_to_cpu(entry->e_value_offs) + size > inode->i_sb->s_blocksize)
-+              goto bad_block;
-+
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (buffer) {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+              /* return value of attribute */
-+              memcpy(buffer, bh->b_data + le16_to_cpu(entry->e_value_offs),
-+                      size);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_list()
-+ *
-+ * Copy a list of attribute names into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext2_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_entry *entry;
-+      unsigned int block, size = 0;
-+      char *buf, *end;
-+      int error;
-+
-+      ea_idebug(inode, "buffer=%p, buffer_size=%ld",
-+                buffer, (long)buffer_size);
-+
-+      if (!EXT2_I(inode)->i_file_acl)
-+              return 0;
-+      block = EXT2_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext2_error(inode->i_sb, "ext2_xattr_list",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* compute the size required for the list of attribute names */
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT2_XATTR_NEXT(entry)) {
-+              struct ext2_xattr_handler *handler;
-+              struct ext2_xattr_entry *next =
-+                      EXT2_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+
-+              handler = ext2_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      size += handler->list(NULL, inode, entry->e_name,
-+                                            entry->e_name_len);
-+      }
-+
-+      if (ext2_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (!buffer) {
-+              error = size;
-+              goto cleanup;
-+      } else {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+      }
-+
-+      /* list the attribute names */
-+      buf = buffer;
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT2_XATTR_NEXT(entry)) {
-+              struct ext2_xattr_handler *handler;
-+              
-+              handler = ext2_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      buf += handler->list(buf, inode, entry->e_name,
-+                                           entry->e_name_len);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * If the EXT2_FEATURE_COMPAT_EXT_ATTR feature of this file system is
-+ * not set, set it.
-+ */
-+static void ext2_xattr_update_super_block(struct super_block *sb)
-+{
-+      if (EXT2_HAS_COMPAT_FEATURE(sb, EXT2_FEATURE_COMPAT_EXT_ATTR))
-+              return;
-+
-+      lock_super(sb);
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+      EXT2_SB(sb)->s_feature_compat |= EXT2_FEATURE_COMPAT_EXT_ATTR;
-+#endif
-+      EXT2_SB(sb)->s_es->s_feature_compat |=
-+              cpu_to_le32(EXT2_FEATURE_COMPAT_EXT_ATTR);
-+      sb->s_dirt = 1;
-+      mark_buffer_dirty(EXT2_SB(sb)->s_sbh);
-+      unlock_super(sb);
-+}
-+
-+/*
-+ * ext2_xattr_set()
-+ *
-+ * Create, replace or remove an extended attribute for this inode. Buffer
-+ * is NULL to remove an existing extended attribute, and non-NULL to
-+ * either replace an existing extended attribute, or create a new extended
-+ * attribute. The flags XATTR_REPLACE and XATTR_CREATE
-+ * specify that an extended attribute must exist and must not exist
-+ * previous to the call, respectively.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+int
-+ext2_xattr_set(struct inode *inode, int name_index, const char *name,
-+             const void *value, size_t value_len, int flags)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *bh = NULL;
-+      struct ext2_xattr_header *header = NULL;
-+      struct ext2_xattr_entry *here, *last;
-+      unsigned int name_len;
-+      int block = EXT2_I(inode)->i_file_acl;
-+      int min_offs = sb->s_blocksize, not_found = 1, free, error;
-+      char *end;
-+      
-+      /*
-+       * header -- Points either into bh, or to a temporarily
-+       *           allocated buffer.
-+       * here -- The named entry found, or the place for inserting, within
-+       *         the block pointed to by header.
-+       * last -- Points right after the last named entry within the block
-+       *         pointed to by header.
-+       * min_offs -- The offset of the first value (values are aligned
-+       *             towards the end of the block).
-+       * end -- Points right after the block pointed to by header.
-+       */
-+      
-+      ea_idebug(inode, "name=%d.%s, value=%p, value_len=%ld",
-+                name_index, name, value, (long)value_len);
-+
-+      if (IS_RDONLY(inode))
-+              return -EROFS;
-+      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-+              return -EPERM;
-+      if (value == NULL)
-+              value_len = 0;
-+      if (name == NULL)
-+              return -EINVAL;
-+      name_len = strlen(name);
-+      if (name_len > 255 || value_len > sb->s_blocksize)
-+              return -ERANGE;
-+      down(&ext2_xattr_sem);
-+
-+      if (block) {
-+              /* The inode already has an extended attribute block. */
-+
-+              bh = sb_bread(sb, block);
-+              error = -EIO;
-+              if (!bh)
-+                      goto cleanup;
-+              ea_bdebug(bh, "b_count=%d, refcount=%d",
-+                      atomic_read(&(bh->b_count)),
-+                      le32_to_cpu(HDR(bh)->h_refcount));
-+              header = HDR(bh);
-+              end = bh->b_data + bh->b_size;
-+              if (header->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+                  header->h_blocks != cpu_to_le32(1)) {
-+bad_block:            ext2_error(sb, "ext2_xattr_set",
-+                              "inode %ld: bad block %d", inode->i_ino, block);
-+                      error = -EIO;
-+                      goto cleanup;
-+              }
-+              /* Find the named attribute. */
-+              here = FIRST_ENTRY(bh);
-+              while (!IS_LAST_ENTRY(here)) {
-+                      struct ext2_xattr_entry *next = EXT2_XATTR_NEXT(here);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!here->e_value_block && here->e_value_size) {
-+                              int offs = le16_to_cpu(here->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      not_found = name_index - here->e_name_index;
-+                      if (!not_found)
-+                              not_found = name_len - here->e_name_len;
-+                      if (!not_found)
-+                              not_found = memcmp(name, here->e_name,name_len);
-+                      if (not_found <= 0)
-+                              break;
-+                      here = next;
-+              }
-+              last = here;
-+              /* We still need to compute min_offs and last. */
-+              while (!IS_LAST_ENTRY(last)) {
-+                      struct ext2_xattr_entry *next = EXT2_XATTR_NEXT(last);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!last->e_value_block && last->e_value_size) {
-+                              int offs = le16_to_cpu(last->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      last = next;
-+              }
-+
-+              /* Check whether we have enough space left. */
-+              free = min_offs - ((char*)last - (char*)header) - sizeof(__u32);
-+      } else {
-+              /* We will use a new extended attribute block. */
-+              free = sb->s_blocksize -
-+                      sizeof(struct ext2_xattr_header) - sizeof(__u32);
-+              here = last = NULL;  /* avoid gcc uninitialized warning. */
-+      }
-+
-+      if (not_found) {
-+              /* Request to remove a nonexistent attribute? */
-+              error = -ENOATTR;
-+              if (flags & XATTR_REPLACE)
-+                      goto cleanup;
-+              error = 0;
-+              if (value == NULL)
-+                      goto cleanup;
-+              else
-+                      free -= EXT2_XATTR_LEN(name_len);
-+      } else {
-+              /* Request to create an existing attribute? */
-+              error = -EEXIST;
-+              if (flags & XATTR_CREATE)
-+                      goto cleanup;
-+              if (!here->e_value_block && here->e_value_size) {
-+                      unsigned int size = le32_to_cpu(here->e_value_size);
-+
-+                      if (le16_to_cpu(here->e_value_offs) + size > 
-+                          sb->s_blocksize || size > sb->s_blocksize)
-+                              goto bad_block;
-+                      free += EXT2_XATTR_SIZE(size);
-+              }
-+      }
-+      free -= EXT2_XATTR_SIZE(value_len);
-+      error = -ENOSPC;
-+      if (free < 0)
-+              goto cleanup;
-+
-+      /* Here we know that we can set the new attribute. */
-+
-+      if (header) {
-+              if (header->h_refcount == cpu_to_le32(1)) {
-+                      ea_bdebug(bh, "modifying in-place");
-+                      ext2_xattr_cache_remove(bh);
-+              } else {
-+                      int offset;
-+
-+                      ea_bdebug(bh, "cloning");
-+                      header = kmalloc(bh->b_size, GFP_KERNEL);
-+                      error = -ENOMEM;
-+                      if (header == NULL)
-+                              goto cleanup;
-+                      memcpy(header, HDR(bh), bh->b_size);
-+                      header->h_refcount = cpu_to_le32(1);
-+                      offset = (char *)header - bh->b_data;
-+                      here = ENTRY((char *)here + offset);
-+                      last = ENTRY((char *)last + offset);
-+              }
-+      } else {
-+              /* Allocate a buffer where we construct the new block. */
-+              header = kmalloc(sb->s_blocksize, GFP_KERNEL);
-+              error = -ENOMEM;
-+              if (header == NULL)
-+                      goto cleanup;
-+              memset(header, 0, sb->s_blocksize);
-+              end = (char *)header + sb->s_blocksize;
-+              header->h_magic = cpu_to_le32(EXT2_XATTR_MAGIC);
-+              header->h_blocks = header->h_refcount = cpu_to_le32(1);
-+              last = here = ENTRY(header+1);
-+      }
-+
-+      if (not_found) {
-+              /* Insert the new name. */
-+              int size = EXT2_XATTR_LEN(name_len);
-+              int rest = (char *)last - (char *)here;
-+              memmove((char *)here + size, here, rest);
-+              memset(here, 0, size);
-+              here->e_name_index = name_index;
-+              here->e_name_len = name_len;
-+              memcpy(here->e_name, name, name_len);
-+      } else {
-+              /* Remove the old value. */
-+              if (!here->e_value_block && here->e_value_size) {
-+                      char *first_val = (char *)header + min_offs;
-+                      int offs = le16_to_cpu(here->e_value_offs);
-+                      char *val = (char *)header + offs;
-+                      size_t size = EXT2_XATTR_SIZE(
-+                              le32_to_cpu(here->e_value_size));
-+                      memmove(first_val + size, first_val, val - first_val);
-+                      memset(first_val, 0, size);
-+                      here->e_value_offs = 0;
-+                      min_offs += size;
-+
-+                      /* Adjust all value offsets. */
-+                      last = ENTRY(header+1);
-+                      while (!IS_LAST_ENTRY(last)) {
-+                              int o = le16_to_cpu(last->e_value_offs);
-+                              if (!last->e_value_block && o < offs)
-+                                      last->e_value_offs =
-+                                              cpu_to_le16(o + size);
-+                              last = EXT2_XATTR_NEXT(last);
-+                      }
-+              }
-+              if (value == NULL) {
-+                      /* Remove this attribute. */
-+                      if (EXT2_XATTR_NEXT(ENTRY(header+1)) == last) {
-+                              /* This block is now empty. */
-+                              error = ext2_xattr_set2(inode, bh, NULL);
-+                              goto cleanup;
-+                      } else {
-+                              /* Remove the old name. */
-+                              int size = EXT2_XATTR_LEN(name_len);
-+                              last = ENTRY((char *)last - size);
-+                              memmove(here, (char*)here + size,
-+                                      (char*)last - (char*)here);
-+                              memset(last, 0, size);
-+                      }
-+              }
-+      }
-+
-+      if (value != NULL) {
-+              /* Insert the new value. */
-+              here->e_value_size = cpu_to_le32(value_len);
-+              if (value_len) {
-+                      size_t size = EXT2_XATTR_SIZE(value_len);
-+                      char *val = (char *)header + min_offs - size;
-+                      here->e_value_offs =
-+                              cpu_to_le16((char *)val - (char *)header);
-+                      memset(val + size - EXT2_XATTR_PAD, 0,
-+                             EXT2_XATTR_PAD); /* Clear the pad bytes. */
-+                      memcpy(val, value, value_len);
-+              }
-+      }
-+      ext2_xattr_rehash(header, here);
-+
-+      error = ext2_xattr_set2(inode, bh, header);
-+
-+cleanup:
-+      brelse(bh);
-+      if (!(bh && header == HDR(bh)))
-+              kfree(header);
-+      up(&ext2_xattr_sem);
-+
-+      return error;
-+}
-+
-+/*
-+ * Second half of ext2_xattr_set(): Update the file system.
-+ */
-+static int
-+ext2_xattr_set2(struct inode *inode, struct buffer_head *old_bh,
-+              struct ext2_xattr_header *header)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *new_bh = NULL;
-+      int error;
-+
-+      if (header) {
-+              new_bh = ext2_xattr_cache_find(inode, header);
-+              if (new_bh) {
-+                      /*
-+                       * We found an identical block in the cache.
-+                       * The old block will be released after updating
-+                       * the inode.
-+                       */
-+                      ea_bdebug(old_bh, "reusing block %ld",
-+                              new_bh->b_blocknr);
-+                      
-+                      error = -EDQUOT;
-+                      if (ext2_xattr_quota_alloc(inode, 1))
-+                              goto cleanup;
-+                      
-+                      HDR(new_bh)->h_refcount = cpu_to_le32(
-+                              le32_to_cpu(HDR(new_bh)->h_refcount) + 1);
-+                      ea_bdebug(new_bh, "refcount now=%d",
-+                              le32_to_cpu(HDR(new_bh)->h_refcount));
-+              } else if (old_bh && header == HDR(old_bh)) {
-+                      /* Keep this block. */
-+                      new_bh = old_bh;
-+                      (void)ext2_xattr_cache_insert(new_bh);
-+              } else {
-+                      /* We need to allocate a new block */
-+                      int force = EXT2_I(inode)->i_file_acl != 0;
-+                      int block = ext2_xattr_new_block(inode, &error, force);
-+                      if (error)
-+                              goto cleanup;
-+                      ea_idebug(inode, "creating block %d", block);
-+
-+                      new_bh = sb_getblk(sb, block);
-+                      if (!new_bh) {
-+                              ext2_xattr_free_block(inode, block);
-+                              error = -EIO;
-+                              goto cleanup;
-+                      }
-+                      lock_buffer(new_bh);
-+                      memcpy(new_bh->b_data, header, new_bh->b_size);
-+                      mark_buffer_uptodate(new_bh, 1);
-+                      unlock_buffer(new_bh);
-+                      (void)ext2_xattr_cache_insert(new_bh);
-+                      
-+                      ext2_xattr_update_super_block(sb);
-+              }
-+              mark_buffer_dirty(new_bh);
-+              if (IS_SYNC(inode)) {
-+                      ll_rw_block(WRITE, 1, &new_bh);
-+                      wait_on_buffer(new_bh); 
-+                      error = -EIO;
-+                      if (buffer_req(new_bh) && !buffer_uptodate(new_bh))
-+                              goto cleanup;
-+              }
-+      }
-+
-+      /* Update the inode. */
-+      EXT2_I(inode)->i_file_acl = new_bh ? new_bh->b_blocknr : 0;
-+      inode->i_ctime = CURRENT_TIME;
-+      if (IS_SYNC(inode)) {
-+              error = ext2_sync_inode (inode);
-+              if (error)
-+                      goto cleanup;
-+      } else
-+              mark_inode_dirty(inode);
-+
-+      error = 0;
-+      if (old_bh && old_bh != new_bh) {
-+              /*
-+               * If there was an old block, and we are not still using it,
-+               * we now release the old block.
-+              */
-+              unsigned int refcount = le32_to_cpu(HDR(old_bh)->h_refcount);
-+
-+              if (refcount == 1) {
-+                      /* Free the old block. */
-+                      ea_bdebug(old_bh, "freeing");
-+                      ext2_xattr_free_block(inode, old_bh->b_blocknr);
-+                      mark_buffer_clean(old_bh);
-+              } else {
-+                      /* Decrement the refcount only. */
-+                      refcount--;
-+                      HDR(old_bh)->h_refcount = cpu_to_le32(refcount);
-+                      ext2_xattr_quota_free(inode);
-+                      mark_buffer_dirty(old_bh);
-+                      ea_bdebug(old_bh, "refcount now=%d", refcount);
-+              }
-+      }
-+
-+cleanup:
-+      if (old_bh != new_bh)
-+              brelse(new_bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_delete_inode()
-+ *
-+ * Free extended attribute resources associated with this inode. This
-+ * is called immediately before an inode is freed.
-+ */
-+void
-+ext2_xattr_delete_inode(struct inode *inode)
-+{
-+      struct buffer_head *bh;
-+      unsigned int block = EXT2_I(inode)->i_file_acl;
-+
-+      if (!block)
-+              return;
-+      down(&ext2_xattr_sem);
-+
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh) {
-+              ext2_error(inode->i_sb, "ext2_xattr_delete_inode",
-+                      "inode %ld: block %d read error", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "b_count=%d", atomic_read(&(bh->b_count)));
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT2_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+              ext2_error(inode->i_sb, "ext2_xattr_delete_inode",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "refcount now=%d", le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+      if (HDR(bh)->h_refcount == cpu_to_le32(1)) {
-+              ext2_xattr_cache_remove(bh);
-+              ext2_xattr_free_block(inode, block);
-+              bforget(bh);
-+              bh = NULL;
-+      } else {
-+              HDR(bh)->h_refcount = cpu_to_le32(
-+                      le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+              mark_buffer_dirty(bh);
-+              if (IS_SYNC(inode)) {
-+                      ll_rw_block(WRITE, 1, &bh);
-+                      wait_on_buffer(bh);
-+              }
-+              ext2_xattr_quota_free(inode);
-+      }
-+      EXT2_I(inode)->i_file_acl = 0;
-+
-+cleanup:
-+      brelse(bh);
-+      up(&ext2_xattr_sem);
-+}
-+
-+/*
-+ * ext2_xattr_put_super()
-+ *
-+ * This is called when a file system is unmounted.
-+ */
-+void
-+ext2_xattr_put_super(struct super_block *sb)
-+{
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+      mb_cache_shrink(ext2_xattr_cache, sb->s_dev);
-+#endif
-+}
-+
-+#ifdef CONFIG_EXT2_FS_XATTR_SHARING
-+
-+/*
-+ * ext2_xattr_cache_insert()
-+ *
-+ * Create a new entry in the extended attribute cache, and insert
-+ * it unless such an entry is already in the cache.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+static int
-+ext2_xattr_cache_insert(struct buffer_head *bh)
-+{
-+      __u32 hash = le32_to_cpu(HDR(bh)->h_hash);
-+      struct mb_cache_entry *ce;
-+      int error;
-+
-+      ce = mb_cache_entry_alloc(ext2_xattr_cache);
-+      if (!ce)
-+              return -ENOMEM;
-+      error = mb_cache_entry_insert(ce, bh->b_dev, bh->b_blocknr, &hash);
-+      if (error) {
-+              mb_cache_entry_free(ce);
-+              if (error == -EBUSY) {
-+                      ea_bdebug(bh, "already in cache (%d cache entries)",
-+                              atomic_read(&ext2_xattr_cache->c_entry_count));
-+                      error = 0;
-+              }
-+      } else {
-+              ea_bdebug(bh, "inserting [%x] (%d cache entries)", (int)hash,
-+                        atomic_read(&ext2_xattr_cache->c_entry_count));
-+              mb_cache_entry_release(ce);
-+      }
-+      return error;
-+}
-+
-+/*
-+ * ext2_xattr_cmp()
-+ *
-+ * Compare two extended attribute blocks for equality.
-+ *
-+ * Returns 0 if the blocks are equal, 1 if they differ, and
-+ * a negative error number on errors.
-+ */
-+static int
-+ext2_xattr_cmp(struct ext2_xattr_header *header1,
-+             struct ext2_xattr_header *header2)
-+{
-+      struct ext2_xattr_entry *entry1, *entry2;
-+
-+      entry1 = ENTRY(header1+1);
-+      entry2 = ENTRY(header2+1);
-+      while (!IS_LAST_ENTRY(entry1)) {
-+              if (IS_LAST_ENTRY(entry2))
-+                      return 1;
-+              if (entry1->e_hash != entry2->e_hash ||
-+                  entry1->e_name_len != entry2->e_name_len ||
-+                  entry1->e_value_size != entry2->e_value_size ||
-+                  memcmp(entry1->e_name, entry2->e_name, entry1->e_name_len))
-+                      return 1;
-+              if (entry1->e_value_block != 0 || entry2->e_value_block != 0)
-+                      return -EIO;
-+              if (memcmp((char *)header1 + le16_to_cpu(entry1->e_value_offs),
-+                         (char *)header2 + le16_to_cpu(entry2->e_value_offs),
-+                         le32_to_cpu(entry1->e_value_size)))
-+                      return 1;
-+
-+              entry1 = EXT2_XATTR_NEXT(entry1);
-+              entry2 = EXT2_XATTR_NEXT(entry2);
-+      }
-+      if (!IS_LAST_ENTRY(entry2))
-+              return 1;
-+      return 0;
-+}
-+
-+/*
-+ * ext2_xattr_cache_find()
-+ *
-+ * Find an identical extended attribute block.
-+ *
-+ * Returns a pointer to the block found, or NULL if such a block was
-+ * not found or an error occurred.
-+ */
-+static struct buffer_head *
-+ext2_xattr_cache_find(struct inode *inode, struct ext2_xattr_header *header)
-+{
-+      __u32 hash = le32_to_cpu(header->h_hash);
-+      struct mb_cache_entry *ce;
-+
-+      if (!header->h_hash)
-+              return NULL;  /* never share */
-+      ea_idebug(inode, "looking for cached blocks [%x]", (int)hash);
-+      ce = mb_cache_entry_find_first(ext2_xattr_cache, 0, inode->i_dev, hash);
-+      while (ce) {
-+              struct buffer_head *bh = sb_bread(inode->i_sb, ce->e_block);
-+
-+              if (!bh) {
-+                      ext2_error(inode->i_sb, "ext2_xattr_cache_find",
-+                              "inode %ld: block %ld read error",
-+                              inode->i_ino, ce->e_block);
-+              } else if (le32_to_cpu(HDR(bh)->h_refcount) >
-+                         EXT2_XATTR_REFCOUNT_MAX) {
-+                      ea_idebug(inode, "block %ld refcount %d>%d",ce->e_block,
-+                              le32_to_cpu(HDR(bh)->h_refcount),
-+                              EXT2_XATTR_REFCOUNT_MAX);
-+              } else if (!ext2_xattr_cmp(header, HDR(bh))) {
-+                      ea_bdebug(bh, "b_count=%d",atomic_read(&(bh->b_count)));
-+                      mb_cache_entry_release(ce);
-+                      return bh;
-+              }
-+              brelse(bh);
-+              ce = mb_cache_entry_find_next(ce, 0, inode->i_dev, hash);
-+      }
-+      return NULL;
-+}
-+
-+/*
-+ * ext2_xattr_cache_remove()
-+ *
-+ * Remove the cache entry of a block from the cache. Called when a
-+ * block becomes invalid.
-+ */
-+static void
-+ext2_xattr_cache_remove(struct buffer_head *bh)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      ce = mb_cache_entry_get(ext2_xattr_cache, bh->b_dev, bh->b_blocknr);
-+      if (ce) {
-+              ea_bdebug(bh, "removing (%d cache entries remaining)",
-+                        atomic_read(&ext2_xattr_cache->c_entry_count)-1);
-+              mb_cache_entry_free(ce);
-+      } else 
-+              ea_bdebug(bh, "no cache entry");
-+}
-+
-+#define NAME_HASH_SHIFT 5
-+#define VALUE_HASH_SHIFT 16
-+
-+/*
-+ * ext2_xattr_hash_entry()
-+ *
-+ * Compute the hash of an extended attribute.
-+ */
-+static inline void ext2_xattr_hash_entry(struct ext2_xattr_header *header,
-+                                       struct ext2_xattr_entry *entry)
-+{
-+      __u32 hash = 0;
-+      char *name = entry->e_name;
-+      int n;
-+
-+      for (n=0; n < entry->e_name_len; n++) {
-+              hash = (hash << NAME_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - NAME_HASH_SHIFT)) ^
-+                     *name++;
-+      }
-+
-+      if (entry->e_value_block == 0 && entry->e_value_size != 0) {
-+              __u32 *value = (__u32 *)((char *)header +
-+                      le16_to_cpu(entry->e_value_offs));
-+              for (n = (le32_to_cpu(entry->e_value_size) +
-+                   EXT2_XATTR_ROUND) >> EXT2_XATTR_PAD_BITS; n; n--) {
-+                      hash = (hash << VALUE_HASH_SHIFT) ^
-+                             (hash >> (8*sizeof(hash) - VALUE_HASH_SHIFT)) ^
-+                             le32_to_cpu(*value++);
-+              }
-+      }
-+      entry->e_hash = cpu_to_le32(hash);
-+}
-+
-+#undef NAME_HASH_SHIFT
-+#undef VALUE_HASH_SHIFT
-+
-+#define BLOCK_HASH_SHIFT 16
-+
-+/*
-+ * ext2_xattr_rehash()
-+ *
-+ * Re-compute the extended attribute hash value after an entry has changed.
-+ */
-+static void ext2_xattr_rehash(struct ext2_xattr_header *header,
-+                            struct ext2_xattr_entry *entry)
-+{
-+      struct ext2_xattr_entry *here;
-+      __u32 hash = 0;
-+      
-+      ext2_xattr_hash_entry(header, entry);
-+      here = ENTRY(header+1);
-+      while (!IS_LAST_ENTRY(here)) {
-+              if (!here->e_hash) {
-+                      /* Block is not shared if an entry's hash value == 0 */
-+                      hash = 0;
-+                      break;
-+              }
-+              hash = (hash << BLOCK_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - BLOCK_HASH_SHIFT)) ^
-+                     le32_to_cpu(here->e_hash);
-+              here = EXT2_XATTR_NEXT(here);
-+      }
-+      header->h_hash = cpu_to_le32(hash);
-+}
-+
-+#undef BLOCK_HASH_SHIFT
-+
-+int __init
-+init_ext2_xattr(void)
-+{
-+      ext2_xattr_cache = mb_cache_create("ext2_xattr", NULL,
-+              sizeof(struct mb_cache_entry) +
-+              sizeof(struct mb_cache_entry_index), 1, 61);
-+      if (!ext2_xattr_cache)
-+              return -ENOMEM;
-+
-+      return 0;
-+}
-+
-+void
-+exit_ext2_xattr(void)
-+{
-+      mb_cache_destroy(ext2_xattr_cache);
-+}
-+
-+#else  /* CONFIG_EXT2_FS_XATTR_SHARING */
-+
-+int __init
-+init_ext2_xattr(void)
-+{
-+      return 0;
-+}
-+
-+void
-+exit_ext2_xattr(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT2_FS_XATTR_SHARING */
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/ext2/xattr_user.c       2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,103 @@
-+/*
-+ * linux/fs/ext2/xattr_user.c
-+ * Handler for extended user attributes.
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/string.h>
-+#include <linux/fs.h>
-+#include <linux/ext2_fs.h>
-+#include <linux/ext2_xattr.h>
-+
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+# include <linux/ext2_acl.h>
-+#endif
-+
-+#define XATTR_USER_PREFIX "user."
-+
-+static size_t
-+ext2_xattr_user_list(char *list, struct inode *inode,
-+                   const char *name, int name_len)
-+{
-+      const int prefix_len = sizeof(XATTR_USER_PREFIX)-1;
-+
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return 0;
-+
-+      if (list) {
-+              memcpy(list, XATTR_USER_PREFIX, prefix_len);
-+              memcpy(list+prefix_len, name, name_len);
-+              list[prefix_len + name_len] = '\0';
-+      }
-+      return prefix_len + name_len + 1;
-+}
-+
-+static int
-+ext2_xattr_user_get(struct inode *inode, const char *name,
-+                  void *buffer, size_t size)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+      error = ext2_permission_locked(inode, MAY_READ);
-+#else
-+      error = permission(inode, MAY_READ);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext2_xattr_get(inode, EXT2_XATTR_INDEX_USER, name,
-+                            buffer, size);
-+}
-+
-+static int
-+ext2_xattr_user_set(struct inode *inode, const char *name,
-+                  const void *value, size_t size, int flags)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+      if ( !S_ISREG(inode->i_mode) &&
-+          (!S_ISDIR(inode->i_mode) || inode->i_mode & S_ISVTX))
-+              return -EPERM;
-+#ifdef CONFIG_EXT2_FS_POSIX_ACL
-+      error = ext2_permission_locked(inode, MAY_WRITE);
-+#else
-+      error = permission(inode, MAY_WRITE);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext2_xattr_set(inode, EXT2_XATTR_INDEX_USER, name,
-+                            value, size, flags);
-+}
-+
-+struct ext2_xattr_handler ext2_xattr_user_handler = {
-+      prefix: XATTR_USER_PREFIX,
-+      list:   ext2_xattr_user_list,
-+      get:    ext2_xattr_user_get,
-+      set:    ext2_xattr_user_set,
-+};
-+
-+int __init
-+init_ext2_xattr_user(void)
-+{
-+      return ext2_xattr_register(EXT2_XATTR_INDEX_USER,
-+                                 &ext2_xattr_user_handler);
-+}
-+
-+void
-+exit_ext2_xattr_user(void)
-+{
-+      ext2_xattr_unregister(EXT2_XATTR_INDEX_USER,
-+                            &ext2_xattr_user_handler);
-+}
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/ext3/ext3-exports.c     2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,13 @@
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
-+
-+EXPORT_SYMBOL(ext3_force_commit);
-+EXPORT_SYMBOL(ext3_bread);
-+EXPORT_SYMBOL(ext3_xattr_register);
-+EXPORT_SYMBOL(ext3_xattr_unregister);
-+EXPORT_SYMBOL(ext3_xattr_get);
-+EXPORT_SYMBOL(ext3_xattr_list);
-+EXPORT_SYMBOL(ext3_xattr_set);
---- linux-2.4.22-ac1/fs/ext3/file.c~xattr-0.8.54-2.4.22-rh     2003-09-25 14:55:12.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/file.c     2003-09-25 23:57:02.000000000 +0400
-@@ -23,6 +23,7 @@
- #include <linux/locks.h>
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/ext3_jbd.h>
- #include <linux/smp_lock.h>
-@@ -127,5 +128,9 @@ struct file_operations ext3_file_operati
- struct inode_operations ext3_file_inode_operations = {
-       truncate:       ext3_truncate,          /* BKL held */
-       setattr:        ext3_setattr,           /* BKL held */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
---- linux-2.4.22-ac1/fs/ext3/ialloc.c~xattr-0.8.54-2.4.22-rh   2003-09-25 14:16:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/ialloc.c   2003-09-25 23:57:02.000000000 +0400
-@@ -17,6 +17,7 @@
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/stat.h>
- #include <linux/string.h>
- #include <linux/locks.h>
-@@ -217,6 +218,7 @@ void ext3_free_inode (handle_t *handle, 
-        * as writing the quota to disk may need the lock as well.
-        */
-       DQUOT_INIT(inode);
-+      ext3_xattr_delete_inode(handle, inode);
-       DQUOT_FREE_INODE(inode);
-       DQUOT_DROP(inode);
---- linux-2.4.22-ac1/fs/ext3/inode.c~xattr-0.8.54-2.4.22-rh    2003-09-25 14:16:29.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/inode.c    2003-09-26 00:10:09.000000000 +0400
-@@ -39,6 +39,18 @@
-  */
- #undef SEARCH_FROM_ZERO
-+/*
-+ * Test whether an inode is a fast symlink.
-+ */
-+static inline int ext3_inode_is_fast_symlink(struct inode *inode)
-+{
-+      int ea_blocks = inode->u.ext3_i.i_file_acl ?
-+              (inode->i_sb->s_blocksize >> 9) : 0;
-+
-+      return (S_ISLNK(inode->i_mode) &&
-+              inode->i_blocks - ea_blocks == 0);
-+}
-+
- /* The ext3 forget function must perform a revoke if we are freeing data
-  * which has been journaled.  Metadata (eg. indirect blocks) must be
-  * revoked in all cases. 
-@@ -48,7 +60,7 @@
-  * still needs to be revoked.
-  */
--static int ext3_forget(handle_t *handle, int is_metadata,
-+int ext3_forget(handle_t *handle, int is_metadata,
-                      struct inode *inode, struct buffer_head *bh,
-                      int blocknr)
- {
-@@ -179,9 +191,7 @@ void ext3_delete_inode (struct inode * i
- {
-       handle_t *handle;
-       
--      if (is_bad_inode(inode) ||
--          inode->i_ino == EXT3_ACL_IDX_INO ||
--          inode->i_ino == EXT3_ACL_DATA_INO)
-+      if (is_bad_inode(inode))
-               goto no_delete;
-       lock_kernel();
-@@ -1874,6 +1884,8 @@ void ext3_truncate(struct inode * inode)
-       if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
-           S_ISLNK(inode->i_mode)))
-               return;
-+      if (ext3_inode_is_fast_symlink(inode))
-+              return;
-       if (IS_APPEND(inode) || IS_IMMUTABLE(inode))
-               return;
-@@ -2021,8 +2033,6 @@ int ext3_get_inode_loc (struct inode *in
-       struct ext3_group_desc * gdp;
-               
-       if ((inode->i_ino != EXT3_ROOT_INO &&
--              inode->i_ino != EXT3_ACL_IDX_INO &&
--              inode->i_ino != EXT3_ACL_DATA_INO &&
-               inode->i_ino != EXT3_JOURNAL_INO &&
-               inode->i_ino < EXT3_FIRST_INO(inode->i_sb)) ||
-               inode->i_ino > le32_to_cpu(
-@@ -2163,10 +2173,7 @@ void ext3_read_inode(struct inode * inod
-               inode->u.ext3_i.i_data[block] = iloc.raw_inode->i_block[block];
-       INIT_LIST_HEAD(&inode->u.ext3_i.i_orphan);
--      if (inode->i_ino == EXT3_ACL_IDX_INO ||
--          inode->i_ino == EXT3_ACL_DATA_INO)
--              /* Nothing to do */ ;
--      else if (S_ISREG(inode->i_mode)) {
-+      if (S_ISREG(inode->i_mode)) {
-               inode->i_op = &ext3_file_inode_operations;
-               inode->i_fop = &ext3_file_operations;
-               inode->i_mapping->a_ops = &ext3_aops;
-@@ -2174,15 +2181,17 @@ void ext3_read_inode(struct inode * inod
-               inode->i_op = &ext3_dir_inode_operations;
-               inode->i_fop = &ext3_dir_operations;
-       } else if (S_ISLNK(inode->i_mode)) {
--              if (!inode->i_blocks)
-+              if (ext3_inode_is_fast_symlink(inode))
-                       inode->i_op = &ext3_fast_symlink_inode_operations;
-               else {
--                      inode->i_op = &page_symlink_inode_operations;
-+                      inode->i_op = &ext3_symlink_inode_operations;
-                       inode->i_mapping->a_ops = &ext3_aops;
-               }
--      } else 
-+      } else {
-+              inode->i_op = &ext3_special_inode_operations;
-               init_special_inode(inode, inode->i_mode,
-                                  le32_to_cpu(iloc.raw_inode->i_block[0]));
-+      }
-       brelse(iloc.bh);
-       ext3_set_inode_flags(inode);
-       return;
---- linux-2.4.22-ac1/fs/ext3/Makefile~xattr-0.8.54-2.4.22-rh   2003-09-25 14:55:12.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/Makefile   2003-09-25 23:57:02.000000000 +0400
-@@ -1,5 +1,5 @@
- #
--# Makefile for the linux ext2-filesystem routines.
-+# Makefile for the linux ext3-filesystem routines.
- #
- # Note! Dependencies are done automagically by 'make dep', which also
- # removes any old dependencies. DON'T put your own dependencies here
-@@ -9,10 +9,14 @@
- O_TARGET := ext3.o
--export-objs :=        super.o inode.o
-+export-objs := ext3-exports.o
- obj-y    := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o \
--              ioctl.o namei.o super.o symlink.o hash.o
-+              ioctl.o namei.o super.o symlink.o hash.o ext3-exports.o
- obj-m    := $(O_TARGET)
-+export-objs += xattr.o
-+obj-$(CONFIG_EXT3_FS_XATTR) += xattr.o
-+obj-$(CONFIG_EXT3_FS_XATTR_USER) += xattr_user.o
-+
- include $(TOPDIR)/Rules.make
---- linux-2.4.22-ac1/fs/ext3/namei.c~xattr-0.8.54-2.4.22-rh    2003-09-25 14:58:37.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/namei.c    2003-09-25 23:57:02.000000000 +0400
-@@ -29,6 +29,7 @@
- #include <linux/sched.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/fcntl.h>
- #include <linux/stat.h>
- #include <linux/string.h>
-@@ -1614,7 +1615,7 @@ static int ext3_mkdir(struct inode * dir
-       if (IS_SYNC(dir))
-               handle->h_sync = 1;
--      inode = ext3_new_inode (handle, dir, S_IFDIR);
-+      inode = ext3_new_inode (handle, dir, S_IFDIR | mode);
-       err = PTR_ERR(inode);
-       if (IS_ERR(inode))
-               goto out_stop;
-@@ -1622,7 +1623,6 @@ static int ext3_mkdir(struct inode * dir
-       inode->i_op = &ext3_dir_inode_operations;
-       inode->i_fop = &ext3_dir_operations;
-       inode->i_size = EXT3_I(inode)->i_disksize = inode->i_sb->s_blocksize;
--      inode->i_blocks = 0;    
-       dir_block = ext3_bread (handle, inode, 0, 1, &err);
-       if (!dir_block) {
-               inode->i_nlink--; /* is this nlink == 0? */
-@@ -1649,9 +1649,6 @@ static int ext3_mkdir(struct inode * dir
-       BUFFER_TRACE(dir_block, "call ext3_journal_dirty_metadata");
-       ext3_journal_dirty_metadata(handle, dir_block);
-       brelse (dir_block);
--      inode->i_mode = S_IFDIR | mode;
--      if (dir->i_mode & S_ISGID)
--              inode->i_mode |= S_ISGID;
-       ext3_mark_inode_dirty(handle, inode);
-       err = ext3_add_entry (handle, dentry, inode);
-       if (err) {
-@@ -2020,7 +2017,7 @@ static int ext3_symlink (struct inode * 
-               goto out_stop;
-       if (l > sizeof (EXT3_I(inode)->i_data)) {
--              inode->i_op = &page_symlink_inode_operations;
-+              inode->i_op = &ext3_symlink_inode_operations;
-               inode->i_mapping->a_ops = &ext3_aops;
-               /*
-                * block_symlink() calls back into ext3_prepare/commit_write.
-@@ -2245,4 +2242,16 @@ struct inode_operations ext3_dir_inode_o
-       rmdir:          ext3_rmdir,             /* BKL held */
-       mknod:          ext3_mknod,             /* BKL held */
-       rename:         ext3_rename,            /* BKL held */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
-+
-+struct inode_operations ext3_special_inode_operations = {
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
-+};
-+
---- linux-2.4.22-ac1/fs/ext3/super.c~xattr-0.8.54-2.4.22-rh    2003-09-25 14:55:12.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/ext3/super.c    2003-09-26 00:12:23.000000000 +0400
-@@ -24,6 +24,7 @@
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
- #include <linux/ext3_jbd.h>
-+#include <linux/ext3_xattr.h>
- #include <linux/slab.h>
- #include <linux/init.h>
- #include <linux/locks.h>
-@@ -406,6 +407,7 @@ void ext3_put_super (struct super_block 
-       kdev_t j_dev = sbi->s_journal->j_dev;
-       int i;
-+      ext3_xattr_put_super(sb);
-       journal_destroy(sbi->s_journal);
-       if (!(sb->s_flags & MS_RDONLY)) {
-               EXT3_CLEAR_INCOMPAT_FEATURE(sb, EXT3_FEATURE_INCOMPAT_RECOVER);
-@@ -506,6 +508,7 @@ static int parse_options (char * options
-                         int is_remount)
- {
-       unsigned long *mount_options = &sbi->s_mount_opt;
-+      
-       uid_t *resuid = &sbi->s_resuid;
-       gid_t *resgid = &sbi->s_resgid;
-       char * this_char;
-@@ -518,6 +521,13 @@ static int parse_options (char * options
-            this_char = strtok (NULL, ",")) {
-               if ((value = strchr (this_char, '=')) != NULL)
-                       *value++ = 0;
-+#ifdef CONFIG_EXT3_FS_XATTR_USER
-+              if (!strcmp (this_char, "user_xattr"))
-+                      set_opt (*mount_options, XATTR_USER);
-+              else if (!strcmp (this_char, "nouser_xattr"))
-+                      clear_opt (*mount_options, XATTR_USER);
-+              else
-+#endif
-               if (!strcmp (this_char, "bsddf"))
-                       clear_opt (*mount_options, MINIX_DF);
-               else if (!strcmp (this_char, "nouid32")) {
-@@ -935,6 +945,12 @@ struct super_block * ext3_read_super (st
-       sbi->s_mount_opt = 0;
-       sbi->s_resuid = EXT3_DEF_RESUID;
-       sbi->s_resgid = EXT3_DEF_RESGID;
-+
-+      /* Default extended attribute flags */
-+#ifdef CONFIG_EXT3_FS_XATTR_USER
-+      /* set_opt(sbi->s_mount_opt, XATTR_USER); */
-+#endif
-+
-       if (!parse_options ((char *) data, &sb_block, sbi, &journal_inum, 0)) {
-               sb->s_dev = 0;
-               goto out_fail;
-@@ -1839,22 +1855,35 @@ static DECLARE_FSTYPE_DEV(ext3_fs_type, 
- static int __init init_ext3_fs(void)
- {
-+      int error;
- #ifdef CONFIG_QUOTA
-       init_dquot_operations(&ext3_qops);
-       old_sync_dquot = ext3_qops.sync_dquot;
-       ext3_qops.sync_dquot = ext3_sync_dquot;
- #endif
--        return register_filesystem(&ext3_fs_type);
-+      error = init_ext3_xattr();
-+      if (error)
-+              return error;
-+      error = init_ext3_xattr_user();
-+      if (error)
-+              goto fail;
-+      error = register_filesystem(&ext3_fs_type);
-+      if (!error)
-+              return 0;
-+      
-+      exit_ext3_xattr_user();
-+fail:
-+      exit_ext3_xattr();
-+      return error;
- }
- static void __exit exit_ext3_fs(void)
- {
-       unregister_filesystem(&ext3_fs_type);
-+      exit_ext3_xattr_user();
-+      exit_ext3_xattr();
- }
--EXPORT_SYMBOL(ext3_force_commit);
--EXPORT_SYMBOL(ext3_bread);
--
- MODULE_AUTHOR("Remy Card, Stephen Tweedie, Andrew Morton, Andreas Dilger, Theodore Ts'o and others");
- MODULE_DESCRIPTION("Second Extended Filesystem with journaling extensions");
- MODULE_LICENSE("GPL");
---- linux-2.4.22-ac1/fs/ext3/symlink.c~xattr-0.8.54-2.4.22-rh  2001-11-10 01:25:04.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/ext3/symlink.c  2003-09-25 23:57:02.000000000 +0400
-@@ -20,6 +20,7 @@
- #include <linux/fs.h>
- #include <linux/jbd.h>
- #include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
- static int ext3_readlink(struct dentry *dentry, char *buffer, int buflen)
- {
-@@ -33,7 +34,20 @@ static int ext3_follow_link(struct dentr
-       return vfs_follow_link(nd, s);
- }
-+struct inode_operations ext3_symlink_inode_operations = {
-+      readlink:       page_readlink,          /* BKL not held.  Don't need */
-+      follow_link:    page_follow_link,       /* BKL not held.  Don't need */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
-+};
-+
- struct inode_operations ext3_fast_symlink_inode_operations = {
-       readlink:       ext3_readlink,          /* BKL not held.  Don't need */
-       follow_link:    ext3_follow_link,       /* BKL not held.  Don't need */
-+      setxattr:       ext3_setxattr,          /* BKL held */
-+      getxattr:       ext3_getxattr,          /* BKL held */
-+      listxattr:      ext3_listxattr,         /* BKL held */
-+      removexattr:    ext3_removexattr,       /* BKL held */
- };
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/ext3/xattr.c    2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,1225 @@
-+/*
-+ * linux/fs/ext3/xattr.c
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ *
-+ * Fix by Harrison Xing <harrison@mountainviewdata.com>.
-+ * Ext3 code with a lot of help from Eric Jarman <ejarman@acm.org>.
-+ * Extended attributes for symlinks and special files added per
-+ *  suggestion of Luka Renko <luka.renko@hermes.si>.
-+ */
-+
-+/*
-+ * Extended attributes are stored on disk blocks allocated outside of
-+ * any inode. The i_file_acl field is then made to point to this allocated
-+ * block. If all extended attributes of an inode are identical, these
-+ * inodes may share the same extended attribute block. Such situations
-+ * are automatically detected by keeping a cache of recent attribute block
-+ * numbers and hashes over the block's contents in memory.
-+ *
-+ *
-+ * Extended attribute block layout:
-+ *
-+ *   +------------------+
-+ *   | header           |
-+ *   | entry 1          | |
-+ *   | entry 2          | | growing downwards
-+ *   | entry 3          | v
-+ *   | four null bytes  |
-+ *   | . . .            |
-+ *   | value 1          | ^
-+ *   | value 3          | | growing upwards
-+ *   | value 2          | |
-+ *   +------------------+
-+ *
-+ * The block header is followed by multiple entry descriptors. These entry
-+ * descriptors are variable in size, and alligned to EXT3_XATTR_PAD
-+ * byte boundaries. The entry descriptors are sorted by attribute name,
-+ * so that two extended attribute blocks can be compared efficiently.
-+ *
-+ * Attribute values are aligned to the end of the block, stored in
-+ * no specific order. They are also padded to EXT3_XATTR_PAD byte
-+ * boundaries. No additional gaps are left between them.
-+ *
-+ * Locking strategy
-+ * ----------------
-+ * The VFS already holds the BKL and the inode->i_sem semaphore when any of
-+ * the xattr inode operations are called, so we are guaranteed that only one
-+ * processes accesses extended attributes of an inode at any time.
-+ *
-+ * For writing we also grab the ext3_xattr_sem semaphore. This ensures that
-+ * only a single process is modifying an extended attribute block, even
-+ * if the block is shared among inodes.
-+ *
-+ * Note for porting to 2.5
-+ * -----------------------
-+ * The BKL will no longer be held in the xattr inode operations.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/fs.h>
-+#include <linux/locks.h>
-+#include <linux/slab.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
-+#include <linux/mbcache.h>
-+#include <linux/quotaops.h>
-+#include <asm/semaphore.h>
-+#include <linux/compatmac.h>
-+
-+#define EXT3_EA_USER "user."
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+# define mark_buffer_dirty(bh) mark_buffer_dirty(bh, 1)
-+#endif
-+
-+#define HDR(bh) ((struct ext3_xattr_header *)((bh)->b_data))
-+#define ENTRY(ptr) ((struct ext3_xattr_entry *)(ptr))
-+#define FIRST_ENTRY(bh) ENTRY(HDR(bh)+1)
-+#define IS_LAST_ENTRY(entry) (*(__u32 *)(entry) == 0)
-+
-+#ifdef EXT3_XATTR_DEBUG
-+# define ea_idebug(inode, f...) do { \
-+              printk(KERN_DEBUG "inode %s:%ld: ", \
-+                      kdevname(inode->i_dev), inode->i_ino); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+# define ea_bdebug(bh, f...) do { \
-+              printk(KERN_DEBUG "block %s:%ld: ", \
-+                      kdevname(bh->b_dev), bh->b_blocknr); \
-+              printk(f); \
-+              printk("\n"); \
-+      } while (0)
-+#else
-+# define ea_idebug(f...)
-+# define ea_bdebug(f...)
-+#endif
-+
-+static int ext3_xattr_set2(handle_t *, struct inode *, struct buffer_head *,
-+                         struct ext3_xattr_header *);
-+
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+
-+static int ext3_xattr_cache_insert(struct buffer_head *);
-+static struct buffer_head *ext3_xattr_cache_find(struct inode *,
-+                                               struct ext3_xattr_header *);
-+static void ext3_xattr_cache_remove(struct buffer_head *);
-+static void ext3_xattr_rehash(struct ext3_xattr_header *,
-+                            struct ext3_xattr_entry *);
-+
-+static struct mb_cache *ext3_xattr_cache;
-+
-+#else
-+# define ext3_xattr_cache_insert(bh) 0
-+# define ext3_xattr_cache_find(inode, header) NULL
-+# define ext3_xattr_cache_remove(bh) while(0) {}
-+# define ext3_xattr_rehash(header, entry) while(0) {}
-+#endif
-+
-+/*
-+ * If a file system does not share extended attributes among inodes,
-+ * we should not need the ext3_xattr_sem semaphore. However, the
-+ * filesystem may still contain shared blocks, so we always take
-+ * the lock.
-+ */
-+
-+DECLARE_MUTEX(ext3_xattr_sem);
-+
-+static inline int
-+ext3_xattr_new_block(handle_t *handle, struct inode *inode,
-+                   int * errp, int force)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      int goal = le32_to_cpu(EXT3_SB(sb)->s_es->s_first_data_block) +
-+              EXT3_I(inode)->i_block_group * EXT3_BLOCKS_PER_GROUP(sb);
-+
-+      /* How can we enforce the allocation? */
-+      int block = ext3_new_block(handle, inode, goal, 0, 0, errp);
-+#ifdef OLD_QUOTAS
-+      if (!*errp)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#endif
-+      return block;
-+}
-+
-+static inline int
-+ext3_xattr_quota_alloc(struct inode *inode, int force)
-+{
-+      /* How can we enforce the allocation? */
-+#ifdef OLD_QUOTAS
-+      int error = DQUOT_ALLOC_BLOCK(inode->i_sb, inode, 1);
-+      if (!error)
-+              inode->i_blocks += inode->i_sb->s_blocksize >> 9;
-+#else
-+      int error = DQUOT_ALLOC_BLOCK(inode, 1);
-+#endif
-+      return error;
-+}
-+
-+#ifdef OLD_QUOTAS
-+
-+static inline void
-+ext3_xattr_quota_free(struct inode *inode)
-+{
-+      DQUOT_FREE_BLOCK(inode->i_sb, inode, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+static inline void
-+ext3_xattr_free_block(handle_t *handle, struct inode * inode,
-+                    unsigned long block)
-+{
-+      ext3_free_blocks(handle, inode, block, 1);
-+      inode->i_blocks -= inode->i_sb->s_blocksize >> 9;
-+}
-+
-+#else
-+# define ext3_xattr_quota_free(inode) \
-+      DQUOT_FREE_BLOCK(inode, 1)
-+# define ext3_xattr_free_block(handle, inode, block) \
-+      ext3_free_blocks(handle, inode, block, 1)
-+#endif
-+
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,18)
-+
-+static inline struct buffer_head *
-+sb_bread(struct super_block *sb, int block)
-+{
-+      return bread(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+static inline struct buffer_head *
-+sb_getblk(struct super_block *sb, int block)
-+{
-+      return getblk(sb->s_dev, block, sb->s_blocksize);
-+}
-+
-+#endif
-+
-+struct ext3_xattr_handler *ext3_xattr_handlers[EXT3_XATTR_INDEX_MAX];
-+rwlock_t ext3_handler_lock = RW_LOCK_UNLOCKED;
-+
-+int
-+ext3_xattr_register(int name_index, struct ext3_xattr_handler *handler)
-+{
-+      int error = -EINVAL;
-+
-+      if (name_index > 0 && name_index <= EXT3_XATTR_INDEX_MAX) {
-+              write_lock(&ext3_handler_lock);
-+              if (!ext3_xattr_handlers[name_index-1]) {
-+                      ext3_xattr_handlers[name_index-1] = handler;
-+                      error = 0;
-+              }
-+              write_unlock(&ext3_handler_lock);
-+      }
-+      return error;
-+}
-+
-+void
-+ext3_xattr_unregister(int name_index, struct ext3_xattr_handler *handler)
-+{
-+      if (name_index > 0 || name_index <= EXT3_XATTR_INDEX_MAX) {
-+              write_lock(&ext3_handler_lock);
-+              ext3_xattr_handlers[name_index-1] = NULL;
-+              write_unlock(&ext3_handler_lock);
-+      }
-+}
-+
-+static inline const char *
-+strcmp_prefix(const char *a, const char *a_prefix)
-+{
-+      while (*a_prefix && *a == *a_prefix) {
-+              a++;
-+              a_prefix++;
-+      }
-+      return *a_prefix ? NULL : a;
-+}
-+
-+/*
-+ * Decode the extended attribute name, and translate it into
-+ * the name_index and name suffix.
-+ */
-+static inline struct ext3_xattr_handler *
-+ext3_xattr_resolve_name(const char **name)
-+{
-+      struct ext3_xattr_handler *handler = NULL;
-+      int i;
-+
-+      if (!*name)
-+              return NULL;
-+      read_lock(&ext3_handler_lock);
-+      for (i=0; i<EXT3_XATTR_INDEX_MAX; i++) {
-+              if (ext3_xattr_handlers[i]) {
-+                      const char *n = strcmp_prefix(*name,
-+                              ext3_xattr_handlers[i]->prefix);
-+                      if (n) {
-+                              handler = ext3_xattr_handlers[i];
-+                              *name = n;
-+                              break;
-+                      }
-+              }
-+      }
-+      read_unlock(&ext3_handler_lock);
-+      return handler;
-+}
-+
-+static inline struct ext3_xattr_handler *
-+ext3_xattr_handler(int name_index)
-+{
-+      struct ext3_xattr_handler *handler = NULL;
-+      if (name_index > 0 && name_index <= EXT3_XATTR_INDEX_MAX) {
-+              read_lock(&ext3_handler_lock);
-+              handler = ext3_xattr_handlers[name_index-1];
-+              read_unlock(&ext3_handler_lock);
-+      }
-+      return handler;
-+}
-+
-+/*
-+ * Inode operation getxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext3_getxattr(struct dentry *dentry, const char *name,
-+            void *buffer, size_t size)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->get(inode, name, buffer, size);
-+}
-+
-+/*
-+ * Inode operation listxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+ssize_t
-+ext3_listxattr(struct dentry *dentry, char *buffer, size_t size)
-+{
-+      return ext3_xattr_list(dentry->d_inode, buffer, size);
-+}
-+
-+/*
-+ * Inode operation setxattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext3_setxattr(struct dentry *dentry, const char *name,
-+            const void *value, size_t size, int flags)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      if (size == 0)
-+              value = "";  /* empty EA, do not remove */
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, value, size, flags);
-+}
-+
-+/*
-+ * Inode operation removexattr()
-+ *
-+ * dentry->d_inode->i_sem down
-+ * BKL held [before 2.5.x]
-+ */
-+int
-+ext3_removexattr(struct dentry *dentry, const char *name)
-+{
-+      struct ext3_xattr_handler *handler;
-+      struct inode *inode = dentry->d_inode;
-+
-+      handler = ext3_xattr_resolve_name(&name);
-+      if (!handler)
-+              return -ENOTSUP;
-+      return handler->set(inode, name, NULL, 0, XATTR_REPLACE);
-+}
-+
-+/*
-+ * ext3_xattr_get()
-+ *
-+ * Copy an extended attribute into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext3_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_entry *entry;
-+      unsigned int block, size;
-+      char *end;
-+      int name_len, error;
-+
-+      ea_idebug(inode, "name=%d.%s, buffer=%p, buffer_size=%ld",
-+                name_index, name, buffer, (long)buffer_size);
-+
-+      if (name == NULL)
-+              return -EINVAL;
-+      if (!EXT3_I(inode)->i_file_acl)
-+              return -ENOATTR;
-+      block = EXT3_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext3_error(inode->i_sb, "ext3_xattr_get",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* find named attribute */
-+      name_len = strlen(name);
-+
-+      error = -ERANGE;
-+      if (name_len > 255)
-+              goto cleanup;
-+      entry = FIRST_ENTRY(bh);
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              if (name_index == entry->e_name_index &&
-+                  name_len == entry->e_name_len &&
-+                  memcmp(name, entry->e_name, name_len) == 0)
-+                      goto found;
-+              entry = next;
-+      }
-+      /* Check the remaining name entries */
-+      while (!IS_LAST_ENTRY(entry)) {
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+              entry = next;
-+      }
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      error = -ENOATTR;
-+      goto cleanup;
-+found:
-+      /* check the buffer size */
-+      if (entry->e_value_block != 0)
-+              goto bad_block;
-+      size = le32_to_cpu(entry->e_value_size);
-+      if (size > inode->i_sb->s_blocksize ||
-+          le16_to_cpu(entry->e_value_offs) + size > inode->i_sb->s_blocksize)
-+              goto bad_block;
-+
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (buffer) {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+              /* return value of attribute */
-+              memcpy(buffer, bh->b_data + le16_to_cpu(entry->e_value_offs),
-+                      size);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_list()
-+ *
-+ * Copy a list of attribute names into the buffer
-+ * provided, or compute the buffer size required.
-+ * Buffer is NULL to compute the size of the buffer required.
-+ *
-+ * Returns a negative error number on failure, or the number of bytes
-+ * used / required on success.
-+ */
-+int
-+ext3_xattr_list(struct inode *inode, char *buffer, size_t buffer_size)
-+{
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_entry *entry;
-+      unsigned int block, size = 0;
-+      char *buf, *end;
-+      int error;
-+
-+      ea_idebug(inode, "buffer=%p, buffer_size=%ld",
-+                buffer, (long)buffer_size);
-+
-+      if (!EXT3_I(inode)->i_file_acl)
-+              return 0;
-+      block = EXT3_I(inode)->i_file_acl;
-+      ea_idebug(inode, "reading block %d", block);
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh)
-+              return -EIO;
-+      ea_bdebug(bh, "b_count=%d, refcount=%d",
-+              atomic_read(&(bh->b_count)), le32_to_cpu(HDR(bh)->h_refcount));
-+      end = bh->b_data + bh->b_size;
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+bad_block:    ext3_error(inode->i_sb, "ext3_xattr_list",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              error = -EIO;
-+              goto cleanup;
-+      }
-+      /* compute the size required for the list of attribute names */
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT3_XATTR_NEXT(entry)) {
-+              struct ext3_xattr_handler *handler;
-+              struct ext3_xattr_entry *next =
-+                      EXT3_XATTR_NEXT(entry);
-+              if ((char *)next >= end)
-+                      goto bad_block;
-+
-+              handler = ext3_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      size += handler->list(NULL, inode, entry->e_name,
-+                                            entry->e_name_len);
-+      }
-+
-+      if (ext3_xattr_cache_insert(bh))
-+              ea_idebug(inode, "cache insert failed");
-+      if (!buffer) {
-+              error = size;
-+              goto cleanup;
-+      } else {
-+              error = -ERANGE;
-+              if (size > buffer_size)
-+                      goto cleanup;
-+      }
-+
-+      /* list the attribute names */
-+      buf = buffer;
-+      for (entry = FIRST_ENTRY(bh); !IS_LAST_ENTRY(entry);
-+           entry = EXT3_XATTR_NEXT(entry)) {
-+              struct ext3_xattr_handler *handler;
-+
-+              handler = ext3_xattr_handler(entry->e_name_index);
-+              if (handler)
-+                      buf += handler->list(buf, inode, entry->e_name,
-+                                           entry->e_name_len);
-+      }
-+      error = size;
-+
-+cleanup:
-+      brelse(bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * If the EXT3_FEATURE_COMPAT_EXT_ATTR feature of this file system is
-+ * not set, set it.
-+ */
-+static void ext3_xattr_update_super_block(handle_t *handle,
-+                                        struct super_block *sb)
-+{
-+      if (EXT3_HAS_COMPAT_FEATURE(sb, EXT3_FEATURE_COMPAT_EXT_ATTR))
-+              return;
-+
-+      lock_super(sb);
-+      ext3_journal_get_write_access(handle, EXT3_SB(sb)->s_sbh);
-+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,0)
-+      EXT3_SB(sb)->s_feature_compat |= EXT3_FEATURE_COMPAT_EXT_ATTR;
-+#endif
-+      EXT3_SB(sb)->s_es->s_feature_compat |=
-+              cpu_to_le32(EXT3_FEATURE_COMPAT_EXT_ATTR);
-+      sb->s_dirt = 1;
-+      ext3_journal_dirty_metadata(handle, EXT3_SB(sb)->s_sbh);
-+      unlock_super(sb);
-+}
-+
-+/*
-+ * ext3_xattr_set()
-+ *
-+ * Create, replace or remove an extended attribute for this inode. Buffer
-+ * is NULL to remove an existing extended attribute, and non-NULL to
-+ * either replace an existing extended attribute, or create a new extended
-+ * attribute. The flags XATTR_REPLACE and XATTR_CREATE
-+ * specify that an extended attribute must exist and must not exist
-+ * previous to the call, respectively.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+int
-+ext3_xattr_set(handle_t *handle, struct inode *inode, int name_index,
-+             const char *name, const void *value, size_t value_len, int flags)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *bh = NULL;
-+      struct ext3_xattr_header *header = NULL;
-+      struct ext3_xattr_entry *here, *last;
-+      unsigned int name_len;
-+      int block = EXT3_I(inode)->i_file_acl;
-+      int min_offs = sb->s_blocksize, not_found = 1, free, error;
-+      char *end;
-+      
-+      /*
-+       * header -- Points either into bh, or to a temporarily
-+       *           allocated buffer.
-+       * here -- The named entry found, or the place for inserting, within
-+       *         the block pointed to by header.
-+       * last -- Points right after the last named entry within the block
-+       *         pointed to by header.
-+       * min_offs -- The offset of the first value (values are aligned
-+       *             towards the end of the block).
-+       * end -- Points right after the block pointed to by header.
-+       */
-+      
-+      ea_idebug(inode, "name=%d.%s, value=%p, value_len=%ld",
-+                name_index, name, value, (long)value_len);
-+
-+      if (IS_RDONLY(inode))
-+              return -EROFS;
-+      if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
-+              return -EPERM;
-+      if (value == NULL)
-+              value_len = 0;
-+      if (name == NULL)
-+              return -EINVAL;
-+      name_len = strlen(name);
-+      if (name_len > 255 || value_len > sb->s_blocksize)
-+              return -ERANGE;
-+      down(&ext3_xattr_sem);
-+
-+      if (block) {
-+              /* The inode already has an extended attribute block. */
-+              bh = sb_bread(sb, block);
-+              error = -EIO;
-+              if (!bh)
-+                      goto cleanup;
-+              ea_bdebug(bh, "b_count=%d, refcount=%d",
-+                      atomic_read(&(bh->b_count)),
-+                      le32_to_cpu(HDR(bh)->h_refcount));
-+              header = HDR(bh);
-+              end = bh->b_data + bh->b_size;
-+              if (header->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+                  header->h_blocks != cpu_to_le32(1)) {
-+bad_block:            ext3_error(sb, "ext3_xattr_set",
-+                              "inode %ld: bad block %d", inode->i_ino, block);
-+                      error = -EIO;
-+                      goto cleanup;
-+              }
-+              /* Find the named attribute. */
-+              here = FIRST_ENTRY(bh);
-+              while (!IS_LAST_ENTRY(here)) {
-+                      struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(here);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!here->e_value_block && here->e_value_size) {
-+                              int offs = le16_to_cpu(here->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      not_found = name_index - here->e_name_index;
-+                      if (!not_found)
-+                              not_found = name_len - here->e_name_len;
-+                      if (!not_found)
-+                              not_found = memcmp(name, here->e_name,name_len);
-+                      if (not_found <= 0)
-+                              break;
-+                      here = next;
-+              }
-+              last = here;
-+              /* We still need to compute min_offs and last. */
-+              while (!IS_LAST_ENTRY(last)) {
-+                      struct ext3_xattr_entry *next = EXT3_XATTR_NEXT(last);
-+                      if ((char *)next >= end)
-+                              goto bad_block;
-+                      if (!last->e_value_block && last->e_value_size) {
-+                              int offs = le16_to_cpu(last->e_value_offs);
-+                              if (offs < min_offs)
-+                                      min_offs = offs;
-+                      }
-+                      last = next;
-+              }
-+
-+              /* Check whether we have enough space left. */
-+              free = min_offs - ((char*)last - (char*)header) - sizeof(__u32);
-+      } else {
-+              /* We will use a new extended attribute block. */
-+              free = sb->s_blocksize -
-+                      sizeof(struct ext3_xattr_header) - sizeof(__u32);
-+              here = last = NULL;  /* avoid gcc uninitialized warning. */
-+      }
-+
-+      if (not_found) {
-+              /* Request to remove a nonexistent attribute? */
-+              error = -ENOATTR;
-+              if (flags & XATTR_REPLACE)
-+                      goto cleanup;
-+              error = 0;
-+              if (value == NULL)
-+                      goto cleanup;
-+              else
-+                      free -= EXT3_XATTR_LEN(name_len);
-+      } else {
-+              /* Request to create an existing attribute? */
-+              error = -EEXIST;
-+              if (flags & XATTR_CREATE)
-+                      goto cleanup;
-+              if (!here->e_value_block && here->e_value_size) {
-+                      unsigned int size = le32_to_cpu(here->e_value_size);
-+
-+                      if (le16_to_cpu(here->e_value_offs) + size > 
-+                          sb->s_blocksize || size > sb->s_blocksize)
-+                              goto bad_block;
-+                      free += EXT3_XATTR_SIZE(size);
-+              }
-+      }
-+      free -= EXT3_XATTR_SIZE(value_len);
-+      error = -ENOSPC;
-+      if (free < 0)
-+              goto cleanup;
-+
-+      /* Here we know that we can set the new attribute. */
-+
-+      if (header) {
-+              if (header->h_refcount == cpu_to_le32(1)) {
-+                      ea_bdebug(bh, "modifying in-place");
-+                      ext3_xattr_cache_remove(bh);
-+                      error = ext3_journal_get_write_access(handle, bh);
-+                      if (error)
-+                              goto cleanup;
-+              } else {
-+                      int offset;
-+
-+                      ea_bdebug(bh, "cloning");
-+                      header = kmalloc(bh->b_size, GFP_KERNEL);
-+                      error = -ENOMEM;
-+                      if (header == NULL)
-+                              goto cleanup;
-+                      memcpy(header, HDR(bh), bh->b_size);
-+                      header->h_refcount = cpu_to_le32(1);
-+                      offset = (char *)header - bh->b_data;
-+                      here = ENTRY((char *)here + offset);
-+                      last = ENTRY((char *)last + offset);
-+              }
-+      } else {
-+              /* Allocate a buffer where we construct the new block. */
-+              header = kmalloc(sb->s_blocksize, GFP_KERNEL);
-+              error = -ENOMEM;
-+              if (header == NULL)
-+                      goto cleanup;
-+              memset(header, 0, sb->s_blocksize);
-+              end = (char *)header + sb->s_blocksize;
-+              header->h_magic = cpu_to_le32(EXT3_XATTR_MAGIC);
-+              header->h_blocks = header->h_refcount = cpu_to_le32(1);
-+              last = here = ENTRY(header+1);
-+      }
-+
-+      if (not_found) {
-+              /* Insert the new name. */
-+              int size = EXT3_XATTR_LEN(name_len);
-+              int rest = (char *)last - (char *)here;
-+              memmove((char *)here + size, here, rest);
-+              memset(here, 0, size);
-+              here->e_name_index = name_index;
-+              here->e_name_len = name_len;
-+              memcpy(here->e_name, name, name_len);
-+      } else {
-+              /* Remove the old value. */
-+              if (!here->e_value_block && here->e_value_size) {
-+                      char *first_val = (char *)header + min_offs;
-+                      int offs = le16_to_cpu(here->e_value_offs);
-+                      char *val = (char *)header + offs;
-+                      size_t size = EXT3_XATTR_SIZE(
-+                              le32_to_cpu(here->e_value_size));
-+                      memmove(first_val + size, first_val, val - first_val);
-+                      memset(first_val, 0, size);
-+                      here->e_value_offs = 0;
-+                      min_offs += size;
-+
-+                      /* Adjust all value offsets. */
-+                      last = ENTRY(header+1);
-+                      while (!IS_LAST_ENTRY(last)) {
-+                              int o = le16_to_cpu(last->e_value_offs);
-+                              if (!last->e_value_block && o < offs)
-+                                      last->e_value_offs =
-+                                              cpu_to_le16(o + size);
-+                              last = EXT3_XATTR_NEXT(last);
-+                      }
-+              }
-+              if (value == NULL) {
-+                      /* Remove this attribute. */
-+                      if (EXT3_XATTR_NEXT(ENTRY(header+1)) == last) {
-+                              /* This block is now empty. */
-+                              error = ext3_xattr_set2(handle, inode, bh,NULL);
-+                              goto cleanup;
-+                      } else {
-+                              /* Remove the old name. */
-+                              int size = EXT3_XATTR_LEN(name_len);
-+                              last = ENTRY((char *)last - size);
-+                              memmove(here, (char*)here + size,
-+                                      (char*)last - (char*)here);
-+                              memset(last, 0, size);
-+                      }
-+              }
-+      }
-+
-+      if (value != NULL) {
-+              /* Insert the new value. */
-+              here->e_value_size = cpu_to_le32(value_len);
-+              if (value_len) {
-+                      size_t size = EXT3_XATTR_SIZE(value_len);
-+                      char *val = (char *)header + min_offs - size;
-+                      here->e_value_offs =
-+                              cpu_to_le16((char *)val - (char *)header);
-+                      memset(val + size - EXT3_XATTR_PAD, 0,
-+                             EXT3_XATTR_PAD); /* Clear the pad bytes. */
-+                      memcpy(val, value, value_len);
-+              }
-+      }
-+      ext3_xattr_rehash(header, here);
-+
-+      error = ext3_xattr_set2(handle, inode, bh, header);
-+
-+cleanup:
-+      brelse(bh);
-+      if (!(bh && header == HDR(bh)))
-+              kfree(header);
-+      up(&ext3_xattr_sem);
-+
-+      return error;
-+}
-+
-+/*
-+ * Second half of ext3_xattr_set(): Update the file system.
-+ */
-+static int
-+ext3_xattr_set2(handle_t *handle, struct inode *inode,
-+              struct buffer_head *old_bh, struct ext3_xattr_header *header)
-+{
-+      struct super_block *sb = inode->i_sb;
-+      struct buffer_head *new_bh = NULL;
-+      int error;
-+
-+      if (header) {
-+              new_bh = ext3_xattr_cache_find(inode, header);
-+              if (new_bh) {
-+                      /*
-+                       * We found an identical block in the cache.
-+                       * The old block will be released after updating
-+                       * the inode.
-+                       */
-+                      ea_bdebug(old_bh, "reusing block %ld",
-+                              new_bh->b_blocknr);
-+                      
-+                      error = -EDQUOT;
-+                      if (ext3_xattr_quota_alloc(inode, 1))
-+                              goto cleanup;
-+                      
-+                      error = ext3_journal_get_write_access(handle, new_bh);
-+                      if (error)
-+                              goto cleanup;
-+                      HDR(new_bh)->h_refcount = cpu_to_le32(
-+                              le32_to_cpu(HDR(new_bh)->h_refcount) + 1);
-+                      ea_bdebug(new_bh, "refcount now=%d",
-+                              le32_to_cpu(HDR(new_bh)->h_refcount));
-+              } else if (old_bh && header == HDR(old_bh)) {
-+                      /* Keep this block. */
-+                      new_bh = old_bh;
-+                      (void)ext3_xattr_cache_insert(new_bh);
-+              } else {
-+                      /* We need to allocate a new block */
-+                      int force = EXT3_I(inode)->i_file_acl != 0;
-+                      int block = ext3_xattr_new_block(handle, inode,
-+                                                       &error, force);
-+                      if (error)
-+                              goto cleanup;
-+                      ea_idebug(inode, "creating block %d", block);
-+
-+                      new_bh = sb_getblk(sb, block);
-+                      if (!new_bh) {
-+getblk_failed:                        ext3_xattr_free_block(handle, inode, block);
-+                              error = -EIO;
-+                              goto cleanup;
-+                      }
-+                      lock_buffer(new_bh);
-+                      error = ext3_journal_get_create_access(handle, new_bh);
-+                      if (error) {
-+                              unlock_buffer(new_bh);
-+                              goto getblk_failed;
-+                      }
-+                      memcpy(new_bh->b_data, header, new_bh->b_size);
-+                      mark_buffer_uptodate(new_bh, 1);
-+                      unlock_buffer(new_bh);
-+                      (void)ext3_xattr_cache_insert(new_bh);
-+                      
-+                      ext3_xattr_update_super_block(handle, sb);
-+              }
-+              error = ext3_journal_dirty_metadata(handle, new_bh);
-+              if (error)
-+                      goto cleanup;
-+      }
-+
-+      /* Update the inode. */
-+      EXT3_I(inode)->i_file_acl = new_bh ? new_bh->b_blocknr : 0;
-+      inode->i_ctime = CURRENT_TIME;
-+      ext3_mark_inode_dirty(handle, inode);
-+      if (IS_SYNC(inode))
-+              handle->h_sync = 1;
-+
-+      error = 0;
-+      if (old_bh && old_bh != new_bh) {
-+              /*
-+               * If there was an old block, and we are not still using it,
-+               * we now release the old block.
-+              */
-+              unsigned int refcount = le32_to_cpu(HDR(old_bh)->h_refcount);
-+
-+              error = ext3_journal_get_write_access(handle, old_bh);
-+              if (error)
-+                      goto cleanup;
-+              if (refcount == 1) {
-+                      /* Free the old block. */
-+                      ea_bdebug(old_bh, "freeing");
-+                      ext3_xattr_free_block(handle, inode, old_bh->b_blocknr);
-+
-+                      /* ext3_forget() calls bforget() for us, but we
-+                         let our caller release old_bh, so we need to
-+                         duplicate the handle before. */
-+                      get_bh(old_bh);
-+                      ext3_forget(handle, 1, inode, old_bh,old_bh->b_blocknr);
-+              } else {
-+                      /* Decrement the refcount only. */
-+                      refcount--;
-+                      HDR(old_bh)->h_refcount = cpu_to_le32(refcount);
-+                      ext3_xattr_quota_free(inode);
-+                      ext3_journal_dirty_metadata(handle, old_bh);
-+                      ea_bdebug(old_bh, "refcount now=%d", refcount);
-+              }
-+      }
-+
-+cleanup:
-+      if (old_bh != new_bh)
-+              brelse(new_bh);
-+
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_delete_inode()
-+ *
-+ * Free extended attribute resources associated with this inode. This
-+ * is called immediately before an inode is freed.
-+ */
-+void
-+ext3_xattr_delete_inode(handle_t *handle, struct inode *inode)
-+{
-+      struct buffer_head *bh;
-+      unsigned int block = EXT3_I(inode)->i_file_acl;
-+
-+      if (!block)
-+              return;
-+      down(&ext3_xattr_sem);
-+
-+      bh = sb_bread(inode->i_sb, block);
-+      if (!bh) {
-+              ext3_error(inode->i_sb, "ext3_xattr_delete_inode",
-+                      "inode %ld: block %d read error", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ea_bdebug(bh, "b_count=%d", atomic_read(&(bh->b_count)));
-+      if (HDR(bh)->h_magic != cpu_to_le32(EXT3_XATTR_MAGIC) ||
-+          HDR(bh)->h_blocks != cpu_to_le32(1)) {
-+              ext3_error(inode->i_sb, "ext3_xattr_delete_inode",
-+                      "inode %ld: bad block %d", inode->i_ino, block);
-+              goto cleanup;
-+      }
-+      ext3_journal_get_write_access(handle, bh);
-+      ea_bdebug(bh, "refcount now=%d", le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+      if (HDR(bh)->h_refcount == cpu_to_le32(1)) {
-+              ext3_xattr_cache_remove(bh);
-+              ext3_xattr_free_block(handle, inode, block);
-+              ext3_forget(handle, 1, inode, bh, block);
-+              bh = NULL;
-+      } else {
-+              HDR(bh)->h_refcount = cpu_to_le32(
-+                      le32_to_cpu(HDR(bh)->h_refcount) - 1);
-+              ext3_journal_dirty_metadata(handle, bh);
-+              if (IS_SYNC(inode))
-+                      handle->h_sync = 1;
-+              ext3_xattr_quota_free(inode);
-+      }
-+      EXT3_I(inode)->i_file_acl = 0;
-+
-+cleanup:
-+      brelse(bh);
-+      up(&ext3_xattr_sem);
-+}
-+
-+/*
-+ * ext3_xattr_put_super()
-+ *
-+ * This is called when a file system is unmounted.
-+ */
-+void
-+ext3_xattr_put_super(struct super_block *sb)
-+{
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+      mb_cache_shrink(ext3_xattr_cache, sb->s_dev);
-+#endif
-+}
-+
-+#ifdef CONFIG_EXT3_FS_XATTR_SHARING
-+
-+/*
-+ * ext3_xattr_cache_insert()
-+ *
-+ * Create a new entry in the extended attribute cache, and insert
-+ * it unless such an entry is already in the cache.
-+ *
-+ * Returns 0, or a negative error number on failure.
-+ */
-+static int
-+ext3_xattr_cache_insert(struct buffer_head *bh)
-+{
-+      __u32 hash = le32_to_cpu(HDR(bh)->h_hash);
-+      struct mb_cache_entry *ce;
-+      int error;
-+
-+      ce = mb_cache_entry_alloc(ext3_xattr_cache);
-+      if (!ce)
-+              return -ENOMEM;
-+      error = mb_cache_entry_insert(ce, bh->b_dev, bh->b_blocknr, &hash);
-+      if (error) {
-+              mb_cache_entry_free(ce);
-+              if (error == -EBUSY) {
-+                      ea_bdebug(bh, "already in cache (%d cache entries)",
-+                              atomic_read(&ext3_xattr_cache->c_entry_count));
-+                      error = 0;
-+              }
-+      } else {
-+              ea_bdebug(bh, "inserting [%x] (%d cache entries)", (int)hash,
-+                        atomic_read(&ext3_xattr_cache->c_entry_count));
-+              mb_cache_entry_release(ce);
-+      }
-+      return error;
-+}
-+
-+/*
-+ * ext3_xattr_cmp()
-+ *
-+ * Compare two extended attribute blocks for equality.
-+ *
-+ * Returns 0 if the blocks are equal, 1 if they differ, and
-+ * a negative error number on errors.
-+ */
-+static int
-+ext3_xattr_cmp(struct ext3_xattr_header *header1,
-+             struct ext3_xattr_header *header2)
-+{
-+      struct ext3_xattr_entry *entry1, *entry2;
-+
-+      entry1 = ENTRY(header1+1);
-+      entry2 = ENTRY(header2+1);
-+      while (!IS_LAST_ENTRY(entry1)) {
-+              if (IS_LAST_ENTRY(entry2))
-+                      return 1;
-+              if (entry1->e_hash != entry2->e_hash ||
-+                  entry1->e_name_len != entry2->e_name_len ||
-+                  entry1->e_value_size != entry2->e_value_size ||
-+                  memcmp(entry1->e_name, entry2->e_name, entry1->e_name_len))
-+                      return 1;
-+              if (entry1->e_value_block != 0 || entry2->e_value_block != 0)
-+                      return -EIO;
-+              if (memcmp((char *)header1 + le16_to_cpu(entry1->e_value_offs),
-+                         (char *)header2 + le16_to_cpu(entry2->e_value_offs),
-+                         le32_to_cpu(entry1->e_value_size)))
-+                      return 1;
-+
-+              entry1 = EXT3_XATTR_NEXT(entry1);
-+              entry2 = EXT3_XATTR_NEXT(entry2);
-+      }
-+      if (!IS_LAST_ENTRY(entry2))
-+              return 1;
-+      return 0;
-+}
-+
-+/*
-+ * ext3_xattr_cache_find()
-+ *
-+ * Find an identical extended attribute block.
-+ *
-+ * Returns a pointer to the block found, or NULL if such a block was
-+ * not found or an error occurred.
-+ */
-+static struct buffer_head *
-+ext3_xattr_cache_find(struct inode *inode, struct ext3_xattr_header *header)
-+{
-+      __u32 hash = le32_to_cpu(header->h_hash);
-+      struct mb_cache_entry *ce;
-+
-+      if (!header->h_hash)
-+              return NULL;  /* never share */
-+      ea_idebug(inode, "looking for cached blocks [%x]", (int)hash);
-+      ce = mb_cache_entry_find_first(ext3_xattr_cache, 0, inode->i_dev, hash);
-+      while (ce) {
-+              struct buffer_head *bh = sb_bread(inode->i_sb, ce->e_block);
-+
-+              if (!bh) {
-+                      ext3_error(inode->i_sb, "ext3_xattr_cache_find",
-+                              "inode %ld: block %ld read error",
-+                              inode->i_ino, ce->e_block);
-+              } else if (le32_to_cpu(HDR(bh)->h_refcount) >
-+                         EXT3_XATTR_REFCOUNT_MAX) {
-+                      ea_idebug(inode, "block %ld refcount %d>%d",ce->e_block,
-+                              le32_to_cpu(HDR(bh)->h_refcount),
-+                              EXT3_XATTR_REFCOUNT_MAX);
-+              } else if (!ext3_xattr_cmp(header, HDR(bh))) {
-+                      ea_bdebug(bh, "b_count=%d",atomic_read(&(bh->b_count)));
-+                      mb_cache_entry_release(ce);
-+                      return bh;
-+              }
-+              brelse(bh);
-+              ce = mb_cache_entry_find_next(ce, 0, inode->i_dev, hash);
-+      }
-+      return NULL;
-+}
-+
-+/*
-+ * ext3_xattr_cache_remove()
-+ *
-+ * Remove the cache entry of a block from the cache. Called when a
-+ * block becomes invalid.
-+ */
-+static void
-+ext3_xattr_cache_remove(struct buffer_head *bh)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      ce = mb_cache_entry_get(ext3_xattr_cache, bh->b_dev, bh->b_blocknr);
-+      if (ce) {
-+              ea_bdebug(bh, "removing (%d cache entries remaining)",
-+                        atomic_read(&ext3_xattr_cache->c_entry_count)-1);
-+              mb_cache_entry_free(ce);
-+      } else 
-+              ea_bdebug(bh, "no cache entry");
-+}
-+
-+#define NAME_HASH_SHIFT 5
-+#define VALUE_HASH_SHIFT 16
-+
-+/*
-+ * ext3_xattr_hash_entry()
-+ *
-+ * Compute the hash of an extended attribute.
-+ */
-+static inline void ext3_xattr_hash_entry(struct ext3_xattr_header *header,
-+                                       struct ext3_xattr_entry *entry)
-+{
-+      __u32 hash = 0;
-+      char *name = entry->e_name;
-+      int n;
-+
-+      for (n=0; n < entry->e_name_len; n++) {
-+              hash = (hash << NAME_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - NAME_HASH_SHIFT)) ^
-+                     *name++;
-+      }
-+
-+      if (entry->e_value_block == 0 && entry->e_value_size != 0) {
-+              __u32 *value = (__u32 *)((char *)header +
-+                      le16_to_cpu(entry->e_value_offs));
-+              for (n = (le32_to_cpu(entry->e_value_size) +
-+                   EXT3_XATTR_ROUND) >> EXT3_XATTR_PAD_BITS; n; n--) {
-+                      hash = (hash << VALUE_HASH_SHIFT) ^
-+                             (hash >> (8*sizeof(hash) - VALUE_HASH_SHIFT)) ^
-+                             le32_to_cpu(*value++);
-+              }
-+      }
-+      entry->e_hash = cpu_to_le32(hash);
-+}
-+
-+#undef NAME_HASH_SHIFT
-+#undef VALUE_HASH_SHIFT
-+
-+#define BLOCK_HASH_SHIFT 16
-+
-+/*
-+ * ext3_xattr_rehash()
-+ *
-+ * Re-compute the extended attribute hash value after an entry has changed.
-+ */
-+static void ext3_xattr_rehash(struct ext3_xattr_header *header,
-+                            struct ext3_xattr_entry *entry)
-+{
-+      struct ext3_xattr_entry *here;
-+      __u32 hash = 0;
-+      
-+      ext3_xattr_hash_entry(header, entry);
-+      here = ENTRY(header+1);
-+      while (!IS_LAST_ENTRY(here)) {
-+              if (!here->e_hash) {
-+                      /* Block is not shared if an entry's hash value == 0 */
-+                      hash = 0;
-+                      break;
-+              }
-+              hash = (hash << BLOCK_HASH_SHIFT) ^
-+                     (hash >> (8*sizeof(hash) - BLOCK_HASH_SHIFT)) ^
-+                     le32_to_cpu(here->e_hash);
-+              here = EXT3_XATTR_NEXT(here);
-+      }
-+      header->h_hash = cpu_to_le32(hash);
-+}
-+
-+#undef BLOCK_HASH_SHIFT
-+
-+int __init
-+init_ext3_xattr(void)
-+{
-+      ext3_xattr_cache = mb_cache_create("ext3_xattr", NULL,
-+              sizeof(struct mb_cache_entry) +
-+              sizeof(struct mb_cache_entry_index), 1, 61);
-+      if (!ext3_xattr_cache)
-+              return -ENOMEM;
-+
-+      return 0;
-+}
-+
-+void
-+exit_ext3_xattr(void)
-+{
-+      if (ext3_xattr_cache)
-+              mb_cache_destroy(ext3_xattr_cache);
-+      ext3_xattr_cache = NULL;
-+}
-+
-+#else  /* CONFIG_EXT3_FS_XATTR_SHARING */
-+
-+int __init
-+init_ext3_xattr(void)
-+{
-+      return 0;
-+}
-+
-+void
-+exit_ext3_xattr(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT3_FS_XATTR_SHARING */
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/ext3/xattr_user.c       2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,111 @@
-+/*
-+ * linux/fs/ext3/xattr_user.c
-+ * Handler for extended user attributes.
-+ *
-+ * Copyright (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/string.h>
-+#include <linux/fs.h>
-+#include <linux/ext3_jbd.h>
-+#include <linux/ext3_fs.h>
-+#include <linux/ext3_xattr.h>
-+
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+# include <linux/ext3_acl.h>
-+#endif
-+
-+#define XATTR_USER_PREFIX "user."
-+
-+static size_t
-+ext3_xattr_user_list(char *list, struct inode *inode,
-+                   const char *name, int name_len)
-+{
-+      const int prefix_len = sizeof(XATTR_USER_PREFIX)-1;
-+
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return 0;
-+
-+      if (list) {
-+              memcpy(list, XATTR_USER_PREFIX, prefix_len);
-+              memcpy(list+prefix_len, name, name_len);
-+              list[prefix_len + name_len] = '\0';
-+      }
-+      return prefix_len + name_len + 1;
-+}
-+
-+static int
-+ext3_xattr_user_get(struct inode *inode, const char *name,
-+                  void *buffer, size_t size)
-+{
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+      error = ext3_permission_locked(inode, MAY_READ);
-+#else
-+      error = permission(inode, MAY_READ);
-+#endif
-+      if (error)
-+              return error;
-+
-+      return ext3_xattr_get(inode, EXT3_XATTR_INDEX_USER, name,
-+                            buffer, size);
-+}
-+
-+static int
-+ext3_xattr_user_set(struct inode *inode, const char *name,
-+                  const void *value, size_t size, int flags)
-+{
-+      handle_t *handle;
-+      int error;
-+
-+      if (strcmp(name, "") == 0)
-+              return -EINVAL;
-+      if (!test_opt(inode->i_sb, XATTR_USER))
-+              return -ENOTSUP;
-+      if ( !S_ISREG(inode->i_mode) &&
-+          (!S_ISDIR(inode->i_mode) || inode->i_mode & S_ISVTX))
-+              return -EPERM;
-+#ifdef CONFIG_EXT3_FS_POSIX_ACL
-+      error = ext3_permission_locked(inode, MAY_WRITE);
-+#else
-+      error = permission(inode, MAY_WRITE);
-+#endif
-+      if (error)
-+              return error;
-+
-+      handle = ext3_journal_start(inode, EXT3_XATTR_TRANS_BLOCKS);
-+      if (IS_ERR(handle))
-+              return PTR_ERR(handle);
-+      error = ext3_xattr_set(handle, inode, EXT3_XATTR_INDEX_USER, name,
-+                             value, size, flags);
-+      ext3_journal_stop(handle, inode);
-+
-+      return error;
-+}
-+
-+struct ext3_xattr_handler ext3_xattr_user_handler = {
-+      prefix: XATTR_USER_PREFIX,
-+      list:   ext3_xattr_user_list,
-+      get:    ext3_xattr_user_get,
-+      set:    ext3_xattr_user_set,
-+};
-+
-+int __init
-+init_ext3_xattr_user(void)
-+{
-+      return ext3_xattr_register(EXT3_XATTR_INDEX_USER,
-+                                 &ext3_xattr_user_handler);
-+}
-+
-+void
-+exit_ext3_xattr_user(void)
-+{
-+      ext3_xattr_unregister(EXT3_XATTR_INDEX_USER,
-+                            &ext3_xattr_user_handler);
-+}
---- linux-2.4.22-ac1/fs/jfs/jfs_xattr.h~xattr-0.8.54-2.4.22-rh 2002-11-29 02:53:15.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/jfs/jfs_xattr.h 2003-09-25 23:57:02.000000000 +0400
-@@ -52,8 +52,10 @@ struct jfs_ea_list {
- #define       END_EALIST(ealist) \
-       ((struct jfs_ea *) (((char *) (ealist)) + EALIST_SIZE(ealist)))
--extern int __jfs_setxattr(struct inode *, const char *, void *, size_t, int);
--extern int jfs_setxattr(struct dentry *, const char *, void *, size_t, int);
-+extern int __jfs_setxattr(struct inode *, const char *, const void *, size_t,
-+                        int);
-+extern int jfs_setxattr(struct dentry *, const char *, const void *, size_t,
-+                      int);
- extern ssize_t __jfs_getxattr(struct inode *, const char *, void *, size_t);
- extern ssize_t jfs_getxattr(struct dentry *, const char *, void *, size_t);
- extern ssize_t jfs_listxattr(struct dentry *, char *, size_t);
---- linux-2.4.22-ac1/fs/jfs/xattr.c~xattr-0.8.54-2.4.22-rh     2002-11-29 02:53:15.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/jfs/xattr.c     2003-09-25 23:57:02.000000000 +0400
-@@ -641,7 +641,7 @@ static int ea_put(struct inode *inode, s
- }
- static int can_set_xattr(struct inode *inode, const char *name,
--                       void *value, size_t value_len)
-+                       const void *value, size_t value_len)
- {
-       if (IS_RDONLY(inode))
-               return -EROFS;
-@@ -660,7 +660,7 @@ static int can_set_xattr(struct inode *i
-       return permission(inode, MAY_WRITE);
- }
--int __jfs_setxattr(struct inode *inode, const char *name, void *value,
-+int __jfs_setxattr(struct inode *inode, const char *name, const void *value,
-                  size_t value_len, int flags)
- {
-       struct jfs_ea_list *ealist;
-@@ -799,7 +799,7 @@ int __jfs_setxattr(struct inode *inode, 
-       return rc;
- }
--int jfs_setxattr(struct dentry *dentry, const char *name, void *value,
-+int jfs_setxattr(struct dentry *dentry, const char *name, const void *value,
-                size_t value_len, int flags)
- {
-       if (value == NULL) {    /* empty EA, do not remove */
---- linux-2.4.22-ac1/fs/Makefile~xattr-0.8.54-2.4.22-rh        2003-09-25 14:50:00.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/fs/Makefile        2003-09-25 23:57:02.000000000 +0400
-@@ -82,6 +82,9 @@ obj-y                                += binfmt_script.o
- obj-$(CONFIG_BINFMT_ELF)      += binfmt_elf.o
-+export-objs += mbcache.o
-+obj-$(CONFIG_FS_MBCACHE)      += mbcache.o
-+
- # persistent filesystems
- obj-y += $(join $(subdir-y),$(subdir-y:%=/%.o))
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/fs/mbcache.c       2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,648 @@
-+/*
-+ * linux/fs/mbcache.c
-+ * (C) 2001-2002 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+/*
-+ * Filesystem Meta Information Block Cache (mbcache)
-+ *
-+ * The mbcache caches blocks of block devices that need to be located
-+ * by their device/block number, as well as by other criteria (such
-+ * as the block's contents).
-+ *
-+ * There can only be one cache entry in a cache per device and block number.
-+ * Additional indexes need not be unique in this sense. The number of
-+ * additional indexes (=other criteria) can be hardwired at compile time
-+ * or specified at cache create time.
-+ *
-+ * Each cache entry is of fixed size. An entry may be `valid' or `invalid'
-+ * in the cache. A valid entry is in the main hash tables of the cache,
-+ * and may also be in the lru list. An invalid entry is not in any hashes
-+ * or lists.
-+ *
-+ * A valid cache entry is only in the lru list if no handles refer to it.
-+ * Invalid cache entries will be freed when the last handle to the cache
-+ * entry is released. Entries that cannot be freed immediately are put
-+ * back on the lru list.
-+ */
-+
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+
-+#include <linux/fs.h>
-+#include <linux/slab.h>
-+#include <linux/sched.h>
-+#include <linux/cache_def.h>
-+#include <linux/version.h>
-+#include <linux/init.h>
-+#include <linux/mbcache.h>
-+
-+
-+#ifdef MB_CACHE_DEBUG
-+# define mb_debug(f...) do { \
-+              printk(KERN_DEBUG f); \
-+              printk("\n"); \
-+      } while (0)
-+#define mb_assert(c) do { if (!(c)) \
-+              printk(KERN_ERR "assertion " #c " failed\n"); \
-+      } while(0)
-+#else
-+# define mb_debug(f...) do { } while(0)
-+# define mb_assert(c) do { } while(0)
-+#endif
-+#define mb_error(f...) do { \
-+              printk(KERN_ERR f); \
-+              printk("\n"); \
-+      } while(0)
-+              
-+MODULE_AUTHOR("Andreas Gruenbacher <a.gruenbacher@computer.org>");
-+MODULE_DESCRIPTION("Meta block cache (for extended attributes)");
-+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,0)
-+MODULE_LICENSE("GPL");
-+#endif
-+
-+EXPORT_SYMBOL(mb_cache_create);
-+EXPORT_SYMBOL(mb_cache_shrink);
-+EXPORT_SYMBOL(mb_cache_destroy);
-+EXPORT_SYMBOL(mb_cache_entry_alloc);
-+EXPORT_SYMBOL(mb_cache_entry_insert);
-+EXPORT_SYMBOL(mb_cache_entry_release);
-+EXPORT_SYMBOL(mb_cache_entry_takeout);
-+EXPORT_SYMBOL(mb_cache_entry_free);
-+EXPORT_SYMBOL(mb_cache_entry_dup);
-+EXPORT_SYMBOL(mb_cache_entry_get);
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+EXPORT_SYMBOL(mb_cache_entry_find_first);
-+EXPORT_SYMBOL(mb_cache_entry_find_next);
-+#endif
-+
-+
-+/*
-+ * Global data: list of all mbcache's, lru list, and a spinlock for
-+ * accessing cache data structures on SMP machines. The lru list is
-+ * global across all mbcaches.
-+ */
-+
-+static LIST_HEAD(mb_cache_list);
-+static LIST_HEAD(mb_cache_lru_list);
-+static spinlock_t mb_cache_spinlock = SPIN_LOCK_UNLOCKED;
-+
-+static inline int
-+mb_cache_indexes(struct mb_cache *cache)
-+{
-+#ifdef MB_CACHE_INDEXES_COUNT
-+      return MB_CACHE_INDEXES_COUNT;
-+#else
-+      return cache->c_indexes_count;
-+#endif
-+}
-+
-+/*
-+ * What the mbcache registers as to get shrunk dynamically.
-+ */
-+
-+static void
-+mb_cache_memory_pressure(int priority, unsigned int gfp_mask);
-+
-+static struct cache_definition mb_cache_definition = {
-+      "mb_cache",
-+      mb_cache_memory_pressure
-+};
-+
-+
-+static inline int
-+__mb_cache_entry_is_hashed(struct mb_cache_entry *ce)
-+{
-+      return !list_empty(&ce->e_block_list);
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_unhash(struct mb_cache_entry *ce)
-+{
-+      int n;
-+
-+      if (__mb_cache_entry_is_hashed(ce)) {
-+              list_del_init(&ce->e_block_list);
-+              for (n=0; n<mb_cache_indexes(ce->e_cache); n++)
-+                      list_del(&ce->e_indexes[n].o_list);
-+      }
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_forget(struct mb_cache_entry *ce, int gfp_mask)
-+{
-+      struct mb_cache *cache = ce->e_cache;
-+
-+      mb_assert(atomic_read(&ce->e_used) == 0);
-+      if (cache->c_op.free && cache->c_op.free(ce, gfp_mask)) {
-+              /* free failed -- put back on the lru list
-+                 for freeing later. */
-+              spin_lock(&mb_cache_spinlock);
-+              list_add(&ce->e_lru_list, &mb_cache_lru_list);
-+              spin_unlock(&mb_cache_spinlock);
-+      } else {
-+              kmem_cache_free(cache->c_entry_cache, ce);
-+              atomic_dec(&cache->c_entry_count);
-+      }
-+}
-+
-+
-+static inline void
-+__mb_cache_entry_release_unlock(struct mb_cache_entry *ce)
-+{
-+      if (atomic_dec_and_test(&ce->e_used)) {
-+              if (__mb_cache_entry_is_hashed(ce))
-+                      list_add_tail(&ce->e_lru_list, &mb_cache_lru_list);
-+              else {
-+                      spin_unlock(&mb_cache_spinlock);
-+                      __mb_cache_entry_forget(ce, GFP_KERNEL);
-+                      return;
-+              }
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+}
-+
-+
-+/*
-+ * mb_cache_memory_pressure()  memory pressure callback
-+ *
-+ * This function is called by the kernel memory management when memory
-+ * gets low.
-+ *
-+ * @priority: Amount by which to shrink the cache (0 = highes priority)
-+ * @gfp_mask: (ignored)
-+ */
-+static void
-+mb_cache_memory_pressure(int priority, unsigned int gfp_mask)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+      int count = 0;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &mb_cache_list) {
-+              struct mb_cache *cache =
-+                      list_entry(l, struct mb_cache, c_cache_list);
-+              mb_debug("cache %s (%d)", cache->c_name,
-+                        atomic_read(&cache->c_entry_count));
-+              count += atomic_read(&cache->c_entry_count);
-+      }
-+      mb_debug("trying to free %d of %d entries",
-+                count / (priority ? priority : 1), count);
-+      if (priority)
-+              count /= priority;
-+      while (count-- && !list_empty(&mb_cache_lru_list)) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(mb_cache_lru_list.next,
-+                                 struct mb_cache_entry, e_lru_list);
-+              list_del(&ce->e_lru_list);
-+              __mb_cache_entry_unhash(ce);
-+              list_add_tail(&ce->e_lru_list, &free_list);
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), gfp_mask);
-+      }
-+}
-+
-+
-+/*
-+ * mb_cache_create()  create a new cache
-+ *
-+ * All entries in one cache are equal size. Cache entries may be from
-+ * multiple devices. If this is the first mbcache created, registers
-+ * the cache with kernel memory management. Returns NULL if no more
-+ * memory was available.
-+ *
-+ * @name: name of the cache (informal)
-+ * @cache_op: contains the callback called when freeing a cache entry
-+ * @entry_size: The size of a cache entry, including
-+ *              struct mb_cache_entry
-+ * @indexes_count: number of additional indexes in the cache. Must equal
-+ *                 MB_CACHE_INDEXES_COUNT if the number of indexes is
-+ *                 hardwired.
-+ * @bucket_count: number of hash buckets
-+ */
-+struct mb_cache *
-+mb_cache_create(const char *name, struct mb_cache_op *cache_op,
-+              size_t entry_size, int indexes_count, int bucket_count)
-+{
-+      int m=0, n;
-+      struct mb_cache *cache = NULL;
-+
-+      if(entry_size < sizeof(struct mb_cache_entry) +
-+         indexes_count * sizeof(struct mb_cache_entry_index))
-+              return NULL;
-+
-+      MOD_INC_USE_COUNT;
-+      cache = kmalloc(sizeof(struct mb_cache) +
-+                      indexes_count * sizeof(struct list_head), GFP_KERNEL);
-+      if (!cache)
-+              goto fail;
-+      cache->c_name = name;
-+      cache->c_op.free = NULL;
-+      if (cache_op)
-+              cache->c_op.free = cache_op->free;
-+      atomic_set(&cache->c_entry_count, 0);
-+      cache->c_bucket_count = bucket_count;
-+#ifdef MB_CACHE_INDEXES_COUNT
-+      mb_assert(indexes_count == MB_CACHE_INDEXES_COUNT);
-+#else
-+      cache->c_indexes_count = indexes_count;
-+#endif
-+      cache->c_block_hash = kmalloc(bucket_count * sizeof(struct list_head),
-+                                    GFP_KERNEL);
-+      if (!cache->c_block_hash)
-+              goto fail;
-+      for (n=0; n<bucket_count; n++)
-+              INIT_LIST_HEAD(&cache->c_block_hash[n]);
-+      for (m=0; m<indexes_count; m++) {
-+              cache->c_indexes_hash[m] = kmalloc(bucket_count *
-+                                               sizeof(struct list_head),
-+                                               GFP_KERNEL);
-+              if (!cache->c_indexes_hash[m])
-+                      goto fail;
-+              for (n=0; n<bucket_count; n++)
-+                      INIT_LIST_HEAD(&cache->c_indexes_hash[m][n]);
-+      }
-+      cache->c_entry_cache = kmem_cache_create(name, entry_size, 0,
-+              0 /*SLAB_POISON | SLAB_RED_ZONE*/, NULL, NULL);
-+      if (!cache->c_entry_cache)
-+              goto fail;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_add(&cache->c_cache_list, &mb_cache_list);
-+      spin_unlock(&mb_cache_spinlock);
-+      return cache;
-+
-+fail:
-+      if (cache) {
-+              while (--m >= 0)
-+                      kfree(cache->c_indexes_hash[m]);
-+              if (cache->c_block_hash)
-+                      kfree(cache->c_block_hash);
-+              kfree(cache);
-+      }
-+      MOD_DEC_USE_COUNT;
-+      return NULL;
-+}
-+
-+
-+/*
-+ * mb_cache_shrink()
-+ *
-+ * Removes all cache entires of a device from the cache. All cache entries
-+ * currently in use cannot be freed, and thus remain in the cache.
-+ *
-+ * @cache: which cache to shrink
-+ * @dev: which device's cache entries to shrink
-+ */
-+void
-+mb_cache_shrink(struct mb_cache *cache, kdev_t dev)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &mb_cache_lru_list) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_lru_list);
-+              if (ce->e_dev == dev) {
-+                      list_del(&ce->e_lru_list);
-+                      list_add_tail(&ce->e_lru_list, &free_list);
-+                      __mb_cache_entry_unhash(ce);
-+              }
-+      }
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), GFP_KERNEL);
-+      }
-+}
-+
-+
-+/*
-+ * mb_cache_destroy()
-+ *
-+ * Shrinks the cache to its minimum possible size (hopefully 0 entries),
-+ * and then destroys it. If this was the last mbcache, un-registers the
-+ * mbcache from kernel memory management.
-+ */
-+void
-+mb_cache_destroy(struct mb_cache *cache)
-+{
-+      LIST_HEAD(free_list);
-+      struct list_head *l, *ltmp;
-+      int n;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &mb_cache_lru_list) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_lru_list);
-+              if (ce->e_cache == cache) {
-+                      list_del(&ce->e_lru_list);
-+                      list_add_tail(&ce->e_lru_list, &free_list);
-+                      __mb_cache_entry_unhash(ce);
-+              }
-+      }
-+      list_del(&cache->c_cache_list);
-+      spin_unlock(&mb_cache_spinlock);
-+      list_for_each_safe(l, ltmp, &free_list) {
-+              __mb_cache_entry_forget(list_entry(l, struct mb_cache_entry,
-+                                                 e_lru_list), GFP_KERNEL);
-+      }
-+
-+      if (atomic_read(&cache->c_entry_count) > 0) {
-+              mb_error("cache %s: %d orphaned entries",
-+                        cache->c_name,
-+                        atomic_read(&cache->c_entry_count));
-+      }
-+
-+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,3,0))
-+      /* We don't have kmem_cache_destroy() in 2.2.x */
-+      kmem_cache_shrink(cache->c_entry_cache);
-+#else
-+      kmem_cache_destroy(cache->c_entry_cache);
-+#endif
-+      for (n=0; n < mb_cache_indexes(cache); n++)
-+              kfree(cache->c_indexes_hash[n]);
-+      kfree(cache->c_block_hash);
-+      kfree(cache);
-+
-+      MOD_DEC_USE_COUNT;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_alloc()
-+ *
-+ * Allocates a new cache entry. The new entry will not be valid initially,
-+ * and thus cannot be looked up yet. It should be filled with data, and
-+ * then inserted into the cache using mb_cache_entry_insert(). Returns NULL
-+ * if no more memory was available.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_alloc(struct mb_cache *cache)
-+{
-+      struct mb_cache_entry *ce;
-+
-+      atomic_inc(&cache->c_entry_count);
-+      ce = kmem_cache_alloc(cache->c_entry_cache, GFP_KERNEL);
-+      if (ce) {
-+              INIT_LIST_HEAD(&ce->e_lru_list);
-+              INIT_LIST_HEAD(&ce->e_block_list);
-+              ce->e_cache = cache;
-+              atomic_set(&ce->e_used, 1);
-+      }
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_insert()
-+ *
-+ * Inserts an entry that was allocated using mb_cache_entry_alloc() into
-+ * the cache. After this, the cache entry can be looked up, but is not yet
-+ * in the lru list as the caller still holds a handle to it. Returns 0 on
-+ * success, or -EBUSY if a cache entry for that device + inode exists
-+ * already (this may happen after a failed lookup, if another process has
-+ * inserted the same cache entry in the meantime).
-+ *
-+ * @dev: device the cache entry belongs to
-+ * @block: block number
-+ * @keys: array of additional keys. There must be indexes_count entries
-+ *        in the array (as specified when creating the cache).
-+ */
-+int
-+mb_cache_entry_insert(struct mb_cache_entry *ce, kdev_t dev,
-+                    unsigned long block, unsigned int keys[])
-+{
-+      struct mb_cache *cache = ce->e_cache;
-+      unsigned int bucket = (HASHDEV(dev) + block) % cache->c_bucket_count;
-+      struct list_head *l;
-+      int error = -EBUSY, n;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &cache->c_block_hash[bucket]) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry, e_block_list);
-+              if (ce->e_dev == dev && ce->e_block == block)
-+                      goto out;
-+      }
-+      __mb_cache_entry_unhash(ce);
-+      ce->e_dev = dev;
-+      ce->e_block = block;
-+      list_add(&ce->e_block_list, &cache->c_block_hash[bucket]);
-+      for (n=0; n<mb_cache_indexes(cache); n++) {
-+              ce->e_indexes[n].o_key = keys[n];
-+              bucket = keys[n] % cache->c_bucket_count;
-+              list_add(&ce->e_indexes[n].o_list,
-+                       &cache->c_indexes_hash[n][bucket]);
-+      }
-+out:
-+      spin_unlock(&mb_cache_spinlock);
-+      return error;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_release()
-+ *
-+ * Release a handle to a cache entry. When the last handle to a cache entry
-+ * is released it is either freed (if it is invalid) or otherwise inserted
-+ * in to the lru list.
-+ */
-+void
-+mb_cache_entry_release(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      __mb_cache_entry_release_unlock(ce);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_takeout()
-+ *
-+ * Take a cache entry out of the cache, making it invalid. The entry can later
-+ * be re-inserted using mb_cache_entry_insert(), or released using
-+ * mb_cache_entry_release().
-+ */
-+void
-+mb_cache_entry_takeout(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      mb_assert(list_empty(&ce->e_lru_list));
-+      __mb_cache_entry_unhash(ce);
-+      spin_unlock(&mb_cache_spinlock);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_free()
-+ *
-+ * This is equivalent to the sequence mb_cache_entry_takeout() --
-+ * mb_cache_entry_release().
-+ */
-+void
-+mb_cache_entry_free(struct mb_cache_entry *ce)
-+{
-+      spin_lock(&mb_cache_spinlock);
-+      mb_assert(list_empty(&ce->e_lru_list));
-+      __mb_cache_entry_unhash(ce);
-+      __mb_cache_entry_release_unlock(ce);
-+}
-+
-+
-+/*
-+ * mb_cache_entry_dup()
-+ *
-+ * Duplicate a handle to a cache entry (does not duplicate the cache entry
-+ * itself). After the call, both the old and the new handle must be released.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_dup(struct mb_cache_entry *ce)
-+{
-+      atomic_inc(&ce->e_used);
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_get()
-+ *
-+ * Get a cache entry  by device / block number. (There can only be one entry
-+ * in the cache per device and block.) Returns NULL if no such cache entry
-+ * exists.
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_get(struct mb_cache *cache, kdev_t dev, unsigned long block)
-+{
-+      unsigned int bucket = (HASHDEV(dev) + block) % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      spin_lock(&mb_cache_spinlock);
-+      list_for_each(l, &cache->c_block_hash[bucket]) {
-+              ce = list_entry(l, struct mb_cache_entry, e_block_list);
-+              if (ce->e_dev == dev && ce->e_block == block) {
-+                      if (!list_empty(&ce->e_lru_list))
-+                              list_del_init(&ce->e_lru_list);
-+                      atomic_inc(&ce->e_used);
-+                      goto cleanup;
-+              }
-+      }
-+      ce = NULL;
-+
-+cleanup:
-+      spin_unlock(&mb_cache_spinlock);
-+      return ce;
-+}
-+
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+
-+static struct mb_cache_entry *
-+__mb_cache_entry_find(struct list_head *l, struct list_head *head,
-+                    int index, kdev_t dev, unsigned int key)
-+{
-+      while (l != head) {
-+              struct mb_cache_entry *ce =
-+                      list_entry(l, struct mb_cache_entry,
-+                                 e_indexes[index].o_list);
-+              if (ce->e_dev == dev && ce->e_indexes[index].o_key == key) {
-+                      if (!list_empty(&ce->e_lru_list))
-+                              list_del_init(&ce->e_lru_list);
-+                      atomic_inc(&ce->e_used);
-+                      return ce;
-+              }
-+              l = l->next;
-+      }
-+      return NULL;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_find_first()
-+ *
-+ * Find the first cache entry on a given device with a certain key in
-+ * an additional index. Additonal matches can be found with
-+ * mb_cache_entry_find_next(). Returns NULL if no match was found.
-+ *
-+ * @cache: the cache to search
-+ * @index: the number of the additonal index to search (0<=index<indexes_count)
-+ * @dev: the device the cache entry should belong to
-+ * @key: the key in the index
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_find_first(struct mb_cache *cache, int index, kdev_t dev,
-+                        unsigned int key)
-+{
-+      unsigned int bucket = key % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      mb_assert(index < mb_cache_indexes(cache));
-+      spin_lock(&mb_cache_spinlock);
-+      l = cache->c_indexes_hash[index][bucket].next;
-+      ce = __mb_cache_entry_find(l, &cache->c_indexes_hash[index][bucket],
-+                                 index, dev, key);
-+      spin_unlock(&mb_cache_spinlock);
-+      return ce;
-+}
-+
-+
-+/*
-+ * mb_cache_entry_find_next()
-+ *
-+ * Find the next cache entry on a given device with a certain key in an
-+ * additional index. Returns NULL if no match could be found. The previous
-+ * entry is atomatically released, so that mb_cache_entry_find_next() can
-+ * be called like this:
-+ *
-+ * entry = mb_cache_entry_find_first();
-+ * while (entry) {
-+ *    ...
-+ *    entry = mb_cache_entry_find_next(entry, ...);
-+ * }
-+ *
-+ * @prev: The previous match
-+ * @index: the number of the additonal index to search (0<=index<indexes_count)
-+ * @dev: the device the cache entry should belong to
-+ * @key: the key in the index
-+ */
-+struct mb_cache_entry *
-+mb_cache_entry_find_next(struct mb_cache_entry *prev, int index, kdev_t dev,
-+                       unsigned int key)
-+{
-+      struct mb_cache *cache = prev->e_cache;
-+      unsigned int bucket = key % cache->c_bucket_count;
-+      struct list_head *l;
-+      struct mb_cache_entry *ce;
-+
-+      mb_assert(index < mb_cache_indexes(cache));
-+      spin_lock(&mb_cache_spinlock);
-+      l = prev->e_indexes[index].o_list.next;
-+      ce = __mb_cache_entry_find(l, &cache->c_indexes_hash[index][bucket],
-+                                 index, dev, key);
-+      __mb_cache_entry_release_unlock(prev);
-+      return ce;
-+}
-+
-+#endif  /* !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0) */
-+
-+static int __init init_mbcache(void)
-+{
-+      register_cache(&mb_cache_definition);
-+      return 0;
-+}
-+
-+static void __exit exit_mbcache(void)
-+{
-+      unregister_cache(&mb_cache_definition);
-+}
-+
-+module_init(init_mbcache)
-+module_exit(exit_mbcache)
-+
---- linux-2.4.22-ac1/include/asm-arm/unistd.h~xattr-0.8.54-2.4.22-rh   2003-08-25 15:44:43.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/asm-arm/unistd.h   2003-09-25 23:57:02.000000000 +0400
-@@ -250,7 +250,6 @@
- #define __NR_security                 (__NR_SYSCALL_BASE+223)
- #define __NR_gettid                   (__NR_SYSCALL_BASE+224)
- #define __NR_readahead                        (__NR_SYSCALL_BASE+225)
--#if 0 /* allocated in 2.5 */
- #define __NR_setxattr                 (__NR_SYSCALL_BASE+226)
- #define __NR_lsetxattr                        (__NR_SYSCALL_BASE+227)
- #define __NR_fsetxattr                        (__NR_SYSCALL_BASE+228)
-@@ -263,7 +262,6 @@
- #define __NR_removexattr              (__NR_SYSCALL_BASE+235)
- #define __NR_lremovexattr             (__NR_SYSCALL_BASE+236)
- #define __NR_fremovexattr             (__NR_SYSCALL_BASE+237)
--#endif
- #define __NR_tkill                    (__NR_SYSCALL_BASE+238)
- #if 0 /* allocated in 2.5 */
- #define __NR_sendfile64                 (__NR_SYSCALL_BASE+239)
---- linux-2.4.22-ac1/include/asm-ppc64/unistd.h~xattr-0.8.54-2.4.22-rh 2003-06-13 18:51:38.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/asm-ppc64/unistd.h 2003-09-25 23:57:02.000000000 +0400
-@@ -218,6 +218,7 @@
- #define __NR_mincore          206
- #define __NR_gettid           207
- #define __NR_tkill            208
-+#endif
- #define __NR_setxattr         209
- #define __NR_lsetxattr                210
- #define __NR_fsetxattr                211
-@@ -230,6 +231,7 @@
- #define __NR_removexattr      218
- #define __NR_lremovexattr     219
- #define __NR_fremovexattr     220
-+#if 0 /* Reserved syscalls */
- #define __NR_futex            221
- #define __NR_sched_setaffinity        222     
- #define __NR_sched_getaffinity        223
---- linux-2.4.22-ac1/include/asm-s390/unistd.h~xattr-0.8.54-2.4.22-rh  2003-06-13 18:51:38.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/asm-s390/unistd.h  2003-09-26 00:14:23.000000000 +0400
-@@ -213,6 +213,19 @@
- #define __NR_getdents64               220
- #define __NR_fcntl64          221
- #define __NR_readahead                222
-+#define __NR_setxattr         224
-+#define __NR_lsetxattr                225
-+#define __NR_fsetxattr                226
-+#define __NR_getxattr         227
-+#define __NR_lgetxattr                228
-+#define __NR_fgetxattr                229
-+#define __NR_listxattr                230
-+#define __NR_llistxattr               231
-+#define __NR_flistxattr               232
-+#define __NR_removexattr      233
-+#define __NR_lremovexattr     234
-+#define __NR_fremovexattr     235
-+
- /*
-  * Numbers 224-235 are reserved for posix acl
-  */
---- linux-2.4.22-ac1/include/asm-s390x/unistd.h~xattr-0.8.54-2.4.22-rh 2003-06-13 18:51:38.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/asm-s390x/unistd.h 2003-09-26 00:15:11.000000000 +0400
-@@ -181,6 +181,19 @@
- #define __NR_mincore            218
- #define __NR_madvise            219
- #define __NR_readahead                222
-+#define __NR_setxattr         224
-+#define __NR_lsetxattr                225
-+#define __NR_fsetxattr                226
-+#define __NR_getxattr         227
-+#define __NR_lgetxattr                228
-+#define __NR_fgetxattr                229
-+#define __NR_listxattr                230
-+#define __NR_llistxattr               231
-+#define __NR_flistxattr               232
-+#define __NR_removexattr      233
-+#define __NR_lremovexattr     234
-+#define __NR_fremovexattr     235
-+
- /*
-  * Numbers 224-235 are reserved for posix acl
-  */
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/include/linux/cache_def.h  2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,15 @@
-+/*
-+ * linux/cache_def.h
-+ * Handling of caches defined in drivers, filesystems, ...
-+ *
-+ * Copyright (C) 2002 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+ */
-+
-+struct cache_definition {
-+      const char *name;
-+      void (*shrink)(int, unsigned int);
-+      struct list_head link;
-+};
-+
-+extern void register_cache(struct cache_definition *);
-+extern void unregister_cache(struct cache_definition *);
---- linux-2.4.22-ac1/include/linux/errno.h~xattr-0.8.54-2.4.22-rh      2001-02-10 01:46:13.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/include/linux/errno.h      2003-09-25 23:57:02.000000000 +0400
-@@ -23,4 +23,8 @@
- #endif
-+/* Defined for extended attributes */
-+#define ENOATTR ENODATA               /* No such attribute */
-+#define ENOTSUP EOPNOTSUPP    /* Operation not supported */
-+
- #endif
---- linux-2.4.22-ac1/include/linux/ext2_fs.h~xattr-0.8.54-2.4.22-rh    2003-06-13 18:51:38.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/ext2_fs.h    2003-09-25 23:57:02.000000000 +0400
-@@ -57,8 +57,6 @@
-  */
- #define       EXT2_BAD_INO             1      /* Bad blocks inode */
- #define EXT2_ROOT_INO          2      /* Root inode */
--#define EXT2_ACL_IDX_INO       3      /* ACL inode */
--#define EXT2_ACL_DATA_INO      4      /* ACL inode */
- #define EXT2_BOOT_LOADER_INO   5      /* Boot loader inode */
- #define EXT2_UNDEL_DIR_INO     6      /* Undelete directory inode */
-@@ -86,7 +84,6 @@
- #else
- # define EXT2_BLOCK_SIZE(s)           (EXT2_MIN_BLOCK_SIZE << (s)->s_log_block_size)
- #endif
--#define EXT2_ACLE_PER_BLOCK(s)                (EXT2_BLOCK_SIZE(s) / sizeof (struct ext2_acl_entry))
- #define       EXT2_ADDR_PER_BLOCK(s)          (EXT2_BLOCK_SIZE(s) / sizeof (__u32))
- #ifdef __KERNEL__
- # define EXT2_BLOCK_SIZE_BITS(s)      ((s)->s_blocksize_bits)
-@@ -121,28 +118,6 @@
- #endif
- /*
-- * ACL structures
-- */
--struct ext2_acl_header        /* Header of Access Control Lists */
--{
--      __u32   aclh_size;
--      __u32   aclh_file_count;
--      __u32   aclh_acle_count;
--      __u32   aclh_first_acle;
--};
--
--struct ext2_acl_entry /* Access Control List Entry */
--{
--      __u32   acle_size;
--      __u16   acle_perms;     /* Access permissions */
--      __u16   acle_type;      /* Type of entry */
--      __u16   acle_tag;       /* User or group identity */
--      __u16   acle_pad1;
--      __u32   acle_next;      /* Pointer on next entry for the */
--                                      /* same inode or on next free entry */
--};
--
--/*
-  * Structure of a blocks group descriptor
-  */
- struct ext2_group_desc
-@@ -314,6 +289,7 @@ struct ext2_inode {
- #define EXT2_MOUNT_ERRORS_PANIC               0x0040  /* Panic on errors */
- #define EXT2_MOUNT_MINIX_DF           0x0080  /* Mimics the Minix statfs */
- #define EXT2_MOUNT_NO_UID32           0x0200  /* Disable 32-bit UIDs */
-+#define EXT2_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
- #define clear_opt(o, opt)             o &= ~EXT2_MOUNT_##opt
- #define set_opt(o, opt)                       o |= EXT2_MOUNT_##opt
-@@ -397,6 +373,7 @@ struct ext2_super_block {
- #ifdef __KERNEL__
- #define EXT2_SB(sb)   (&((sb)->u.ext2_sb))
-+#define EXT2_I(inode) (&((inode)->u.ext2_i))
- #else
- /* Assume that user mode programs are passing in an ext2fs superblock, not
-  * a kernel struct super_block.  This will allow us to call the feature-test
-@@ -466,7 +443,7 @@ struct ext2_super_block {
- #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008
- #define EXT2_FEATURE_INCOMPAT_ANY             0xffffffff
--#define EXT2_FEATURE_COMPAT_SUPP      0
-+#define EXT2_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
- #define EXT2_FEATURE_INCOMPAT_SUPP    EXT2_FEATURE_INCOMPAT_FILETYPE
- #define EXT2_FEATURE_RO_COMPAT_SUPP   (EXT2_FEATURE_RO_COMPAT_SPARSE_SUPER| \
-                                        EXT2_FEATURE_RO_COMPAT_LARGE_FILE| \
-@@ -624,8 +601,10 @@ extern struct address_space_operations e
- /* namei.c */
- extern struct inode_operations ext2_dir_inode_operations;
-+extern struct inode_operations ext2_special_inode_operations;
- /* symlink.c */
-+extern struct inode_operations ext2_symlink_inode_operations;
- extern struct inode_operations ext2_fast_symlink_inode_operations;
- #endif        /* __KERNEL__ */
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/include/linux/ext2_xattr.h 2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,157 @@
-+/*
-+  File: linux/ext2_xattr.h
-+
-+  On-disk format of extended attributes for the ext2 filesystem.
-+
-+  (C) 2001 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+#include <linux/config.h>
-+#include <linux/init.h>
-+#include <linux/xattr.h>
-+
-+/* Magic value in attribute blocks */
-+#define EXT2_XATTR_MAGIC              0xEA020000
-+
-+/* Maximum number of references to one attribute block */
-+#define EXT2_XATTR_REFCOUNT_MAX               1024
-+
-+/* Name indexes */
-+#define EXT2_XATTR_INDEX_MAX                  10
-+#define EXT2_XATTR_INDEX_USER                 1
-+#define EXT2_XATTR_INDEX_POSIX_ACL_ACCESS     2
-+#define EXT2_XATTR_INDEX_POSIX_ACL_DEFAULT    3
-+
-+struct ext2_xattr_header {
-+      __u32   h_magic;        /* magic number for identification */
-+      __u32   h_refcount;     /* reference count */
-+      __u32   h_blocks;       /* number of disk blocks used */
-+      __u32   h_hash;         /* hash value of all attributes */
-+      __u32   h_reserved[4];  /* zero right now */
-+};
-+
-+struct ext2_xattr_entry {
-+      __u8    e_name_len;     /* length of name */
-+      __u8    e_name_index;   /* attribute name index */
-+      __u16   e_value_offs;   /* offset in disk block of value */
-+      __u32   e_value_block;  /* disk block attribute is stored on (n/i) */
-+      __u32   e_value_size;   /* size of attribute value */
-+      __u32   e_hash;         /* hash value of name and value */
-+      char    e_name[0];      /* attribute name */
-+};
-+
-+#define EXT2_XATTR_PAD_BITS           2
-+#define EXT2_XATTR_PAD                (1<<EXT2_XATTR_PAD_BITS)
-+#define EXT2_XATTR_ROUND              (EXT2_XATTR_PAD-1)
-+#define EXT2_XATTR_LEN(name_len) \
-+      (((name_len) + EXT2_XATTR_ROUND + \
-+      sizeof(struct ext2_xattr_entry)) & ~EXT2_XATTR_ROUND)
-+#define EXT2_XATTR_NEXT(entry) \
-+      ( (struct ext2_xattr_entry *)( \
-+        (char *)(entry) + EXT2_XATTR_LEN((entry)->e_name_len)) )
-+#define EXT2_XATTR_SIZE(size) \
-+      (((size) + EXT2_XATTR_ROUND) & ~EXT2_XATTR_ROUND)
-+
-+#ifdef __KERNEL__
-+
-+# ifdef CONFIG_EXT2_FS_XATTR
-+
-+struct ext2_xattr_handler {
-+      char *prefix;
-+      size_t (*list)(char *list, struct inode *inode, const char *name,
-+                     int name_len);
-+      int (*get)(struct inode *inode, const char *name, void *buffer,
-+                 size_t size);
-+      int (*set)(struct inode *inode, const char *name, const void *buffer,
-+                 size_t size, int flags);
-+};
-+
-+extern int ext2_xattr_register(int, struct ext2_xattr_handler *);
-+extern void ext2_xattr_unregister(int, struct ext2_xattr_handler *);
-+
-+extern int ext2_setxattr(struct dentry *, const char *, const void *, size_t, int);
-+extern ssize_t ext2_getxattr(struct dentry *, const char *, void *, size_t);
-+extern ssize_t ext2_listxattr(struct dentry *, char *, size_t);
-+extern int ext2_removexattr(struct dentry *, const char *);
-+
-+extern int ext2_xattr_get(struct inode *, int, const char *, void *, size_t);
-+extern int ext2_xattr_list(struct inode *, char *, size_t);
-+extern int ext2_xattr_set(struct inode *, int, const char *, const void *, size_t, int);
-+
-+extern void ext2_xattr_delete_inode(struct inode *);
-+extern void ext2_xattr_put_super(struct super_block *);
-+
-+extern int init_ext2_xattr(void) __init;
-+extern void exit_ext2_xattr(void);
-+
-+# else  /* CONFIG_EXT2_FS_XATTR */
-+#  define ext2_setxattr               NULL
-+#  define ext2_getxattr               NULL
-+#  define ext2_listxattr      NULL
-+#  define ext2_removexattr    NULL
-+
-+static inline int
-+ext2_xattr_get(struct inode *inode, int name_index,
-+             const char *name, void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext2_xattr_list(struct inode *inode, char *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext2_xattr_set(struct inode *inode, int name_index, const char *name,
-+             const void *value, size_t size, int flags)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline void
-+ext2_xattr_delete_inode(struct inode *inode)
-+{
-+}
-+
-+static inline void
-+ext2_xattr_put_super(struct super_block *sb)
-+{
-+}
-+
-+static inline int
-+init_ext2_xattr(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext2_xattr(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT2_FS_XATTR */
-+
-+# ifdef CONFIG_EXT2_FS_XATTR_USER
-+
-+extern int init_ext2_xattr_user(void) __init;
-+extern void exit_ext2_xattr_user(void);
-+
-+# else  /* CONFIG_EXT2_FS_XATTR_USER */
-+
-+static inline int
-+init_ext2_xattr_user(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext2_xattr_user(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT2_FS_XATTR_USER */
-+
-+#endif  /* __KERNEL__ */
-+
---- linux-2.4.22-ac1/include/linux/ext3_fs.h~xattr-0.8.54-2.4.22-rh    2003-09-25 14:58:30.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/ext3_fs.h    2003-09-25 23:57:02.000000000 +0400
-@@ -63,8 +63,6 @@
-  */
- #define       EXT3_BAD_INO             1      /* Bad blocks inode */
- #define EXT3_ROOT_INO          2      /* Root inode */
--#define EXT3_ACL_IDX_INO       3      /* ACL inode */
--#define EXT3_ACL_DATA_INO      4      /* ACL inode */
- #define EXT3_BOOT_LOADER_INO   5      /* Boot loader inode */
- #define EXT3_UNDEL_DIR_INO     6      /* Undelete directory inode */
- #define EXT3_RESIZE_INO                7      /* Reserved group descriptors inode */
-@@ -94,7 +92,6 @@
- #else
- # define EXT3_BLOCK_SIZE(s)           (EXT3_MIN_BLOCK_SIZE << (s)->s_log_block_size)
- #endif
--#define EXT3_ACLE_PER_BLOCK(s)                (EXT3_BLOCK_SIZE(s) / sizeof (struct ext3_acl_entry))
- #define       EXT3_ADDR_PER_BLOCK(s)          (EXT3_BLOCK_SIZE(s) / sizeof (__u32))
- #ifdef __KERNEL__
- # define EXT3_BLOCK_SIZE_BITS(s)      ((s)->s_blocksize_bits)
-@@ -129,28 +126,6 @@
- #endif
- /*
-- * ACL structures
-- */
--struct ext3_acl_header        /* Header of Access Control Lists */
--{
--      __u32   aclh_size;
--      __u32   aclh_file_count;
--      __u32   aclh_acle_count;
--      __u32   aclh_first_acle;
--};
--
--struct ext3_acl_entry /* Access Control List Entry */
--{
--      __u32   acle_size;
--      __u16   acle_perms;     /* Access permissions */
--      __u16   acle_type;      /* Type of entry */
--      __u16   acle_tag;       /* User or group identity */
--      __u16   acle_pad1;
--      __u32   acle_next;      /* Pointer on next entry for the */
--                                      /* same inode or on next free entry */
--};
--
--/*
-  * Structure of a blocks group descriptor
-  */
- struct ext3_group_desc
-@@ -346,6 +321,7 @@ struct ext3_inode {
-   #define EXT3_MOUNT_WRITEBACK_DATA   0x0C00  /* No data ordering */
- #define EXT3_MOUNT_UPDATE_JOURNAL     0x1000  /* Update the journal format */
- #define EXT3_MOUNT_NO_UID32           0x2000  /* Disable 32-bit UIDs */
-+#define EXT3_MOUNT_XATTR_USER         0x4000  /* Extended user attributes */
- /* Compatibility, for having both ext2_fs.h and ext3_fs.h included at once */
- #ifndef _LINUX_EXT2_FS_H
-@@ -523,7 +499,7 @@ struct ext3_super_block {
- #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
- #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
--#define EXT3_FEATURE_COMPAT_SUPP      0
-+#define EXT3_FEATURE_COMPAT_SUPP      EXT2_FEATURE_COMPAT_EXT_ATTR
- #define EXT3_FEATURE_INCOMPAT_SUPP    (EXT3_FEATURE_INCOMPAT_FILETYPE| \
-                                        EXT3_FEATURE_INCOMPAT_RECOVER)
- #define EXT3_FEATURE_RO_COMPAT_SUPP   (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
-@@ -707,6 +683,7 @@ extern void ext3_check_inodes_bitmap (st
- extern unsigned long ext3_count_free (struct buffer_head *, unsigned);
- /* inode.c */
-+extern int ext3_forget(handle_t *, int, struct inode *, struct buffer_head *, int);
- extern struct buffer_head * ext3_getblk (handle_t *, struct inode *, long, int, int *);
- extern struct buffer_head * ext3_bread (handle_t *, struct inode *, int, int, int *);
-@@ -776,8 +753,10 @@ extern struct address_space_operations e
- /* namei.c */
- extern struct inode_operations ext3_dir_inode_operations;
-+extern struct inode_operations ext3_special_inode_operations;
- /* symlink.c */
-+extern struct inode_operations ext3_symlink_inode_operations;
- extern struct inode_operations ext3_fast_symlink_inode_operations;
---- linux-2.4.22-ac1/include/linux/ext3_jbd.h~xattr-0.8.54-2.4.22-rh   2003-09-25 14:55:12.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/ext3_jbd.h   2003-09-25 23:57:02.000000000 +0400
-@@ -30,13 +30,19 @@
- #define EXT3_SINGLEDATA_TRANS_BLOCKS  8U
-+/* Extended attributes may touch two data buffers, two bitmap buffers,
-+ * and two group and summaries. */
-+
-+#define EXT3_XATTR_TRANS_BLOCKS               8
-+
- /* Define the minimum size for a transaction which modifies data.  This
-  * needs to take into account the fact that we may end up modifying two
-  * quota files too (one for the group, one for the user quota).  The
-  * superblock only gets updated once, of course, so don't bother
-  * counting that again for the quota updates. */
--#define EXT3_DATA_TRANS_BLOCKS                (3 * EXT3_SINGLEDATA_TRANS_BLOCKS - 2)
-+#define EXT3_DATA_TRANS_BLOCKS                (3 * EXT3_SINGLEDATA_TRANS_BLOCKS + \
-+                                       EXT3_XATTR_TRANS_BLOCKS - 2)
- extern int ext3_writepage_trans_blocks(struct inode *inode);
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/include/linux/ext3_xattr.h 2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,157 @@
-+/*
-+  File: linux/ext3_xattr.h
-+
-+  On-disk format of extended attributes for the ext3 filesystem.
-+
-+  (C) 2001 Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+#include <linux/config.h>
-+#include <linux/init.h>
-+#include <linux/xattr.h>
-+
-+/* Magic value in attribute blocks */
-+#define EXT3_XATTR_MAGIC              0xEA020000
-+
-+/* Maximum number of references to one attribute block */
-+#define EXT3_XATTR_REFCOUNT_MAX               1024
-+
-+/* Name indexes */
-+#define EXT3_XATTR_INDEX_MAX                  10
-+#define EXT3_XATTR_INDEX_USER                 1
-+#define EXT3_XATTR_INDEX_POSIX_ACL_ACCESS     2
-+#define EXT3_XATTR_INDEX_POSIX_ACL_DEFAULT    3
-+
-+struct ext3_xattr_header {
-+      __u32   h_magic;        /* magic number for identification */
-+      __u32   h_refcount;     /* reference count */
-+      __u32   h_blocks;       /* number of disk blocks used */
-+      __u32   h_hash;         /* hash value of all attributes */
-+      __u32   h_reserved[4];  /* zero right now */
-+};
-+
-+struct ext3_xattr_entry {
-+      __u8    e_name_len;     /* length of name */
-+      __u8    e_name_index;   /* attribute name index */
-+      __u16   e_value_offs;   /* offset in disk block of value */
-+      __u32   e_value_block;  /* disk block attribute is stored on (n/i) */
-+      __u32   e_value_size;   /* size of attribute value */
-+      __u32   e_hash;         /* hash value of name and value */
-+      char    e_name[0];      /* attribute name */
-+};
-+
-+#define EXT3_XATTR_PAD_BITS           2
-+#define EXT3_XATTR_PAD                (1<<EXT3_XATTR_PAD_BITS)
-+#define EXT3_XATTR_ROUND              (EXT3_XATTR_PAD-1)
-+#define EXT3_XATTR_LEN(name_len) \
-+      (((name_len) + EXT3_XATTR_ROUND + \
-+      sizeof(struct ext3_xattr_entry)) & ~EXT3_XATTR_ROUND)
-+#define EXT3_XATTR_NEXT(entry) \
-+      ( (struct ext3_xattr_entry *)( \
-+        (char *)(entry) + EXT3_XATTR_LEN((entry)->e_name_len)) )
-+#define EXT3_XATTR_SIZE(size) \
-+      (((size) + EXT3_XATTR_ROUND) & ~EXT3_XATTR_ROUND)
-+
-+#ifdef __KERNEL__
-+
-+# ifdef CONFIG_EXT3_FS_XATTR
-+
-+struct ext3_xattr_handler {
-+      char *prefix;
-+      size_t (*list)(char *list, struct inode *inode, const char *name,
-+                     int name_len);
-+      int (*get)(struct inode *inode, const char *name, void *buffer,
-+                 size_t size);
-+      int (*set)(struct inode *inode, const char *name, const void *buffer,
-+                 size_t size, int flags);
-+};
-+
-+extern int ext3_xattr_register(int, struct ext3_xattr_handler *);
-+extern void ext3_xattr_unregister(int, struct ext3_xattr_handler *);
-+
-+extern int ext3_setxattr(struct dentry *, const char *, const void *, size_t, int);
-+extern ssize_t ext3_getxattr(struct dentry *, const char *, void *, size_t);
-+extern ssize_t ext3_listxattr(struct dentry *, char *, size_t);
-+extern int ext3_removexattr(struct dentry *, const char *);
-+
-+extern int ext3_xattr_get(struct inode *, int, const char *, void *, size_t);
-+extern int ext3_xattr_list(struct inode *, char *, size_t);
-+extern int ext3_xattr_set(handle_t *handle, struct inode *, int, const char *, const void *, size_t, int);
-+
-+extern void ext3_xattr_delete_inode(handle_t *, struct inode *);
-+extern void ext3_xattr_put_super(struct super_block *);
-+
-+extern int init_ext3_xattr(void) __init;
-+extern void exit_ext3_xattr(void);
-+
-+# else  /* CONFIG_EXT3_FS_XATTR */
-+#  define ext3_setxattr               NULL
-+#  define ext3_getxattr               NULL
-+#  define ext3_listxattr      NULL
-+#  define ext3_removexattr    NULL
-+
-+static inline int
-+ext3_xattr_get(struct inode *inode, int name_index, const char *name,
-+             void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext3_xattr_list(struct inode *inode, void *buffer, size_t size)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline int
-+ext3_xattr_set(handle_t *handle, struct inode *inode, int name_index,
-+             const char *name, const void *value, size_t size, int flags)
-+{
-+      return -ENOTSUP;
-+}
-+
-+static inline void
-+ext3_xattr_delete_inode(handle_t *handle, struct inode *inode)
-+{
-+}
-+
-+static inline void
-+ext3_xattr_put_super(struct super_block *sb)
-+{
-+}
-+
-+static inline int
-+init_ext3_xattr(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext3_xattr(void)
-+{
-+}
-+
-+# endif  /* CONFIG_EXT3_FS_XATTR */
-+
-+# ifdef CONFIG_EXT3_FS_XATTR_USER
-+
-+extern int init_ext3_xattr_user(void) __init;
-+extern void exit_ext3_xattr_user(void);
-+
-+# else  /* CONFIG_EXT3_FS_XATTR_USER */
-+
-+static inline int
-+init_ext3_xattr_user(void)
-+{
-+      return 0;
-+}
-+
-+static inline void
-+exit_ext3_xattr_user(void)
-+{
-+}
-+
-+#endif  /* CONFIG_EXT3_FS_XATTR_USER */
-+
-+#endif  /* __KERNEL__ */
-+
---- linux-2.4.22-ac1/include/linux/fs.h~xattr-0.8.54-2.4.22-rh 2003-09-25 14:45:32.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/include/linux/fs.h 2003-09-25 23:57:02.000000000 +0400
-@@ -918,7 +918,7 @@ struct inode_operations {
-       int (*setattr) (struct dentry *, struct iattr *);
-       int (*setattr_raw) (struct inode *, struct iattr *);
-       int (*getattr) (struct dentry *, struct iattr *);
--      int (*setxattr) (struct dentry *, const char *, void *, size_t, int);
-+      int (*setxattr) (struct dentry *, const char *, const void *, size_t, int);
-       ssize_t (*getxattr) (struct dentry *, const char *, void *, size_t);
-       ssize_t (*listxattr) (struct dentry *, char *, size_t);
-       int (*removexattr) (struct dentry *, const char *);
---- /dev/null  2003-01-30 13:24:37.000000000 +0300
-+++ linux-2.4.22-ac1-alexey/include/linux/mbcache.h    2003-09-25 23:57:02.000000000 +0400
-@@ -0,0 +1,69 @@
-+/*
-+  File: linux/mbcache.h
-+
-+  (C) 2001 by Andreas Gruenbacher, <a.gruenbacher@computer.org>
-+*/
-+
-+/* Hardwire the number of additional indexes */
-+#define MB_CACHE_INDEXES_COUNT 1
-+
-+struct mb_cache_entry;
-+
-+struct mb_cache_op {
-+      int (*free)(struct mb_cache_entry *, int);
-+};
-+
-+struct mb_cache {
-+      struct list_head                c_cache_list;
-+      const char                      *c_name;
-+      struct mb_cache_op              c_op;
-+      atomic_t                        c_entry_count;
-+      int                             c_bucket_count;
-+#ifndef MB_CACHE_INDEXES_COUNT
-+      int                             c_indexes_count;
-+#endif
-+      kmem_cache_t                    *c_entry_cache;
-+      struct list_head                *c_block_hash;
-+      struct list_head                *c_indexes_hash[0];
-+};
-+
-+struct mb_cache_entry_index {
-+      struct list_head                o_list;
-+      unsigned int                    o_key;
-+};
-+
-+struct mb_cache_entry {
-+      struct list_head                e_lru_list;
-+      struct mb_cache                 *e_cache;
-+      atomic_t                        e_used;
-+      kdev_t                          e_dev;
-+      unsigned long                   e_block;
-+      struct list_head                e_block_list;
-+      struct mb_cache_entry_index     e_indexes[0];
-+};
-+
-+/* Functions on caches */
-+
-+struct mb_cache * mb_cache_create(const char *, struct mb_cache_op *, size_t,
-+                                int, int);
-+void mb_cache_shrink(struct mb_cache *, kdev_t);
-+void mb_cache_destroy(struct mb_cache *);
-+
-+/* Functions on cache entries */
-+
-+struct mb_cache_entry *mb_cache_entry_alloc(struct mb_cache *);
-+int mb_cache_entry_insert(struct mb_cache_entry *, kdev_t, unsigned long,
-+                        unsigned int[]);
-+void mb_cache_entry_rehash(struct mb_cache_entry *, unsigned int[]);
-+void mb_cache_entry_release(struct mb_cache_entry *);
-+void mb_cache_entry_takeout(struct mb_cache_entry *);
-+void mb_cache_entry_free(struct mb_cache_entry *);
-+struct mb_cache_entry *mb_cache_entry_dup(struct mb_cache_entry *);
-+struct mb_cache_entry *mb_cache_entry_get(struct mb_cache *, kdev_t,
-+                                        unsigned long);
-+#if !defined(MB_CACHE_INDEXES_COUNT) || (MB_CACHE_INDEXES_COUNT > 0)
-+struct mb_cache_entry *mb_cache_entry_find_first(struct mb_cache *cache, int,
-+                                               kdev_t, unsigned int);
-+struct mb_cache_entry *mb_cache_entry_find_next(struct mb_cache_entry *, int,
-+                                              kdev_t, unsigned int);
-+#endif
---- linux-2.4.22-ac1/kernel/ksyms.c~xattr-0.8.54-2.4.22-rh     2003-09-25 14:42:46.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/kernel/ksyms.c     2003-09-26 00:19:05.000000000 +0400
-@@ -11,6 +11,7 @@
- #include <linux/config.h>
- #include <linux/slab.h>
-+#include <linux/cache_def.h>
- #include <linux/smp.h>
- #include <linux/module.h>
- #include <linux/blkdev.h>
-@@ -106,6 +107,7 @@ EXPORT_SYMBOL(exit_files);
- EXPORT_SYMBOL(exit_fs);
- EXPORT_SYMBOL(exit_sighand);
- EXPORT_SYMBOL(unshare_files);
-+EXPORT_SYMBOL(copy_fs_struct);
- /* internal kernel memory management */
- EXPORT_SYMBOL(_alloc_pages);
-@@ -124,6 +126,8 @@ EXPORT_SYMBOL(kmem_cache_validate);
- EXPORT_SYMBOL(kmem_cache_alloc);
- EXPORT_SYMBOL(kmem_cache_free);
- EXPORT_SYMBOL(kmem_cache_size);
-+EXPORT_SYMBOL(register_cache);
-+EXPORT_SYMBOL(unregister_cache);
- EXPORT_SYMBOL(kmalloc);
- EXPORT_SYMBOL(kfree);
- EXPORT_SYMBOL(vfree);
---- linux-2.4.22-ac1/mm/vmscan.c~xattr-0.8.54-2.4.22-rh        2003-09-25 14:16:28.000000000 +0400
-+++ linux-2.4.22-ac1-alexey/mm/vmscan.c        2003-09-25 23:57:02.000000000 +0400
-@@ -18,6 +18,7 @@
- #include <linux/kernel_stat.h>
- #include <linux/swap.h>
- #include <linux/swapctl.h>
-+#include <linux/cache_def.h>
- #include <linux/smp_lock.h>
- #include <linux/pagemap.h>
- #include <linux/init.h>
-@@ -34,6 +35,39 @@
-  */
- #define DEF_PRIORITY (6)
-+static DECLARE_MUTEX(other_caches_sem);
-+static LIST_HEAD(cache_definitions);
-+
-+void register_cache(struct cache_definition *cache)
-+{
-+      down(&other_caches_sem);
-+      list_add(&cache->link, &cache_definitions);
-+      up(&other_caches_sem);
-+}
-+
-+void unregister_cache(struct cache_definition *cache)
-+{
-+      down(&other_caches_sem);
-+      list_del(&cache->link);
-+      up(&other_caches_sem);
-+}
-+
-+static void shrink_other_caches(unsigned int priority, int gfp_mask)
-+{
-+      struct list_head *p;
-+
-+      if (down_trylock(&other_caches_sem))
-+              return;
-+
-+      list_for_each_prev(p, &cache_definitions) {
-+              struct cache_definition *cache =
-+                      list_entry(p, struct cache_definition, link);
-+
-+              cache->shrink(priority, gfp_mask);
-+      }
-+      up(&other_caches_sem);
-+}
-+
- /*
-  * The swap-out function returns 1 if it successfully
-  * scanned all the pages it was asked to (`count').
-@@ -577,6 +611,7 @@ static int shrink_caches(zone_t * classz
-       shrink_dcache_memory(priority, gfp_mask);
-       shrink_icache_memory(priority, gfp_mask);
-+      shrink_other_caches(priority, gfp_mask);
- #ifdef CONFIG_QUOTA
-       shrink_dqcache_memory(DEF_PRIORITY, gfp_mask);
- #endif
-
-_
index 7c0ae18..46487e1 100644 (file)
@@ -13,3 +13,4 @@ lookup_bdev_init_intent.patch
 8kstack-2.6-rhel4.patch
 remove-suid-2.6-suse.patch
 export-show_task-2.6-vanilla.patch
+sd_iostats-2.6-rhel4.patch 
index aba1070..e60eebd 100644 (file)
@@ -1,3 +1,4 @@
+dev_read_only-2.6-lnxi.patch
 sd_iostats-2.6-suse.patch
 blkdev_tunables-2.6-suse.patch
 bluesmoke-2.6-suse-lnxi.patch 
diff --git a/lustre/kernel_patches/series/2.6-vanilla.series b/lustre/kernel_patches/series/2.6-vanilla.series
deleted file mode 100644 (file)
index 7fa0d34..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-uml-2.6.7-01-bb2.patch
-lustre_version.patch
-vfs_intent-2.6-vanilla.patch
-vfs_nointent-2.6-vanilla.patch
-vfs_races-2.6-vanilla.patch
-ext3-wantedi-misc-2.6-suse.patch 
-nfs-cifs-intent-2.6-vanilla.patch 
-iopen-misc-2.6-suse.patch 
-export-truncate-2.6-suse.patch 
-export_symbols-2.6-suse.patch 
-dev_read_only-2.6-suse.patch 
-export-2.6-suse.patch
-header-guards-2.6-suse.patch
-lookup_bdev_init_intent.patch
-ext3-super-ntohl.patch
index 033119a..d846b4d 100644 (file)
@@ -1,5 +1,5 @@
 configurable-x86-stack-2.4.20.patch
-dev_read_only_hp_2.4.20.patch
+dev_read_only_2.4.20-rh.patch
 exports_2.4.20-rh-hp.patch
 lustre_version.patch
 vfs_intent-2.4.20-hp.patch 
@@ -45,6 +45,5 @@ inode-max-readahead-2.4.24.patch
 dcache_refcount_debug.patch
 ext3-extents-2.4.24.patch
 ext3-extents-asyncdel-2.4.24.patch
-ext3-mballoc-2.4.24.patch
 ext3-nlinks-2.4.20-hp_pnnl.patch 
 export-zap-page-range.patch
diff --git a/lustre/kernel_patches/series/ldiskfs-2.6-vanilla.series b/lustre/kernel_patches/series/ldiskfs-2.6-vanilla.series
deleted file mode 100644 (file)
index 13cf85a..0000000
+++ /dev/null
@@ -1,11 +0,0 @@
-ext3-wantedi-2.6-suse.patch
-ext3-san-jdike-2.6-suse.patch
-iopen-2.6-vanilla.patch 
-export_symbols-ext3-2.6-suse.patch
-ext3-map_inode_page-2.6-suse.patch
-ext3-ea-in-inode-2.6-suse.patch
-export-ext3-2.6-suse.patch
-ext3-include-fixes-2.6-suse.patch
-ext3-extents-2.6.7.patch 
-ext3-mballoc2-2.6.7.patch 
-ext3-nlinks-2.6.7.patch
diff --git a/lustre/kernel_patches/series/rh-2.4.20 b/lustre/kernel_patches/series/rh-2.4.20
deleted file mode 100644 (file)
index 02481d0..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-configurable-x86-stack-2.4.20-rh.patch
-mcore-2.4.20-8.patch
-dsp.patch
-dev_read_only_2.4.20-rh.patch
-exports_2.4.20-rh-hp.patch
-lustre_version.patch
-vfs_intent-2.4.20-rh.patch 
-invalidate_show-2.4.20-rh.patch
-iod-rmap-exports-2.4.20.patch
-export-truncate.patch
-ext-2.4-patch-1-chaos.patch
-ext-2.4-patch-2.patch
-ext-2.4-patch-3.patch
-ext-2.4-patch-4.patch
-linux-2.4.20-xattr-0.8.54-chaos.patch
-ext3-2.4.20-fixes.patch
-ext3_orphan_lock-2.4.20-rh.patch
-ext3_delete_thread_2.4.20_chaos.patch 
-ext3-noread-2.4.20.patch
-extN-wantedi.patch
-ext3-san-2.4.20.patch
-ext3-map_inode_page.patch
-ext3-error-export.patch
-iopen-2.4.20.patch
-jbd-dont-account-blocks-twice.patch
-jbd-commit-tricks.patch
-ext3-o_direct-1.2.4.20-rh.patch 
-ext3-no-write-super-chaos.patch
-dynamic-locks-2.4.20-rh.patch 
-vfs-pdirops-2.4.20-rh.patch 
-ext3-pdirops-2.4.20-rh.patch 
-tcp_zero_copy_2.4.20_chaos.patch
-gpl_header-chaos-2.4.20.patch
-add_page_private.patch
-jbd-flushtime.patch
-jbd-get_write_access.patch
-nfs_export_kernel-2.4.20-rh.patch
-ext3-ea-in-inode-2.4.20.patch
-listman-2.4.20.patch
-ext3-trusted_ea-2.4.20.patch
-netconsole-2.4.20-rh.patch
-ext3-xattr-ptr-arith-fix.patch
-procfs-ndynamic-2.4.patch
-ext3-truncate-buffer-head.patch
-inode-max-readahead-2.4.24.patch
-mkdep-revert-rh-2.4.patch
-ext3-extents-2.4.20-rh.patch 
-ext3-extents-asyncdel-2.4.20-rh.patch
-ext3-mballoc-2.4.24.patch
-x86-fpu-crash.patch
-export-show_task-2.4-rh.patch 
-export-zap-page-range.patch
-grab_cache_page_nowait_gfp-rh-2.4.patch 
diff --git a/lustre/kernel_patches/series/rh-2.4.22 b/lustre/kernel_patches/series/rh-2.4.22
deleted file mode 100644 (file)
index 2e2fa8b..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-configurable-x86-stack-2.4.22-rh.patch
-dev_read_only_2.4.20-rh.patch
-exports_2.4.20-rh-hp.patch
-lustre_version.patch
-vfs_intent-2.4.22-rh.patch
-invalidate_show-2.4.20-rh.patch
-export-truncate.patch
-iod-stock-exports-2.4.22-rh.patch
-ext3-htree-2.4.22-rh.patch
-xattr-0.8.54-2.4.22-rh.patch
-ext3-orphan_lock-2.4.22-rh.patch
-ext3-noread-2.4.20.patch
-ext3_delete_thread_2.4.20_chaos.patch
-extN-wantedi-2.4.22-rh.patch
-ext3-san-2.4.20.patch
-ext3-map_inode_page.patch
-ext3-error-export.patch
-iopen-2.4.20.patch
-tcp-zero-copy-2.4.22-rh.patch
-jbd-dont-account-blocks-twice.patch
-jbd-commit-tricks.patch
-add_page_private.patch
-socket-exports-2.4.22-rh.patch
-nfs_export_kernel-2.4.22-rh.patch
-ext3-ea-in-inode-2.4.22-rh.patch
-listman-2.4.20.patch
-ext3-trusted_ea-2.4.20.patch
-ext3-xattr-ptr-arith-fix.patch
-procfs-ndynamic-2.4.patch
-ext3-truncate-buffer-head.patch
diff --git a/lustre/kernel_patches/series/suse-2.4.19 b/lustre/kernel_patches/series/suse-2.4.19
deleted file mode 100644 (file)
index 8748256..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-dev_read_only_hp_2.4.20.patch
-exports_2.4.19-suse.patch 
-lustre_version.patch
-vfs_intent-2.4.19-suse.patch 
-invalidate_show.patch
-export-truncate.patch
-iod-stock-24-exports-2.4.19-suse.patch 
-jbd-2.4.18-jcberr.patch
-ext-2.4-patch-1-chaos.patch 
-ext-2.4-patch-2.patch
-ext-2.4-patch-3.patch
-ext-2.4-patch-4.patch
-linux-2.4.19-xattr-0.8.54-suse.patch 
-ext3-2.4-ino_t.patch
-ext3-largefile.patch
-ext3-truncate_blocks.patch
-ext3-use-after-free-suse.patch 
-ext3-orphan_lock-2.4.19-suse.patch 
-ext3-delete_thread-2.4.19-suse.patch 
-ext3-noread-2.4.20.patch
-extN-wantedi-2.4.19-suse.patch 
-ext3-san-2.4.20.patch
-ext3-map_inode_page.patch
-ext3-error-export.patch
-iopen-2.4.19-suse.patch 
-tcp-zero-copy.patch
-add_page_private.patch
-removepage-2.4.19-suse.patch 
-jbd-ctx_switch.patch
-jbd-flushtime-2.4.19-suse.patch 
-jbd-get_write_access.patch
-ext3-ea-in-inode-2.4.20.patch 
-listman-2.4.20.patch
-ext3-trusted_ea-2.4.20.patch 
-ext3-truncate-buffer-head.patch
diff --git a/lustre/kernel_patches/series/suse-2.4.21 b/lustre/kernel_patches/series/suse-2.4.21
deleted file mode 100644 (file)
index 8cf74b3..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-configurable-x86-stack-2.4.20.patch
-dev_read_only_2.4.20-rh.patch
-exports_2.4.20-rh-hp.patch
-lustre_version.patch
-vfs_intent-2.4.20-vanilla.patch
-invalidate_show.patch
-export-truncate.patch
-iod-stock-24-exports.patch
-ext3-htree-suse.patch
-linux-2.4.21-xattr-0.8.54-suse.patch
-ext3-orphan_lock-suse.patch 
-ext3-noread-2.4.20.patch
-ext3-delete_thread-suse.patch 
-extN-wantedi.patch
-ext3-san-2.4.20.patch
-ext3-map_inode_page.patch
-ext3-error-export.patch
-iopen-2.4.20.patch
-tcp-zero-copy-2.4.22-rh.patch
-jbd-dont-account-blocks-twice.patch
-jbd-commit-tricks.patch
-ext3-no-write-super-chaos.patch
-add_page_private.patch
-socket-exports-vanilla.patch
-nfs_export_kernel-2.4.20.patch
-ext3-raw-lookup.patch
-ext3-ea-in-inode-2.4.20.patch
-listman-2.4.20.patch
-ext3-trusted_ea-2.4.20.patch
-ext3-xattr-ptr-arith-fix.patch
-procfs-ndynamic-2.4.patch
-ext3-truncate-buffer-head.patch
similarity index 96%
rename from lustre/kernel_patches/series/suse-2.4.21-2
rename to lustre/kernel_patches/series/suse-2.4.21-cray
index 52337b9..27928ea 100644 (file)
@@ -24,7 +24,7 @@ ext3-no-write-super-chaos.patch
 add_page_private.patch
 nfs_export_kernel-2.4.21-suse2.patch
 ext3-raw-lookup.patch
-ext3-ea-in-inode-2.4.21-chaos.patch
+ext3-ea-in-inode-2.4.21-suse2.patch
 listman-2.4.20.patch
 ext3-xattr-ptr-arith-fix.patch
 procfs-ndynamic-2.4.21-suse2.patch 
index a2d6649..3dd0d43 100644 (file)
@@ -37,7 +37,6 @@ ext3-truncate-buffer-head.patch
 inode-max-readahead-2.4.24.patch
 ext3-extents-2.4.24.patch
 ext3-extents-asyncdel-2.4.24.patch
-ext3-mballoc-2.4.24.patch
 export_num_siblings.patch
 ext3-nlinks-2.4.24.patch
 export-show_task-2.4-vanilla.patch 
diff --git a/lustre/kernel_patches/targets/2.6-rhel4.target.in b/lustre/kernel_patches/targets/2.6-rhel4.target.in
new file mode 100644 (file)
index 0000000..a44bc0f
--- /dev/null
@@ -0,0 +1,24 @@
+lnxmaj="2.6.9"
+lnxrel="5.0.3.EL"
+
+KERNEL=linux-${lnxmaj}-${lnxrel}.tar.bz2
+SERIES=2.6-rhel4.series
+VERSION=${lnxmaj}
+EXTRA_VERSION=${lnxrel}_lustre.@VERSION@
+RHBUILD=1
+LINUX26=1
+
+BASE_ARCHS="i686 x86_64 ia64"
+BIGMEM_ARCHS=""
+BOOT_ARCHS=""
+JENSEN_ARCHS=""
+SMP_ARCHS="i686 x86_64 ia64"
+UP_ARCHS=""
+
+# the modules in this kernel do not build with gcc 3.3 or 2.96
+for cc in gcc32 gcc33 ; do
+    if which $cc >/dev/null 2>/dev/null ; then
+        export CC=$cc
+        break
+    fi
+done
index 8e4ba6f..4d8423e 100644 (file)
@@ -1,10 +1,11 @@
-SERIES                 MNEMONIC                 COMMENT                     ARCH
+SERIES             MNEMONIC                 COMMENT                     ARCH
 
 SUPPORTED KERNELS:
-rhel-2.4.21            linux-2.4.21-20.3EL                                  all
-2.6-suse               linux-2.6                SLES9 SP1 kernel            all
+rhel-2.4.21        linux-2.4.21-20.3EL      RHEL3 2.4.21                all
+2.6-suse           linux-2.6-suse           SLES9 SP1 kernel            all
+2.6-rhel4          linux-2.6-rhel4          RHEL4 2.6.9 kernel       i386,x86_64
 
 UNSUPPORTED KERNELS; BEING PHASED OUT; MAY BE MISSING CRITICAL BUG FIXES:
-hp-pnnl-2.4.20         linux-2.4.20-hp4_pnnl1   same as vanilla but no uml  ia64
-vanilla-2.4.24         linux-2.4.24             patch with uml-2.4.24-6     um
-suse-2.4.21-jvn        linux-2.4.21-241         sles8 2.4 kernel            i386
+hp-pnnl-2.4.20     linux-2.4.20-hp4_pnnl1   same as vanilla but no uml  ia64
+vanilla-2.4.24     linux-2.4.24             patch with uml-2.4.24-6     um
+suse-2.4.21-jvn    linux-2.4.21-241         sles8 2.4 kernel            i386
index 2fb9c66..85830fc 100644 (file)
@@ -211,7 +211,7 @@ err:
 
 }
 
-int client_obd_cleanup(struct obd_device *obddev, int flags)
+int client_obd_cleanup(struct obd_device *obddev)
 {
         struct client_obd *cli = &obddev->u.cli;
 
@@ -227,7 +227,7 @@ int client_obd_cleanup(struct obd_device *obddev, int flags)
         class_destroy_import(cli->cl_import);
         cli->cl_import = NULL;
 
-        ldlm_put_ref(flags & OBD_OPT_FORCE);
+        ldlm_put_ref(obddev->obd_force);
 
         RETURN(0);
 }
@@ -280,7 +280,7 @@ out_ldlm:
                 obd->obd_namespace = NULL;
 out_disco:
                 cli->cl_conn_count--;
-                class_disconnect(exp, 0);
+                class_disconnect(exp);
         } else {
                 class_export_put(exp);
         }
@@ -289,7 +289,7 @@ out_sem:
         return rc;
 }
 
-int client_disconnect_export(struct obd_export *exp, int failover)
+int client_disconnect_export(struct obd_export *exp)
 {
         struct obd_device *obd = class_exp2obd(exp);
         struct client_obd *cli = &obd->u.cli;
@@ -335,7 +335,7 @@ int client_disconnect_export(struct obd_export *exp, int failover)
 
         EXIT;
  out_no_disconnect:
-        err = class_disconnect(exp, 0);
+        err = class_disconnect(exp);
         if (!rc && err)
                 rc = err;
  out_sem:
@@ -589,7 +589,7 @@ int target_handle_disconnect(struct ptlrpc_request *req)
 
         /* keep the rq_export around so we can send the reply */
         exp = class_export_get(req->rq_export);
-        req->rq_status = obd_disconnect(exp, 0);
+        req->rq_status = obd_disconnect(exp);
         RETURN(0);
 }
 
@@ -692,6 +692,8 @@ void target_cleanup_recovery(struct obd_device *obd)
         struct list_head *tmp, *n;
         struct ptlrpc_request *req;
 
+        LASSERT(obd->obd_stopping);
+
         spin_lock_bh(&obd->obd_processing_task_lock);
         if (!obd->obd_recovering) {
                 spin_unlock_bh(&obd->obd_processing_task_lock);
@@ -702,7 +704,6 @@ void target_cleanup_recovery(struct obd_device *obd)
         target_cancel_recovery_timer(obd);
         spin_unlock_bh(&obd->obd_processing_task_lock);
 
-
         list_for_each_safe(tmp, n, &obd->obd_delayed_reply_queue) {
                 req = list_entry(tmp, struct ptlrpc_request, rq_list);
                 list_del(&req->rq_list);
@@ -732,7 +733,7 @@ void target_abort_recovery(void *data)
 
         CERROR("%s: recovery period over; disconnecting unfinished clients.\n",
                obd->obd_name);
-        class_disconnect_stale_exports(obd, 0);
+        class_disconnect_stale_exports(obd);
         abort_recovery_queue(obd);
 
         target_finish_recovery(obd);
@@ -1028,13 +1029,23 @@ int target_queue_final_reply(struct ptlrpc_request *req, int rc)
                 LBUG();
         memcpy(saved_req, req, sizeof *saved_req);
         memcpy(reqmsg, req->rq_reqmsg, req->rq_reqlen);
+        
+        /* Don't race cleanup */
+        spin_lock_bh(&obd->obd_processing_task_lock);
+        if (obd->obd_stopping) {
+                spin_unlock_bh(&obd->obd_processing_task_lock);
+                OBD_FREE(reqmsg, req->rq_reqlen);
+                OBD_FREE(saved_req, sizeof *req);
+                req->rq_status = -ENOTCONN;
+                /* rv is ignored anyhow */
+                return -ENOTCONN;
+        }
         ptlrpc_rs_addref(req->rq_reply_state);  /* +1 ref for saved reply */
         req = saved_req;
         req->rq_reqmsg = reqmsg;
         class_export_get(req->rq_export);
         list_add(&req->rq_list, &obd->obd_delayed_reply_queue);
 
-        spin_lock_bh(&obd->obd_processing_task_lock);
         /* only count the first "replay over" request from each
            export */
         if (req->rq_export->exp_replay_needed) {
@@ -1044,6 +1055,7 @@ int target_queue_final_reply(struct ptlrpc_request *req, int rc)
         recovery_done = (obd->obd_recoverable_clients == 0);
         spin_unlock_bh(&obd->obd_processing_task_lock);
 
+        OBD_RACE(OBD_FAIL_LDLM_RECOV_CLIENTS);
         if (recovery_done) {
                 spin_lock_bh(&obd->obd_processing_task_lock);
                 obd->obd_recovering = obd->obd_abort_recovery = 0;
index ec30586..e46c0fe 100644 (file)
@@ -178,7 +178,7 @@ static void waiting_locks_callback(unsigned long unused)
                 lock = list_entry(waiting_locks_list.next, struct ldlm_lock,
                                   l_pending_chain);
 
-                if (lock->l_callback_timeout > jiffies)
+                if (time_after(lock->l_callback_timeout, jiffies))
                         break;
 
                 LDLM_ERROR(lock, "lock callback timer expired: evicting client "
@@ -245,7 +245,7 @@ static int ldlm_add_waiting_lock(struct ldlm_lock *lock)
 
         timeout_rounded = round_timeout(lock->l_callback_timeout);
 
-        if (timeout_rounded < waiting_locks_timer.expires ||
+        if (time_before(timeout_rounded, waiting_locks_timer.expires) ||
             !timer_pending(&waiting_locks_timer)) {
                 mod_timer(&waiting_locks_timer, timeout_rounded);
         }
@@ -622,6 +622,21 @@ int ldlm_handle_enqueue(struct ptlrpc_request *req,
                 }
         }
 
+        if (dlm_req->lock_desc.l_resource.lr_type < LDLM_MIN_TYPE ||
+            dlm_req->lock_desc.l_resource.lr_type >= LDLM_MAX_TYPE) {
+                DEBUG_REQ(D_ERROR, req, "invalid lock request type %d\n",
+                          dlm_req->lock_desc.l_resource.lr_type);
+                GOTO(out, rc = -EFAULT);
+        }
+
+        if (dlm_req->lock_desc.l_req_mode < LCK_EX ||
+            dlm_req->lock_desc.l_req_mode > LCK_NL ||
+            dlm_req->lock_desc.l_req_mode & (dlm_req->lock_desc.l_req_mode-1)) {
+                DEBUG_REQ(D_ERROR, req, "invalid lock request mode %d\n",
+                          dlm_req->lock_desc.l_req_mode);
+                GOTO(out, rc = -EFAULT);
+        }
+
         /* The lock's callback data might be set in the policy function */
         lock = ldlm_lock_create(obddev->obd_namespace, &dlm_req->lock_handle2,
                                 dlm_req->lock_desc.l_resource.lr_name,
index 71f090b..b362344 100644 (file)
@@ -179,15 +179,16 @@ void ldlm_proc_namespace(struct ldlm_namespace *ns)
         lock_name[MAX_STRING_SIZE] = '\0';
 
         memset(lock_vars, 0, sizeof(lock_vars));
-        lock_vars[0].read_fptr = lprocfs_rd_u64;
         lock_vars[0].name = lock_name;
 
         snprintf(lock_name, MAX_STRING_SIZE, "%s/resource_count", ns->ns_name);
-        lock_vars[0].data = &ns->ns_resources;
+        lock_vars[0].data = &ns->ns_refcount;
+        lock_vars[0].read_fptr = lprocfs_rd_atomic;
         lprocfs_add_vars(ldlm_ns_proc_dir, lock_vars, 0);
 
         snprintf(lock_name, MAX_STRING_SIZE, "%s/lock_count", ns->ns_name);
         lock_vars[0].data = &ns->ns_locks;
+        lock_vars[0].read_fptr = lprocfs_rd_u64;
         lprocfs_add_vars(ldlm_ns_proc_dir, lock_vars, 0);
 
         if (ns->ns_client) {
@@ -237,11 +238,11 @@ struct ldlm_namespace *ldlm_namespace_new(char *name, __u32 client)
 
         INIT_LIST_HEAD(&ns->ns_root_list);
         l_lock_init(&ns->ns_lock);
-        ns->ns_refcount = 0;
+        init_waitqueue_head(&ns->ns_refcount_waitq);
+        atomic_set(&ns->ns_refcount, 0);
         ns->ns_client = client;
         spin_lock_init(&ns->ns_counter_lock);
         ns->ns_locks = 0;
-        ns->ns_resources = 0;
 
         for (bucket = ns->ns_hash + RES_HASH_SIZE - 1; bucket >= ns->ns_hash;
              bucket--)
@@ -353,19 +354,11 @@ int ldlm_namespace_cleanup(struct ldlm_namespace *ns, int flags)
                         cleanup_resource(res, &res->lr_converting, flags);
                         cleanup_resource(res, &res->lr_waiting, flags);
 
-                        /* XXX what a mess: don't force cleanup if we're
-                         * local_only (which is only used by recovery).  In that
-                         * case, we probably still have outstanding lock refs
-                         * which reference these resources. -phil */
-                        if (!ldlm_resource_putref(res) &&
-                            !(flags & LDLM_FL_LOCAL_ONLY)) {
+                        if (!ldlm_resource_putref(res)) {
                                 CERROR("Namespace %s resource refcount %d "
-                                       "after lock cleanup; forcing cleanup.\n",
+                                       "after lock cleanup\n",
                                        ns->ns_name,
                                        atomic_read(&res->lr_refcount));
-                                ldlm_resource_dump(D_ERROR, res);
-                                atomic_set(&res->lr_refcount, 1);
-                                ldlm_resource_putref(res);
                         }
                 }
         }
@@ -400,6 +393,25 @@ int ldlm_namespace_free(struct ldlm_namespace *ns, int force)
         }
 #endif
 
+        if (atomic_read(&ns->ns_refcount) > 0) {
+                struct l_wait_info lwi = LWI_INTR(NULL, NULL);
+                int rc;
+                CDEBUG(D_DLMTRACE, 
+                       "dlm namespace %s free waiting on refcount %d\n", 
+                       ns->ns_name, atomic_read(&ns->ns_refcount));
+                rc = l_wait_event(ns->ns_refcount_waitq,
+                                  atomic_read(&ns->ns_refcount) == 0, &lwi);
+                if (atomic_read(&ns->ns_refcount)) {
+                        CERROR("Lock manager: waiting for the %s namespace "
+                               "was aborted with %d resources in use. (%d)\n"
+                               "I'm going to try to clean up anyway, but I "
+                               "might require a reboot of this node.\n",
+                               ns->ns_name, atomic_read(&ns->ns_refcount), rc);
+                }
+                CDEBUG(D_DLMTRACE, 
+                       "dlm namespace %s free done waiting\n", ns->ns_name);
+        }
+
         POISON(ns->ns_hash, 0x5a, sizeof(*ns->ns_hash) * RES_HASH_SIZE);
         OBD_VFREE(ns->ns_hash, sizeof(*ns->ns_hash) * RES_HASH_SIZE);
         OBD_FREE(ns->ns_name, strlen(ns->ns_name) + 1);
@@ -448,27 +460,23 @@ static struct ldlm_resource *ldlm_resource_new(void)
  * Returns: newly-allocated, referenced, unlocked resource */
 static struct ldlm_resource *
 ldlm_resource_add(struct ldlm_namespace *ns, struct ldlm_resource *parent,
-                  struct ldlm_res_id name, __u32 type)
+                  struct ldlm_res_id name, ldlm_type_t type)
 {
         struct list_head *bucket;
         struct ldlm_resource *res;
         ENTRY;
 
-        LASSERTF(type >= LDLM_MIN_TYPE && type <= LDLM_MAX_TYPE,
-                 "type: %d", type);
+        LASSERTF(type >= LDLM_MIN_TYPE && type < LDLM_MAX_TYPE,
+                 "type: %d\n", type);
 
         res = ldlm_resource_new();
         if (!res)
                 RETURN(NULL);
 
-        spin_lock(&ns->ns_counter_lock);
-        ns->ns_resources++;
-        spin_unlock(&ns->ns_counter_lock);
-
         l_lock(&ns->ns_lock);
         memcpy(&res->lr_name, &name, sizeof(res->lr_name));
         res->lr_namespace = ns;
-        ns->ns_refcount++;
+        atomic_inc(&ns->ns_refcount);
 
         res->lr_type = type;
         res->lr_most_restr = LCK_NL;
@@ -493,7 +501,7 @@ ldlm_resource_add(struct ldlm_namespace *ns, struct ldlm_resource *parent,
  * Returns: referenced, unlocked ldlm_resource or NULL */
 struct ldlm_resource *
 ldlm_resource_get(struct ldlm_namespace *ns, struct ldlm_resource *parent,
-                  struct ldlm_res_id name, __u32 type, int create)
+                  struct ldlm_res_id name, ldlm_type_t type, int create)
 {
         struct list_head *bucket, *tmp;
         struct ldlm_resource *res = NULL;
@@ -552,7 +560,7 @@ struct ldlm_resource *ldlm_resource_getref(struct ldlm_resource *res)
         LASSERT(res != NULL);
         LASSERT(res != LP_POISON);
         atomic_inc(&res->lr_refcount);
-        CDEBUG(D_INFO, "getref res: %p count: %d\n", res,
+        CDEBUG(D_DLMTRACE, "getref res: %p count: %d\n", res,
                atomic_read(&res->lr_refcount));
         return res;
 }
@@ -563,7 +571,7 @@ int ldlm_resource_putref(struct ldlm_resource *res)
         int rc = 0;
         ENTRY;
 
-        CDEBUG(D_INFO, "putref res: %p count: %d\n", res,
+        CDEBUG(D_DLMTRACE, "putref res: %p count: %d\n", res,
                atomic_read(&res->lr_refcount) - 1);
         LASSERT(atomic_read(&res->lr_refcount) > 0);
         LASSERT(atomic_read(&res->lr_refcount) < LI_POISON);
@@ -600,7 +608,6 @@ int ldlm_resource_putref(struct ldlm_resource *res)
                         LBUG();
                 }
 
-                ns->ns_refcount--;
                 list_del_init(&res->lr_hash);
                 list_del_init(&res->lr_childof);
                 if (res->lr_lvb_data)
@@ -609,9 +616,10 @@ int ldlm_resource_putref(struct ldlm_resource *res)
 
                 OBD_SLAB_FREE(res, ldlm_resource_slab, sizeof *res);
 
-                spin_lock(&ns->ns_counter_lock);
-                ns->ns_resources--;
-                spin_unlock(&ns->ns_counter_lock);
+                if (atomic_dec_and_test(&ns->ns_refcount)) {
+                        CDEBUG(D_DLMTRACE, "last ref on ns %s\n", ns->ns_name);
+                        wake_up(&ns->ns_refcount_waitq);
+                }
 
                 rc = 1;
                 EXIT;
@@ -674,7 +682,7 @@ void ldlm_namespace_dump(int level, struct ldlm_namespace *ns)
         struct list_head *tmp;
 
         CDEBUG(level, "--- Namespace: %s (rc: %d, client: %d)\n", ns->ns_name,
-               ns->ns_refcount, ns->ns_client);
+               atomic_read(&ns->ns_refcount), ns->ns_client);
 
         l_lock(&ns->ns_lock);
         if (time_after(jiffies, ns->ns_next_dump)) {
index b0c6bda..da29c9f 100644 (file)
@@ -43,7 +43,7 @@
 #undef LIST_HEAD
 
 #include <portals/api-support.h> /* needed for ptpctl.h */
-#include <portals/ptlctl.h>    /* needed for parse_dump */
+#include <portals/ptlctl.h>     /* needed for parse_dump */
 #include <procbridge.h>
 
 #include "llite_lib.h"
@@ -183,14 +183,14 @@ int lib_ioctl_nalcmd(int dev_id, int opc, void * ptr)
                 }
         }
 
-       return (0);
+        return (0);
 }
 
 int lib_ioctl(int dev_id, int opc, void * ptr)
 {
         int rc;
 
-       if (dev_id == OBD_DEV_ID) {
+        if (dev_id == OBD_DEV_ID) {
                 struct obd_ioctl_data *ioc = ptr;
 
                 //XXX hack!!!
@@ -204,8 +204,8 @@ int lib_ioctl(int dev_id, int opc, void * ptr)
 
                 if (rc)
                         return rc;
-       }
-       return (0);
+        }
+        return (0);
 }
 
 int lllib_init(char *dumpfile)
@@ -323,7 +323,7 @@ int liblustre_process_log(struct config_llog_instance *cfg, int allow_recov)
                 CERROR("class_config_parse_llog failed: rc = %d\n", rc);
         }
 
-        err = obd_disconnect(exp, 0);
+        err = obd_disconnect(exp);
 
 out_cleanup:
         LCFG_INIT(lcfg, LCFG_CLEANUP, name);
@@ -410,7 +410,7 @@ void __liblustre_setup_(void)
         char *root_path = "/";
         unsigned mntflgs = 0;
 
-       int err;
+        int err;
 
         /* consider tha case of starting multiple liblustre instances
          * at a same time on single node.
@@ -419,10 +419,10 @@ void __liblustre_setup_(void)
 
         signal(SIGUSR1, sighandler_USR1);
 
-       lustre_path = getenv(ENV_LUSTRE_MNTPNT);
-       if (!lustre_path) {
+        lustre_path = getenv(ENV_LUSTRE_MNTPNT);
+        if (!lustre_path) {
                 lustre_path = "/mnt/lustre";
-       }
+        }
 
         target = getenv(ENV_LUSTRE_MNTTGT);
         if (!target) {
@@ -454,38 +454,38 @@ void __liblustre_setup_(void)
                         obd_timeout);
         }
 
-       if (_sysio_init() != 0) {
-               perror("init sysio");
-               exit(1);
-       }
+        if (_sysio_init() != 0) {
+                perror("init sysio");
+                exit(1);
+        }
 
         /* cygwin don't need native driver */
 #ifndef __CYGWIN__
         _sysio_native_init();
 #endif
 
-       err = _sysio_mount_root(root_path, root_driver, mntflgs, NULL);
-       if (err) {
-               perror(root_driver);
-               exit(1);
-       }
+        err = _sysio_mount_root(root_path, root_driver, mntflgs, NULL);
+        if (err) {
+                perror(root_driver);
+                exit(1);
+        }
 
 #if 1
-       portal_debug = 0;
-       portal_subsystem_debug = 0;
+        portal_debug = 0;
+        portal_subsystem_debug = 0;
 #endif
-       err = lllib_init(dumpfile);
-       if (err) {
-               perror("init llite driver");
-               exit(1);
-       }       
+        err = lllib_init(dumpfile);
+        if (err) {
+                perror("init llite driver");
+                exit(1);
+        }       
 
         err = mount("/", lustre_path, lustre_driver, mntflgs, NULL);
-       if (err) {
-               errno = -err;
-               perror(lustre_driver);
-               exit(1);
-       }
+        if (err) {
+                errno = -err;
+                perror(lustre_driver);
+                exit(1);
+        }
 
 #if 0
         __sysio_hook_sys_enter = llu_check_request;
@@ -495,6 +495,6 @@ void __liblustre_setup_(void)
 
 void __liblustre_cleanup_(void)
 {
-       _sysio_shutdown();
+        _sysio_shutdown();
         PtlFini();
 }
index 1186004..44735fd 100644 (file)
@@ -55,7 +55,7 @@ static void llu_fsop_gone(struct filesys *fs)
         ENTRY;
 
         list_del(&sbi->ll_conn_chain);
-        obd_disconnect(sbi->ll_osc_exp, 0);
+        obd_disconnect(sbi->ll_osc_exp);
 
         /* NULL request to force sync on the MDS, and get the last_committed
          * value to flush remaining RPCs from the sending queue on client.
@@ -66,7 +66,7 @@ static void llu_fsop_gone(struct filesys *fs)
         if (!obd->obd_no_recov)
                 mdc_getstatus(sbi->ll_mdc_exp, &rootfid);
 
-        obd_disconnect(sbi->ll_mdc_exp, 0);
+        obd_disconnect(sbi->ll_mdc_exp);
 
         OBD_FREE(sbi, sizeof(*sbi));
 
@@ -1433,9 +1433,9 @@ out_inode:
 out_request:
         ptlrpc_req_finished(request);
 out_osc:
-        obd_disconnect(sbi->ll_osc_exp, 0);
+        obd_disconnect(sbi->ll_osc_exp);
 out_mdc:
-        obd_disconnect(sbi->ll_mdc_exp, 0);
+        obd_disconnect(sbi->ll_mdc_exp);
 out_free:
         OBD_FREE(sbi, sizeof(*sbi));
         return err;
index f29f732..39a53bd 100644 (file)
@@ -322,14 +322,18 @@ int ll_revalidate_it(struct dentry *de, int lookup_flags,
         rc = 1;
 
         /* unfortunately ll_intent_lock may cause a callback and revoke our
-           dentry */
+         * dentry */
         spin_lock(&dcache_lock);
         hlist_del_init(&de->d_hash);
         __d_rehash(de, 0);
         spin_unlock(&dcache_lock);
 
  out:
-        if (req != NULL && rc == 1)
+        /* If we had succesful it lookup on mds, but it happened to be negative,
+           we do not free request as it will be reused during lookup (see
+           comment in mdc/mdc_locks.c::mdc_intent_lock(). But if
+           request was not completed, we need to free it. (bug 5154) */
+        if (req != NULL && (rc == 1 || !it_disposition(it, DISP_ENQ_COMPLETE)))
                 ptlrpc_req_finished(req);
         if (rc == 0) {
                 ll_unhash_aliases(de->d_inode);
index 7640446..9e566f9 100644 (file)
@@ -7,6 +7,83 @@
 
 #include <linux/lustre_debug.h>
 
+/*
+struct lustre_intent_data {
+        __u64 it_lock_handle[2];
+        __u32 it_disposition;
+        __u32 it_status;
+        __u32 it_lock_mode;
+        }; */
+
+#define LL_IT2STR(it) ((it) ? ldlm_it2str((it)->it_op) : "0")
+
+static inline struct lookup_intent *ll_nd2it(struct nameidata *nd)
+{
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
+        return &nd->intent;
+#else
+        return nd->intent;
+#endif
+}
+
+struct ll_dentry_data {
+        int                      lld_cwd_count;
+        int                      lld_mnt_count;
+        struct obd_client_handle lld_cwd_och;
+        struct obd_client_handle lld_mnt_och;
+};
+
+#define ll_d2d(de) ((struct ll_dentry_data*) de->d_fsdata)
+
+extern struct file_operations ll_pgcache_seq_fops;
+
+#define LLI_INODE_MAGIC                 0x111d0de5
+#define LLI_INODE_DEAD                  0xdeadd00d
+#define LLI_F_HAVE_OST_SIZE_LOCK        0
+#define LLI_F_HAVE_MDS_SIZE_LOCK        1
+struct ll_inode_info {
+        int                     lli_inode_magic;
+        int                     lli_size_pid;
+        struct semaphore        lli_size_sem;
+        struct semaphore        lli_open_sem;
+        struct lov_stripe_md   *lli_smd;
+        char                   *lli_symlink_name;
+        __u64                   lli_maxbytes;
+        __u64                   lli_io_epoch;
+        unsigned long           lli_flags;
+
+        /* this lock protects s_d_w and p_w_ll and mmap_cnt */
+        spinlock_t              lli_lock;
+        struct list_head        lli_pending_write_llaps;
+        int                     lli_send_done_writing;
+        atomic_t                lli_mmap_cnt;
+
+        struct list_head        lli_close_item;
+
+        /* for writepage() only to communicate to fsync */
+        int                     lli_async_rc;
+
+        struct file_operations *ll_save_ifop;
+        struct file_operations *ll_save_ffop;
+        struct file_operations *ll_save_wfop;
+        struct file_operations *ll_save_wrfop;
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
+        struct inode            lli_vfs_inode;
+#endif
+};
+
+// FIXME: replace the name of this with LL_I to conform to kernel stuff
+// static inline struct ll_inode_info *LL_I(struct inode *inode)
+static inline struct ll_inode_info *ll_i2info(struct inode *inode)
+{
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
+        return container_of(inode, struct ll_inode_info, lli_vfs_inode);
+#else
+        return (struct ll_inode_info *)&(inode->u.generic_ip);
+#endif
+}
+
+
 /* default to about 40meg of readahead on a given system.  That much tied
  * up in 512k readahead requests serviced at 40ms each is about 1GB/s. */
 #define SBI_DEFAULT_READAHEAD_MAX (40UL << (20 - PAGE_CACHE_SHIFT))
index b7a58c4..fbc9200 100644 (file)
@@ -240,9 +240,9 @@ out_root:
         if (root)
                 iput(root);
 out_osc:
-        obd_disconnect(sbi->ll_osc_exp, 0);
+        obd_disconnect(sbi->ll_osc_exp);
 out_mdc:
-        obd_disconnect(sbi->ll_mdc_exp, 0);
+        obd_disconnect(sbi->ll_mdc_exp);
 out:
         lprocfs_unregister_mountpoint(sbi);
         RETURN(err);
@@ -275,11 +275,11 @@ void lustre_dump_dentry(struct dentry *dentry, int recur)
                 subdirs++;
 
         CERROR("dentry %p dump: name=%.*s parent=%.*s (%p), inode=%p, count=%u,"
-               " flags=0x%x, vfs_flags=0x%lx, fsdata=%p, %d subdirs\n", dentry,
+               " flags=0x%x, vfs_flags=0x%x, fsdata=%p, %d subdirs\n", dentry,
                dentry->d_name.len, dentry->d_name.name,
                dentry->d_parent->d_name.len, dentry->d_parent->d_name.name,
                dentry->d_parent, dentry->d_inode, atomic_read(&dentry->d_count),
-               dentry->d_flags, dentry->d_vfs_flags, dentry->d_fsdata, subdirs);
+               dentry->d_flags, dentry->d_flags, dentry->d_fsdata, subdirs);
         if (dentry->d_inode != NULL)
                 lustre_dump_inode(dentry->d_inode);
 
@@ -301,7 +301,7 @@ void lustre_common_put_super(struct super_block *sb)
         ll_close_thread_shutdown(sbi->ll_lcq);
 
         list_del(&sbi->ll_conn_chain);
-        obd_disconnect(sbi->ll_osc_exp, 0);
+        obd_disconnect(sbi->ll_osc_exp);
 
         lprocfs_unregister_mountpoint(sbi);
         if (sbi->ll_proc_root) {
@@ -309,7 +309,7 @@ void lustre_common_put_super(struct super_block *sb)
                 sbi->ll_proc_root = NULL;
         }
 
-        obd_disconnect(sbi->ll_mdc_exp, 0);
+        obd_disconnect(sbi->ll_mdc_exp);
 
         // We do this to get rid of orphaned dentries. That is not really trw.
         hlist_for_each_safe(tmp, next, &sbi->ll_orphan_dentry_list) {
@@ -398,6 +398,7 @@ void ll_lli_init(struct ll_inode_info *lli)
 {
         sema_init(&lli->lli_open_sem, 1);
         sema_init(&lli->lli_size_sem, 1);
+        lli->lli_size_pid = 0;
         lli->lli_flags = 0;
         lli->lli_maxbytes = PAGE_CACHE_MAXBYTES;
         spin_lock_init(&lli->lli_lock);
@@ -546,11 +547,22 @@ int lustre_process_log(struct lustre_mount_data *lmd, char * profile,
          */
         rc = class_config_dump_llog(ctxt, profile, cfg);
 #endif
-        if (rc) {
+        switch (rc) {
+        case 0:
+                break;
+        case -EINVAL:
+                LCONSOLE_ERROR("%s: The configuration '%s' could not be read "
+                               "from the MDS.  Make sure this client and the "
+                               "MDS are running compatible versions of "
+                               "Lustre.\n",
+                               obd->obd_name, profile);
+                /* fall through */
+        default:
                 CERROR("class_config_parse_llog failed: rc = %d\n", rc);
+                break;
         }
 
-        err = obd_disconnect(exp, 0);
+        err = obd_disconnect(exp);
 
 out_cleanup:
         LCFG_INIT(lcfg, LCFG_CLEANUP, name);
@@ -1036,10 +1048,12 @@ int ll_setattr_raw(struct inode *inode, struct iattr *attr)
                         RETURN(rc);
 
                 down(&lli->lli_size_sem);
+                lli->lli_size_pid = current->pid;
                 rc = vmtruncate(inode, attr->ia_size);
                 // if vmtruncate returned 0, then ll_truncate dropped _size_sem
                 if (rc != 0) {
                         LASSERT(atomic_read(&lli->lli_size_sem.count) <= 0);
+                        lli->lli_size_pid = 0;
                         up(&lli->lli_size_sem);
                 }
 
index 8bbd1d8..d88a5d5 100644 (file)
@@ -118,12 +118,19 @@ void ll_truncate(struct inode *inode)
         CDEBUG(D_VFSTRACE, "VFS Op:inode=%lu/%u(%p) to %llu\n", inode->i_ino,
                inode->i_generation, inode, inode->i_size);
 
+        if (lli->lli_size_pid != current->pid) {
+                EXIT;
+                return;
+        }
+
         if (!lsm) {
                 CDEBUG(D_INODE, "truncate on inode %lu with no objects\n",
                        inode->i_ino);
                 GOTO(out_unlock, 0);
         }
 
+        LASSERT(atomic_read(&lli->lli_size_sem.count) <= 0);
+
         if (lov_merge_size(lsm, 0) == inode->i_size) {
                 CDEBUG(D_VFSTRACE, "skipping punch for "LPX64" (size = %llu)\n",
                        lsm->lsm_object_id, inode->i_size);
@@ -140,7 +147,7 @@ void ll_truncate(struct inode *inode)
 
         obd_adjust_kms(ll_i2obdexp(inode), lsm, inode->i_size, 1);
 
-        LASSERT(atomic_read(&lli->lli_size_sem.count) <= 0);
+        lli->lli_size_pid = 0;
         up(&lli->lli_size_sem);
 
         rc = obd_punch(ll_i2obdexp(inode), &oa, lsm, inode->i_size,
@@ -156,7 +163,7 @@ void ll_truncate(struct inode *inode)
         return;
 
  out_unlock:
-        LASSERT(atomic_read(&lli->lli_size_sem.count) <= 0);
+        lli->lli_size_pid = 0;
         up(&lli->lli_size_sem);
 } /* ll_truncate */
 
index 7809366..056d60d 100644 (file)
@@ -159,7 +159,6 @@ static struct llog_operations lov_size_repl_logops = {
         lop_cancel: lov_llog_repl_cancel
 };
 
-
 int lov_llog_init(struct obd_device *obd, struct obd_device *tgt,
                   int count, struct llog_catid *logid)
 {
@@ -191,26 +190,21 @@ int lov_llog_init(struct obd_device *obd, struct obd_device *tgt,
 
 int lov_llog_finish(struct obd_device *obd, int count)
 {
-        struct lov_obd *lov = &obd->u.lov;
-        int i, rc = 0;
+        struct llog_ctxt *ctxt;
+        int rc = 0;
         ENTRY;
-        
-        rc = llog_cleanup(llog_get_context(obd, LLOG_UNLINK_ORIG_CTXT));
-        if (rc)
-                RETURN(rc);
 
-        rc = llog_cleanup(llog_get_context(obd, LLOG_SIZE_REPL_CTXT));
+        /* cleanup our llogs only if the ctxts have been setup
+         * (lov1 doesn't setup, lov_mds1 does). */
+        ctxt = llog_get_context(obd, LLOG_UNLINK_ORIG_CTXT);
+        if (ctxt)
+                rc = llog_cleanup(ctxt);
         if (rc)
                 RETURN(rc);
 
-        LASSERT(lov->desc.ld_tgt_count  == count);
-        for (i = 0; i < lov->desc.ld_tgt_count; i++) {
-                struct obd_device *child = lov->tgts[i].ltd_exp->exp_obd;
-                rc = obd_llog_finish(child, 1);
-                if (rc) {
-                        CERROR("error osc_llog_finish %d\n", i);
-                        break;
-                }
-        }
+        ctxt = llog_get_context(obd, LLOG_SIZE_REPL_CTXT);
+        if (ctxt)
+                rc = llog_cleanup(ctxt);
+
         RETURN(rc);
 }
index 3d4eb32..d9e52c3 100644 (file)
@@ -123,7 +123,7 @@ static int lov_connect(struct lustre_handle *conn, struct obd_device *obd,
                 if (rc) {
                         CERROR("Target %s register_observer error %d\n",
                                tgt_uuid->uuid, rc);
-                        obd_disconnect(tgts->ltd_exp, 0);
+                        obd_disconnect(tgts->ltd_exp);
                         GOTO(out_disc, rc);
                 }
 
@@ -143,16 +143,16 @@ static int lov_connect(struct lustre_handle *conn, struct obd_device *obd,
                 tgts->active = 0;
                 /* save for CERROR below; (we know it's terminated) */
                 uuid = tgts->uuid;
-                rc2 = obd_disconnect(tgts->ltd_exp, 0);
+                rc2 = obd_disconnect(tgts->ltd_exp);
                 if (rc2)
                         CERROR("error: LOV target %s disconnect on OST idx %d: "
                                "rc = %d\n", uuid.uuid, i, rc2);
         }
-        class_disconnect(exp, 0);
+        class_disconnect(exp);
         RETURN (rc);
 }
 
-static int lov_disconnect(struct obd_export *exp, int flags)
+static int lov_disconnect(struct obd_export *exp)
 {
         struct obd_device *obd = class_exp2obd(exp);
         struct lov_obd *lov = &obd->u.lov;
@@ -190,7 +190,7 @@ static int lov_disconnect(struct obd_export *exp, int flags)
                 obd_register_observer(osc_exp->exp_obd, NULL);
 
                 spin_unlock(&lov->lov_lock);
-                rc = obd_disconnect(osc_exp, flags);
+                rc = obd_disconnect(osc_exp);
                 spin_lock(&lov->lov_lock);
                 if (rc) {
                         if (lov->tgts[i].active) {
@@ -207,7 +207,7 @@ static int lov_disconnect(struct obd_export *exp, int flags)
         spin_unlock(&lov->lov_lock);
 
  out_local:
-        rc = class_disconnect(exp, 0);
+        rc = class_disconnect(exp);
         RETURN(rc);
 }
 
@@ -387,11 +387,12 @@ static int lov_setup(struct obd_device *obd, obd_count len, void *buf)
         RETURN(0);
 }
 
-static int lov_cleanup(struct obd_device *obd, int flags)
+static int lov_cleanup(struct obd_device *obd)
 {
         struct lov_obd *lov = &obd->u.lov;
 
         lprocfs_obd_cleanup(obd);
+        obd_llog_finish(obd, 0);
         OBD_FREE(lov->tgts, lov->bufsize);
 
         RETURN(0);
@@ -1668,7 +1669,6 @@ static int lov_set_info(struct obd_export *exp, obd_count keylen,
                         RETURN(-EINVAL);
                 for (i = 0; i < lov->desc.ld_tgt_count; i++) {
                         /* initialize all OSCs, even inactive ones */
-
                         err = obd_set_info(lov->tgts[i].ltd_exp,
                                           keylen, key, sizeof(obd_id),
                                           ((obd_id*)val) + i);
index 080d3ad..b9f17ef 100644 (file)
@@ -116,11 +116,26 @@ static void *fsfilt_ext3_start(struct inode *inode, int op, void *desc_private,
                 /* additional block + block bitmap + GDT for long symlink */
                 nblocks += 3;
                 /* no break */
-        case FSFILT_OP_CREATE:
+        case FSFILT_OP_CREATE: {
+#if defined(EXT3_EXTENTS_FL) && defined(EXT3_INDEX_FL)
+                static int warned;
+                if (!warned) {
+                        if (!test_opt(inode->i_sb, EXTENTS)) {
+                                warned = 1;
+                        } else if (((EXT3_I(inode)->i_flags &
+                              cpu_to_le32(EXT3_EXTENTS_FL | EXT3_INDEX_FL)) ==
+                              cpu_to_le32(EXT3_EXTENTS_FL | EXT3_INDEX_FL))) {
+                                CWARN("extent-mapped directory found - contact "
+                                      "CFS: support@clusterfs.com\n");
+                                warned = 1;
+                        }
+                }
+#endif
                 /* create/update logs for each stripe */
                 nblocks += (EXT3_INDEX_EXTRA_TRANS_BLOCKS +
                             EXT3_SINGLEDATA_TRANS_BLOCKS) * logs;
                 /* no break */
+        }
         case FSFILT_OP_MKDIR:
         case FSFILT_OP_MKNOD:
                 /* modify one inode + block bitmap + GDT */
@@ -635,9 +650,9 @@ static int fsfilt_ext3_sync(struct super_block *sb)
         return ext3_force_commit(sb);
 }
 
-#ifndef EXT3_EXT_CACHE_NO       /* we need this for struct ext3_ext_cache */
-#undef EXT3_MULTIBLOCK_ALLOCATOR
+#if defined(EXT3_MULTIBLOCK_ALLOCATOR) && (!defined(EXT3_EXT_CACHE_NO) || defined(EXT_CACHE_MARK))
 #warning "kernel code has old extents/mballoc patch, disabling"
+#undef EXT3_MULTIBLOCK_ALLOCATOR
 #endif
 
 #ifdef EXT3_MULTIBLOCK_ALLOCATOR
@@ -952,16 +967,13 @@ int fsfilt_ext3_map_inode_pages(struct inode *inode, struct page **page,
                                 struct semaphore *optional_sem)
 {
         int rc;
-        if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL) {
 #ifdef EXT3_MULTIBLOCK_ALLOCATOR
+        if (EXT3_I(inode)->i_flags & EXT3_EXTENTS_FL) {
                 rc = fsfilt_ext3_map_ext_inode_pages(inode, page, pages,
                                                      blocks, created, create);
-#else
-                CERROR("extent-mapped file with unsupported kernel\n");
-                rc = -EIO;
-#endif
                 return rc;
         }
+#endif
         if (optional_sem != NULL)
                 down(optional_sem);
         rc = fsfilt_ext3_map_bm_inode_pages(inode, page, pages, blocks,
index 022b534..64b589c 100644 (file)
@@ -41,7 +41,7 @@
 
 #define REQUEST_MINOR 244
 
-static int mdc_cleanup(struct obd_device *obd, int flags);
+static int mdc_cleanup(struct obd_device *obd);
 
 extern int mds_queue_req(struct ptlrpc_request *);
 /* Helper that implements most of mdc_getstatus and signal_completed_replay. */
@@ -899,7 +899,7 @@ static int mdc_setup(struct obd_device *obd, obd_count len, void *buf)
 
         rc = obd_llog_init(obd, obd, 0, NULL);
         if (rc) {
-                mdc_cleanup(obd, 0);
+                mdc_cleanup(obd);
                 CERROR("failed to setup llogging subsystems\n");
         }
 
@@ -944,7 +944,7 @@ int mdc_init_ea_size(struct obd_export *mdc_exp, struct obd_export *lov_exp)
         RETURN(0);
 }
 
-static int mdc_precleanup(struct obd_device *obd, int flags)
+static int mdc_precleanup(struct obd_device *obd)
 {
         int rc = 0;
 
@@ -955,7 +955,7 @@ static int mdc_precleanup(struct obd_device *obd, int flags)
         RETURN(rc);
 }
 
-static int mdc_cleanup(struct obd_device *obd, int flags)
+static int mdc_cleanup(struct obd_device *obd)
 {
         struct client_obd *cli = &obd->u.cli;
 
@@ -965,7 +965,7 @@ static int mdc_cleanup(struct obd_device *obd, int flags)
         lprocfs_obd_cleanup(obd);
         ptlrpcd_decref();
 
-        return client_obd_cleanup(obd, flags);
+        return client_obd_cleanup(obd);
 }
 
 
index 8fcf2e1..5dcdadb 100644 (file)
@@ -60,7 +60,7 @@ static int mds_intent_policy(struct ldlm_namespace *ns,
                              struct ldlm_lock **lockp, void *req_cookie,
                              ldlm_mode_t mode, int flags, void *data);
 static int mds_postsetup(struct obd_device *obd);
-static int mds_cleanup(struct obd_device *obd, int flags);
+static int mds_cleanup(struct obd_device *obd);
 
 /* Assumes caller has already pushed into the kernel filesystem context */
 static int mds_sendpage(struct ptlrpc_request *req, struct file *file,
@@ -295,7 +295,7 @@ static int mds_connect(struct lustre_handle *conn, struct obd_device *obd,
 out:
         if (rc) {
                 OBD_FREE(mcd, sizeof(*mcd));
-                class_disconnect(exp, 0);
+                class_disconnect(exp);
         }
         class_export_put(exp);
 
@@ -358,14 +358,13 @@ static int mds_destroy_export(struct obd_export *export)
         }
         spin_unlock(&med->med_open_lock);
         pop_ctxt(&saved, &obd->obd_ctxt, NULL);
-
 out:
         mds_client_free(export, !(export->exp_flags & OBD_OPT_FAILOVER));
 
         RETURN(rc);
 }
 
-static int mds_disconnect(struct obd_export *exp, int flags)
+static int mds_disconnect(struct obd_export *exp)
 {
         unsigned long irqflags;
         int rc;
@@ -374,12 +373,8 @@ static int mds_disconnect(struct obd_export *exp, int flags)
         LASSERT(exp);
         class_export_get(exp);
 
-        spin_lock_irqsave(&exp->exp_lock, irqflags);
-        exp->exp_flags = flags;
-        spin_unlock_irqrestore(&exp->exp_lock, irqflags);
-
         /* Disconnect early so that clients can't keep using export */
-        rc = class_disconnect(exp, flags);
+        rc = class_disconnect(exp);
         ldlm_cancel_locks_for_export(exp);
 
         /* complete all outstanding replies */
@@ -1391,8 +1386,6 @@ static int mds_setup(struct obd_device *obd, obd_count len, void *buf)
         int rc = 0;
         ENTRY;
 
-        dev_clear_rdonly(2);
-
         if (!lcfg->lcfg_inlbuf1 || !lcfg->lcfg_inlbuf2)
                 RETURN(rc = -EINVAL);
 
@@ -1426,7 +1419,9 @@ static int mds_setup(struct obd_device *obd, obd_count len, void *buf)
         }
 
         CDEBUG(D_SUPER, "%s: mnt = %p\n", lcfg->lcfg_inlbuf1, mnt);
-
+        
+        LASSERT(!ll_check_rdonly(ll_sbdev(mnt->mnt_sb)));
+        
         sema_init(&mds->mds_orphan_recovery_sem, 1);
         sema_init(&mds->mds_epoch_sem, 1);
         spin_lock_init(&mds->mds_transno_lock);
@@ -1436,7 +1431,7 @@ static int mds_setup(struct obd_device *obd, obd_count len, void *buf)
         sprintf(ns_name, "mds-%s", obd->obd_uuid.uuid);
         obd->obd_namespace = ldlm_namespace_new(ns_name, LDLM_NAMESPACE_SERVER);
         if (obd->obd_namespace == NULL) {
-                mds_cleanup(obd, 0);
+                mds_cleanup(obd);
                 GOTO(err_put, rc = -ENOMEM);
         }
         ldlm_register_intent(obd->obd_namespace, mds_intent_policy);
@@ -1502,7 +1497,7 @@ static int mds_setup(struct obd_device *obd, obd_count len, void *buf)
 
 err_fs:
         /* No extra cleanup needed for llog_init_commit_thread() */
-        mds_fs_cleanup(obd, 0);
+        mds_fs_cleanup(obd);
 err_ns:
         ldlm_namespace_free(obd->obd_namespace, 0);
         obd->obd_namespace = NULL;
@@ -1538,8 +1533,22 @@ static int mds_postsetup(struct obd_device *obd)
                 rc = class_config_parse_llog(llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT), 
                                              mds->mds_profile, &cfg);
                 pop_ctxt(&saved, &obd->obd_ctxt, NULL);
-                if (rc)
+                switch (rc) {
+                case 0:
+                        break;
+                case -EINVAL:
+                        LCONSOLE_ERROR("%s: the profile %s could not be read. "
+                                       "If you recently installed a new "
+                                       "version of Lustre, you may need to "
+                                       "re-run 'lconf --write_conf "
+                                       "<yourconfig>.xml' command line before "
+                                       "restarting the MDS.\n",
+                                       obd->obd_name, mds->mds_profile);
+                        /* fall through */
+                default:
                         GOTO(err_llog, rc);
+                        break;
+                }
 
                 lprof = class_get_profile(mds->mds_profile);
                 if (lprof == NULL) {
@@ -1644,24 +1653,33 @@ int mds_lov_clean(struct obd_device *obd)
         RETURN(0);
 }
 
-static int mds_precleanup(struct obd_device *obd, int flags)
+static int mds_precleanup(struct obd_device *obd)
 {
         int rc = 0;
         ENTRY;
 
-        mds_lov_disconnect(obd, flags);
+        mds_lov_set_cleanup_flags(obd);
+        target_cleanup_recovery(obd);
+        mds_lov_disconnect(obd);
         mds_lov_clean(obd);
         llog_cleanup(llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT));
         RETURN(rc);
 }
 
-static int mds_cleanup(struct obd_device *obd, int flags)
+static int mds_cleanup(struct obd_device *obd)
 {
         struct mds_obd *mds = &obd->u.mds;
+        ll_sbdev_type save_dev;
         ENTRY;
 
         if (mds->mds_sb == NULL)
                 RETURN(0);
+        save_dev = ll_sbdev(mds->mds_sb);
+        
+        if (mds->mds_osc_exp)
+                /* lov export was disconnected by mds_lov_clean;
+                   we just need to drop our ref */
+                class_export_put(mds->mds_osc_exp);
 
         lprocfs_obd_cleanup(obd);
 
@@ -1670,7 +1688,7 @@ static int mds_cleanup(struct obd_device *obd, int flags)
                 OBD_FREE(mds->mds_lov_objids,
                          mds->mds_lov_desc.ld_tgt_count * sizeof(obd_id));
         }
-        mds_fs_cleanup(obd, flags);
+        mds_fs_cleanup(obd);
 
         unlock_kernel();
 
@@ -1681,10 +1699,9 @@ static int mds_cleanup(struct obd_device *obd, int flags)
                        atomic_read(&obd->u.mds.mds_vfsmnt->mnt_count));
 
         mntput(mds->mds_vfsmnt);
+        mds->mds_sb = NULL;
 
-        mds->mds_sb = 0;
-
-        ldlm_namespace_free(obd->obd_namespace, flags & OBD_OPT_FORCE);
+        ldlm_namespace_free(obd->obd_namespace, obd->obd_force);
 
         spin_lock_bh(&obd->obd_processing_task_lock);
         if (obd->obd_recovering) {
@@ -1693,8 +1710,11 @@ static int mds_cleanup(struct obd_device *obd, int flags)
         }
         spin_unlock_bh(&obd->obd_processing_task_lock);
 
+        obd_llog_finish(obd, 0);
+
+        ll_clear_rdonly(save_dev);
+        
         lock_kernel();
-        dev_clear_rdonly(2);
         fsfilt_put_ops(obd->obd_fsops);
 
         LCONSOLE_INFO("MDT %s has stopped.\n", obd->obd_name);
@@ -1983,7 +2003,7 @@ err_lprocfs:
         return rc;
 }
 
-static int mdt_cleanup(struct obd_device *obd, int flags)
+static int mdt_cleanup(struct obd_device *obd)
 {
         struct mds_obd *mds = &obd->u.mds;
         ENTRY;
index 42d19c4..ffbf43f 100644 (file)
@@ -364,7 +364,7 @@ static int mds_init_server_data(struct obd_device *obd, struct file *file)
         RETURN(0);
 
 err_client:
-        class_disconnect_exports(obd, 0);
+        class_disconnect_exports(obd);
 err_msd:
         mds_server_free_data(mds);
         RETURN(rc);
@@ -490,7 +490,7 @@ err_lov_objid:
         if (mds->mds_lov_objid_filp && filp_close(mds->mds_lov_objid_filp, 0))
                 CERROR("can't close %s after error\n", LOV_OBJID);
 err_client:
-        class_disconnect_exports(obd, 0);
+        class_disconnect_exports(obd);
 err_last_rcvd:
         if (mds->mds_rcvd_filp && filp_close(mds->mds_rcvd_filp, 0))
                 CERROR("can't close %s after error\n", LAST_RCVD);
@@ -506,18 +506,17 @@ err_fid:
 }
 
 
-int mds_fs_cleanup(struct obd_device *obd, int flags)
+int mds_fs_cleanup(struct obd_device *obd)
 {
         struct mds_obd *mds = &obd->u.mds;
         struct obd_run_ctxt saved;
         int rc = 0;
 
-        if (flags & OBD_OPT_FAILOVER)
+        if (obd->obd_fail)
                 CERROR("%s: shutting down for failover; client state will"
                        " be preserved.\n", obd->obd_name);
 
-        class_disconnect_exports(obd, flags); /* cleans up client info too */
-        target_cleanup_recovery(obd);
+        class_disconnect_exports(obd); /* cleans up client info too */
         mds_server_free_data(mds);
 
         push_ctxt(&saved, &obd->obd_ctxt, NULL);
@@ -656,11 +655,17 @@ int mds_obd_destroy(struct obd_export *exp, struct obdo *oa,
 
         down(&parent_inode->i_sem);
         de = lookup_one_len(fidname, mds->mds_objects_dir, namelen);
-        if (IS_ERR(de) || de->d_inode == NULL) {
-                rc = IS_ERR(de) ? PTR_ERR(de) : -ENOENT;
+        if (IS_ERR(de)) {
+                rc = IS_ERR(de);
+                de = NULL;
+                CERROR("error looking up object "LPU64" %s: rc %d\n",
+                       oa->o_id, fidname, rc);
+                GOTO(out_dput, rc);
+        }
+        if (de->d_inode == NULL) {
                 CERROR("destroying non-existent object "LPU64" %s\n",
                        oa->o_id, fidname);
-                GOTO(out_dput, rc = IS_ERR(de) ? PTR_ERR(de) : -ENOENT);
+                GOTO(out_dput, rc = -ENOENT);
         }
 
         /* Stripe count is 1 here since this is some MDS specific stuff
index 11ff9e9..3ca6feb 100644 (file)
@@ -137,8 +137,8 @@ int mds_llog_finish(struct obd_device *obd, int count);
 
 /* mds/mds_lov.c */
 int mds_lov_connect(struct obd_device *obd, char * lov_name);
-int mds_lov_disconnect(struct obd_device *obd, int flags);
-int mds_get_lovtgts(struct obd_device *, int tgt_count, struct obd_uuid *);
+int mds_lov_disconnect(struct obd_device *obd);
+void mds_lov_set_cleanup_flags(struct obd_device *);
 int mds_lov_write_objids(struct obd_device *obd);
 void mds_lov_update_objids(struct obd_device *obd, obd_id *ids);
 int mds_lov_set_growth(struct mds_obd *mds, int count);
index b7ebc31..1436948 100644 (file)
@@ -144,21 +144,19 @@ int mds_llog_init(struct obd_device *obd, struct obd_device *tgt,
 
 int mds_llog_finish(struct obd_device *obd, int count)
 {
-        struct obd_device *lov_obd = obd->u.mds.mds_osc_obd;
-        int rc;
+        struct llog_ctxt *ctxt;
+        int rc = 0;
         ENTRY;
 
-        rc = llog_cleanup(llog_get_context(obd, LLOG_UNLINK_ORIG_CTXT));
-        if (rc)
-                RETURN(rc);
-
-        rc = llog_cleanup(llog_get_context(obd, LLOG_SIZE_REPL_CTXT));
+        ctxt = llog_get_context(obd, LLOG_UNLINK_ORIG_CTXT);
+        if (ctxt) 
+                rc = llog_cleanup(ctxt);
         if (rc)
                 RETURN(rc);
 
-        rc = obd_llog_finish(lov_obd, count);
-        if (rc)
-                CERROR("error lov_llog_finish\n");
-
+        ctxt = llog_get_context(obd, LLOG_SIZE_REPL_CTXT);
+        if (ctxt)
+                rc = llog_cleanup(ctxt);
+        
         RETURN(rc);
 }
index f9d9568..92eac6b 100644 (file)
@@ -258,39 +258,61 @@ int mds_lov_connect(struct obd_device *obd, char * lov_name)
 err_reg:
         obd_register_observer(mds->mds_osc_obd, NULL);
 err_discon:
-        obd_disconnect(mds->mds_osc_exp, 0);
+        obd_disconnect(mds->mds_osc_exp);
         mds->mds_osc_exp = NULL;
         mds->mds_osc_obd = ERR_PTR(rc);
         RETURN(rc);
 }
 
-int mds_lov_disconnect(struct obd_device *obd, int flags)
+int mds_lov_disconnect(struct obd_device *obd)
 {
         struct mds_obd *mds = &obd->u.mds;
         int rc = 0;
         ENTRY;
 
         if (!IS_ERR(mds->mds_osc_obd) && mds->mds_osc_exp != NULL) {
-                /* cleanup all llogging subsystems */
-                rc = obd_llog_finish(obd, mds->mds_lov_desc.ld_tgt_count);
-                if (rc)
-                        CERROR("failed to cleanup llogging subsystems\n");
-
                 obd_register_observer(mds->mds_osc_obd, NULL);
 
-                rc = obd_disconnect(mds->mds_osc_exp, flags);
-                /* if obd_disconnect fails (probably because the
-                 * export was disconnected by class_disconnect_exports)
-                 * then we just need to drop our ref. */
-                if (rc != 0)
-                        class_export_put(mds->mds_osc_exp);
-                mds->mds_osc_exp = NULL;
-                mds->mds_osc_obd = NULL;
+                /* The actual disconnect of the mds_lov will be called from
+                 * class_disconnect_exports from mds_lov_clean. So we have to
+                 * ensure that class_cleanup doesn't fail due to the extra ref
+                 * we're holding now. The mechanism to do that already exists -
+                 * the obd_force flag. We'll drop the final ref to the
+                 * mds_osc_exp in mds_cleanup. */
+                mds->mds_osc_obd->obd_force = 1;
         }
 
         RETURN(rc);
 }
 
+/* for consistency, let's make the lov and the lov's
+ * osc's see the same cleanup flags as our mds */
+void mds_lov_set_cleanup_flags(struct obd_device *obd)
+{
+        struct mds_obd *mds = &obd->u.mds;
+        struct lov_obd *lov;
+
+        if (IS_ERR(mds->mds_osc_obd) || (mds->mds_osc_exp == NULL))
+                return;
+
+        lov = &mds->mds_osc_obd->u.lov;
+        mds->mds_osc_obd->obd_force = obd->obd_force;
+        mds->mds_osc_obd->obd_fail = obd->obd_fail;
+        if (lov->tgts) {
+                struct obd_export *osc_exp;
+                int i;
+                spin_lock(&lov->lov_lock);
+                for (i = 0; i < lov->desc.ld_tgt_count; i++) {
+                        if (lov->tgts[i].ltd_exp != NULL) {
+                                osc_exp = lov->tgts[i].ltd_exp;
+                                osc_exp->exp_obd->obd_force = obd->obd_force;
+                                osc_exp->exp_obd->obd_fail = obd->obd_fail;
+                        }
+                }
+                spin_unlock(&lov->lov_lock);
+        }
+}
+
 int mds_iocontrol(unsigned int cmd, struct obd_export *exp, int len,
                   void *karg, void *uarg)
 {
@@ -338,7 +360,7 @@ int mds_iocontrol(unsigned int cmd, struct obd_export *exp, int len,
                         RETURN(-EBUSY);
 
                 push_ctxt(&saved, &obd->obd_ctxt, NULL);
-                rc = llog_create(llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT), 
+                rc = llog_create(llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT),
                                  &mds->mds_cfg_llh, NULL, name);
                 if (rc == 0) {
                         llog_init_handle(mds->mds_cfg_llh, LLOG_F_IS_PLAIN,
@@ -412,6 +434,12 @@ int mds_iocontrol(unsigned int cmd, struct obd_export *exp, int len,
                 RETURN(rc);
         }
 
+        case OBD_IOC_SYNC: {
+                CDEBUG(D_HA, "syncing mds %s\n", obd->obd_name);
+                rc = fsfilt_sync(obd, obd->u.mds.mds_sb);
+                RETURN(rc);
+        }
+
         case OBD_IOC_SET_READONLY: {
                 void *handle;
                 struct inode *inode = obd->u.mds.mds_sb->s_root->d_inode;
@@ -420,10 +448,13 @@ int mds_iocontrol(unsigned int cmd, struct obd_export *exp, int len,
                        ll_bdevname(obd->u.mds.mds_sb, tmp));
 
                 handle = fsfilt_start(obd, inode, FSFILT_OP_MKNOD, NULL);
-                LASSERT(handle);
-                rc = fsfilt_commit(obd, inode, handle, 1);
+                if (!IS_ERR(handle))
+                        rc = fsfilt_commit(obd, inode, handle, 1);
+
+                CDEBUG(D_HA, "syncing mds %s\n", obd->obd_name);
+                rc = fsfilt_sync(obd, obd->u.mds.mds_sb);
 
-                dev_set_rdonly(ll_sbdev(obd->u.mds.mds_sb), 2);
+                ll_set_rdonly(ll_sbdev(obd->u.mds.mds_sb));
                 RETURN(0);
         }
 
@@ -504,7 +535,7 @@ int mds_lov_synchronize(void *data)
         LASSERT(obd != NULL);
         LASSERT(uuid != NULL);
 
-        rc = obd_set_info(obd->u.mds.mds_osc_exp, strlen("mds_conn"), 
+        rc = obd_set_info(obd->u.mds.mds_osc_exp, strlen("mds_conn"),
                           "mds_conn", 0, uuid);
         if (rc != 0)
                 RETURN(rc);
@@ -513,7 +544,7 @@ int mds_lov_synchronize(void *data)
                           obd->u.mds.mds_lov_desc.ld_tgt_count,
                           NULL, NULL, uuid);
         if (rc != 0) {
-                CERROR("%s: failed at llog_origin_connect: %d\n", 
+                CERROR("%s: failed at llog_origin_connect: %d\n",
                        obd->obd_name, rc);
                 RETURN(rc);
         }
@@ -522,7 +553,7 @@ int mds_lov_synchronize(void *data)
               obd->obd_name, uuid->uuid);
         rc = mds_lov_clearorphans(&obd->u.mds, uuid);
         if (rc != 0) {
-                CERROR("%s: failed at mds_lov_clearorphans: %d\n", 
+                CERROR("%s: failed at mds_lov_clearorphans: %d\n",
                        obd->obd_name, rc);
                 RETURN(rc);
         }
@@ -546,10 +577,10 @@ int mds_lov_start_synchronize(struct obd_device *obd, struct obd_uuid *uuid)
 
         rc = kernel_thread(mds_lov_synchronize, mlsi, CLONE_VM | CLONE_FILES);
         if (rc < 0)
-                CERROR("%s: error starting mds_lov_synchronize: %d\n", 
+                CERROR("%s: error starting mds_lov_synchronize: %d\n",
                        obd->obd_name, rc);
         else {
-                CDEBUG(D_HA, "%s: mds_lov_synchronize thread: %d\n", 
+                CDEBUG(D_HA, "%s: mds_lov_synchronize thread: %d\n",
                        obd->obd_name, rc);
                 rc = 0;
         }
index 3f4e67e..98ade8a 100644 (file)
@@ -326,7 +326,11 @@ static int mds_create_objects(struct ptlrpc_request *req, int offset,
 
         /* replay case */
         if (lustre_msg_get_flags(req->rq_reqmsg) & MSG_REPLAY) {
-                LASSERT (rec->ur_fid2->id);
+                if (rec->ur_fid2->id == 0) {
+                        DEBUG_REQ(D_ERROR, req, "fid2 not set on open replay");
+                        RETURN(-EFAULT);
+                }
+
                 body->valid |= OBD_MD_FLBLKSZ | OBD_MD_FLEASIZE;
                 lmm_size = rec->ur_eadatalen;
                 lmm = rec->ur_eadata;
@@ -828,11 +832,17 @@ int mds_open(struct mds_update_record *rec, int offset,
                                      rec, rep);
                 if (rc != -ENOENT)
                         RETURN(rc);
+
                 /* We didn't find the correct inode on disk either, so we
                  * need to re-create it via a regular replay. */
-                LASSERT(rec->ur_flags & MDS_OPEN_CREAT);
-        } else {
-                LASSERT(!rec->ur_fid2->id);
+                if (!(rec->ur_flags & MDS_OPEN_CREAT)) {
+                        DEBUG_REQ(D_ERROR, req,"OPEN_CREAT not in open replay");
+                        RETURN(-EFAULT);
+                }
+        } else if (rec->ur_fid2->id) {
+                DEBUG_REQ(D_ERROR, req, "fid2 "LPU64"/%u on open non-replay",
+                          rec->ur_fid2->id, rec->ur_fid2->generation);
+                RETURN(-EFAULT);
         }
 
         LASSERT(offset == 2); /* If we got here, we must be called via intent */
@@ -851,8 +861,15 @@ int mds_open(struct mds_update_record *rec, int offset,
                                         rec->ur_namelen - 1);
         if (IS_ERR(dparent)) {
                 rc = PTR_ERR(dparent);
-                if (rc != -ENOENT)
-                        CERROR("parent lookup error %d\n", rc);
+                if (rc != -ENOENT) {
+                        CERROR("parent "LPU64"/%u lookup error %d\n",
+                               rec->ur_fid1->id, rec->ur_fid1->generation, rc);
+                } else {
+                        /* Just cannot find parent - make it look like
+                         * usual negative lookup to avoid extra MDS RPC */
+                        intent_set_disposition(rep, DISP_LOOKUP_EXECD);
+                        intent_set_disposition(rep, DISP_LOOKUP_NEG);
+                }
                 GOTO(cleanup, rc);
         }
         LASSERT(dparent->d_inode != NULL);
index f4813a2..150948c 100644 (file)
@@ -88,8 +88,8 @@ int proc_version;
 /* The following are visible and mutable through /proc/sys/lustre/. */
 unsigned int obd_fail_loc;
 unsigned int obd_dump_on_timeout;
-unsigned int obd_timeout = 100;
-unsigned int ldlm_timeout = 6;
+unsigned int obd_timeout = 100; /* seconds */
+unsigned int ldlm_timeout = 6;  /* seconds */
 char obd_lustre_upcall[128] = "DEFAULT"; /* or NONE or /full/path/to/upcall  */
 unsigned int obd_sync_filter; /* = 0, don't sync by default */
 
@@ -646,7 +646,7 @@ static void cleanup_obdclass(void)
  * kernel patch */
 #include <linux/lustre_version.h>
 #define LUSTRE_MIN_VERSION 32
-#define LUSTRE_MAX_VERSION 44
+#define LUSTRE_MAX_VERSION 45
 #if (LUSTRE_KERNEL_VERSION < LUSTRE_MIN_VERSION)
 # error Cannot continue: Your Lustre kernel patch is older than the sources
 #elif (LUSTRE_KERNEL_VERSION > LUSTRE_MAX_VERSION)
index 662a03b..4cb163d 100644 (file)
@@ -213,9 +213,10 @@ void class_release_dev(struct obd_device *obd)
         int minor = obd->obd_minor;
 
         spin_lock(&obd_dev_lock);
+        memset(obd, 0x5a, sizeof(*obd));
         obd->obd_type = NULL;
-        //memset(obd, 0, sizeof(*obd));
         obd->obd_minor = minor;
+        obd->obd_name = NULL;
         spin_unlock(&obd_dev_lock);
 }
 
@@ -460,10 +461,7 @@ void __class_export_put(struct obd_export *exp)
                 obd_destroy_export(exp);
 
                 OBD_FREE(exp, sizeof(*exp));
-                if (obd->obd_set_up) {
-                        atomic_dec(&obd->obd_refcount);
-                        wake_up(&obd->obd_refcount_waitq);
-                }
+                class_decref(obd);
         }
 }
 
@@ -625,7 +623,7 @@ int class_connect(struct lustre_handle *conn, struct obd_device *obd,
  * hash entry and one for the export pointer passed in.  The export
  * pointer passed to this function is destroyed should not be used
  * again. */
-int class_disconnect(struct obd_export *export, int flags)
+int class_disconnect(struct obd_export *export)
 {
         ENTRY;
 
@@ -661,6 +659,7 @@ static void  class_disconnect_export_list(struct list_head *list, int flags)
         while(!list_empty(list)) {
                 exp = list_entry(list->next, struct obd_export, exp_obd_chain);
                 class_export_get(exp);
+                exp->exp_flags = flags;
 
                 if (obd_uuid_equals(&exp->exp_client_uuid,
                                     &exp->exp_obd->obd_uuid)) {
@@ -680,7 +679,8 @@ static void  class_disconnect_export_list(struct list_head *list, int flags)
                         class_export_put(exp);
                         continue;
                 }
-                rc = obd_disconnect(fake_exp, flags);
+                fake_exp->exp_flags = flags;
+                rc = obd_disconnect(fake_exp);
                 class_export_put(exp);
                 if (rc) {
                         CDEBUG(D_HA, "disconnecting export %p failed: %d\n",
@@ -692,7 +692,13 @@ static void  class_disconnect_export_list(struct list_head *list, int flags)
         EXIT;
 }
 
-void class_disconnect_exports(struct obd_device *obd, int flags)
+static inline int get_exp_flags_from_obd(struct obd_device *obd)
+{
+        return ((obd->obd_fail ? OBD_OPT_FAILOVER : 0) |
+                (obd->obd_force ? OBD_OPT_FORCE : 0));
+}
+
+void class_disconnect_exports(struct obd_device *obd)
 {
         struct list_head work_list;
         ENTRY;
@@ -705,13 +711,13 @@ void class_disconnect_exports(struct obd_device *obd, int flags)
 
         CDEBUG(D_HA, "OBD device %d (%p) has exports, "
                "disconnecting them\n", obd->obd_minor, obd);
-        class_disconnect_export_list(&work_list, flags);
+        class_disconnect_export_list(&work_list, get_exp_flags_from_obd(obd));
         EXIT;
 }
 
 /* Remove exports that have not completed recovery.
  */
-void class_disconnect_stale_exports(struct obd_device *obd, int flags)
+void class_disconnect_stale_exports(struct obd_device *obd)
 {
         struct list_head work_list;
         struct list_head *pos, *n;
@@ -733,7 +739,7 @@ void class_disconnect_stale_exports(struct obd_device *obd, int flags)
 
         CDEBUG(D_ERROR, "%s: disconnecting %d stale clients\n", 
                obd->obd_name, cnt);
-        class_disconnect_export_list(&work_list, flags);
+        class_disconnect_export_list(&work_list, get_exp_flags_from_obd(obd));
         EXIT;
 }
 
index cdbcce8..c22316c 100644 (file)
@@ -42,15 +42,13 @@ int llog_setup(struct obd_device *obd, int index, struct obd_device *disk_obd,
 
         obd->obd_llog_ctxt[index] = ctxt;
         ctxt->loc_obd = obd;
-        ctxt->loc_exp = class_export_get(disk_obd->obd_self_export);
+        ctxt->loc_exp = disk_obd->obd_self_export;
         ctxt->loc_idx = index;
         ctxt->loc_logops = op;
         sema_init(&ctxt->loc_sem, 1);
 
         if (op->lop_setup)
                 rc = op->lop_setup(obd, index, disk_obd, count, logid);
-        if (ctxt && rc)
-                OBD_FREE(ctxt, sizeof(*ctxt));
 
         RETURN(rc);
 }
@@ -61,13 +59,15 @@ int llog_cleanup(struct llog_ctxt *ctxt)
         int rc = 0;
         ENTRY;
 
-        LASSERT(ctxt);
-
+        if (!ctxt) {
+                CERROR("No ctxt\n");
+                RETURN(-ENODEV);
+        }
+        
         if (CTXTP(ctxt, cleanup))
                 rc = CTXTP(ctxt, cleanup)(ctxt);
 
         ctxt->loc_obd->obd_llog_ctxt[ctxt->loc_idx] = NULL;
-        class_export_put(ctxt->loc_exp);
         ctxt->loc_exp = NULL;
         OBD_FREE(ctxt, sizeof(*ctxt));
 
@@ -97,7 +97,11 @@ int llog_add(struct llog_ctxt *ctxt, struct llog_rec_hdr *rec,
         int rc;
         ENTRY;
 
-        LASSERT(ctxt);
+        if (!ctxt) {
+                CERROR("No ctxt\n");
+                RETURN(-ENODEV);
+        }
+        
         CTXT_CHECK_OP(ctxt, add, -EOPNOTSUPP);
 
         rc = CTXTP(ctxt, add)(ctxt, rec, lsm, logcookies, numcookies);
@@ -111,7 +115,11 @@ int llog_cancel(struct llog_ctxt *ctxt, struct lov_stripe_md *lsm,
         int rc;
         ENTRY;
 
-        LASSERT(ctxt);
+        if (!ctxt) {
+                CERROR("No ctxt\n");
+                RETURN(-ENODEV);
+        }
+        
         CTXT_CHECK_OP(ctxt, cancel, -EOPNOTSUPP);
         rc = CTXTP(ctxt, cancel)(ctxt, lsm, count, cookies, flags);
         RETURN(rc);
@@ -149,7 +157,6 @@ static int cat_cancel_cb(struct llog_handle *cathandle,
                 rc = llog_destroy(loghandle);
                 if (rc)
                         CERROR("failure destroying log in postsetup: %d\n", rc);
-                LASSERT(rc == 0);
 
                 index = loghandle->u.phd.phd_cookie.lgc_index;
                 llog_free_handle(loghandle);
@@ -225,7 +232,7 @@ int llog_obd_origin_cleanup(struct llog_ctxt *ctxt)
         ENTRY;
 
         if (!ctxt)
-                return 0;
+                RETURN(0);
 
         cathandle = ctxt->loc_handle;
         if (cathandle) {
@@ -240,7 +247,6 @@ int llog_obd_origin_cleanup(struct llog_ctxt *ctxt)
                                 if (rc)
                                         CERROR("failure destroying log during "
                                                "cleanup: %d\n", rc);
-                                LASSERT(rc == 0);
 
                                 index = loghandle->u.phd.phd_cookie.lgc_index;
                                 llog_free_handle(loghandle);
@@ -256,7 +262,7 @@ int llog_obd_origin_cleanup(struct llog_ctxt *ctxt)
                 }
                 llog_cat_put(ctxt->loc_handle);
         }
-        return 0;
+        RETURN(0);
 }
 EXPORT_SYMBOL(llog_obd_origin_cleanup);
 
index 88ac16c..5c8af06 100644 (file)
@@ -482,7 +482,7 @@ parse_out:
                 CERROR("6: llog_close failed: rc = %d\n", rc);
         }
 
-        rc = obd_disconnect(exp, 0);
+        rc = obd_disconnect(exp);
 
         RETURN(rc);
 }
@@ -602,7 +602,7 @@ static int llog_test_llog_finish(struct obd_device *obd, int count)
         RETURN(rc);
 }
 
-static int llog_test_cleanup(struct obd_device *obd, int flags)
+static int llog_test_cleanup(struct obd_device *obd)
 {
         int rc = obd_llog_finish(obd, 0);
         if (rc)
@@ -641,7 +641,7 @@ static int llog_test_setup(struct obd_device *obd, obd_count len, void *buf)
 
         rc = llog_run_tests(obd);
         if (rc)
-                llog_test_cleanup(obd, 0);
+                llog_test_cleanup(obd);
 
         lprocfs_init_vars(llog_test, &lvars);
         lprocfs_obd_setup(obd, lvars.obd_vars);
index 7a5d0c9..7b838e1 100644 (file)
@@ -192,6 +192,15 @@ int lprocfs_rd_u64(char *page, char **start, off_t off,
         return snprintf(page, count, LPU64"\n", *(__u64 *)data);
 }
 
+int lprocfs_rd_atomic(char *page, char **start, off_t off,
+                   int count, int *eof, void *data)
+{
+        atomic_t *atom = (atomic_t *)data;
+        LASSERT(atom != NULL);
+        *eof = 1;
+        return snprintf(page, count, "%d\n", atomic_read(atom));
+}
+
 int lprocfs_rd_uuid(char *page, char **start, off_t off, int count,
                     int *eof, void *data)
 {
@@ -873,6 +882,7 @@ EXPORT_SYMBOL(lprocfs_alloc_obd_stats);
 EXPORT_SYMBOL(lprocfs_free_obd_stats);
 
 EXPORT_SYMBOL(lprocfs_rd_u64);
+EXPORT_SYMBOL(lprocfs_rd_atomic);
 EXPORT_SYMBOL(lprocfs_rd_uuid);
 EXPORT_SYMBOL(lprocfs_rd_name);
 EXPORT_SYMBOL(lprocfs_rd_fstype);
index 4bb616d..cd04ae0 100644 (file)
@@ -112,7 +112,6 @@ int class_attach(struct lustre_cfg *lcfg)
         spin_lock_init(&obd->obd_dev_lock);
         spin_lock_init(&obd->obd_osfs_lock);
         obd->obd_osfs_age = jiffies - 1000 * HZ;
-        init_waitqueue_head(&obd->obd_refcount_waitq);
 
         /* XXX belongs in setup not attach  */
         /* recovery data */
@@ -140,6 +139,9 @@ int class_attach(struct lustre_cfg *lcfg)
                         GOTO(out, rc = -EINVAL);
         }
 
+        /* The attach is our first obd reference */
+        atomic_set(&obd->obd_refcount, 1);
+
         obd->obd_attached = 1;
         type->typ_refcnt++;
         CDEBUG(D_IOCTL, "OBD: dev %d attached type %s\n",
@@ -190,8 +192,6 @@ int class_setup(struct obd_device *obd, struct lustre_cfg *lcfg)
         obd->obd_starting = 1;  
         spin_unlock(&obd->obd_dev_lock);
 
-        atomic_set(&obd->obd_refcount, 0);
-
         exp = class_new_export(obd);
         if (exp == NULL)
                 RETURN(err);
@@ -206,19 +206,42 @@ int class_setup(struct obd_device *obd, struct lustre_cfg *lcfg)
 
         obd->obd_type->typ_refcnt++;
         obd->obd_set_up = 1;
-
+        CDEBUG(D_IOCTL, "finished setup of obd %s (uuid %s)\n",
+               obd->obd_name, obd->obd_uuid.uuid);
+        
         RETURN(0);
 
 err_exp:
         class_unlink_export(obd->obd_self_export);
         obd->obd_self_export = NULL;
+        obd->obd_starting = 0;
         RETURN(err);
 }
 
-int class_detach(struct obd_device *obd, struct lustre_cfg *lcfg)
+static int __class_detach(struct obd_device *obd)
 {
         int err = 0;
 
+        if (OBP(obd, detach)) 
+                err = OBP(obd,detach)(obd);
+        
+        if (obd->obd_name) {
+                OBD_FREE(obd->obd_name, strlen(obd->obd_name)+1);
+                obd->obd_name = NULL;
+        } else {
+                CERROR("device %d: no name at detach\n", obd->obd_minor);
+        }
+        
+        LASSERT(OBT(obd));
+        /* Attach took type refcount */
+        obd->obd_type->typ_refcnt--;
+        class_put_type(obd->obd_type);
+        class_release_dev(obd);
+        return (err);
+}
+
+int class_detach(struct obd_device *obd, struct lustre_cfg *lcfg)
+{
         ENTRY;
         if (obd->obd_set_up) {
                 CERROR("OBD device %d still set up\n", obd->obd_minor);
@@ -234,21 +257,11 @@ int class_detach(struct obd_device *obd, struct lustre_cfg *lcfg)
         obd->obd_attached = 0;
         spin_unlock(&obd->obd_dev_lock);
         
-        if (OBP(obd, detach))
-                err = OBP(obd,detach)(obd);
-
-        if (obd->obd_name) {
-                OBD_FREE(obd->obd_name, strlen(obd->obd_name)+1);
-                obd->obd_name = NULL;
-        } else {
-                CERROR("device %d: no name at detach\n", obd->obd_minor);
-        }
+        CDEBUG(D_IOCTL, "detach on obd %s (uuid %s)\n",
+               obd->obd_name, obd->obd_uuid.uuid);
 
-        LASSERT(OBT(obd));
-        obd->obd_type->typ_refcnt--;
-        class_put_type(obd->obd_type);
-        class_release_dev(obd);
-        RETURN(err);
+        class_decref(obd);
+        RETURN(0);
 }
 
 static void dump_exports(struct obd_device *obd)
@@ -267,7 +280,7 @@ static void dump_exports(struct obd_device *obd)
                         nreplies++;
                 }
 
-                CERROR("%s: %p %s %d %d %d: %p %s\n",
+                CDEBUG(D_IOCTL, "%s: %p %s %d %d %d: %p %s\n",
                        obd->obd_name, exp, exp->exp_client_uuid.uuid,
                        atomic_read(&exp->exp_refcount),
                        exp->exp_failed, nreplies, first_reply,
@@ -277,11 +290,12 @@ static void dump_exports(struct obd_device *obd)
 
 int class_cleanup(struct obd_device *obd, struct lustre_cfg *lcfg)
 {
-        int flags = 0;
         int err = 0;
         char *flag;
 
         ENTRY;
+        OBD_RACE(OBD_FAIL_LDLM_RECOV_CLIENTS);
+
         if (!obd->obd_set_up) {
                 CERROR("Device %d not setup\n", obd->obd_minor);
                 RETURN(-ENODEV);
@@ -301,78 +315,83 @@ int class_cleanup(struct obd_device *obd, struct lustre_cfg *lcfg)
                 for (flag = lcfg->lcfg_inlbuf1; *flag != 0; flag++)
                         switch (*flag) {
                         case 'F':
-                                flags |= OBD_OPT_FORCE;
+                                obd->obd_force = 1;
                                 break;
                         case 'A':
-                                flags |= OBD_OPT_FAILOVER;
+                                obd->obd_fail = 1;
+                                obd->obd_no_transno = 1;
+                                LCONSOLE_WARN("Failing %s by user command\n",
+                                       obd->obd_name);
+                                /* Set the obd readonly if we can */
+                                if (OBP(obd, iocontrol))
+                                        obd_iocontrol(OBD_IOC_SET_READONLY,
+                                                      obd->obd_self_export,
+                                                      0, NULL, NULL);
                                 break;
                         default:
                                 CERROR("unrecognised flag '%c'\n",
                                        *flag);
                         }
         }
-
-        /* The one reference that should be remaining is the
-         * obd_self_export */
-        if (atomic_read(&obd->obd_refcount) > 1) {
-                struct l_wait_info lwi = LWI_TIMEOUT_INTR(1 * HZ, NULL,
-                                                          NULL, NULL);
-                int rc;
-
-                if (!(flags & OBD_OPT_FORCE)) {
-                        CERROR("OBD device %d (%p) has refcount %d\n",
-                               obd->obd_minor, obd,
-                               atomic_read(&obd->obd_refcount));
+        
+        /* The two references that should be remaining are the
+         * obd_self_export and the attach reference. */
+        if (atomic_read(&obd->obd_refcount) > 2) {
+                if (!(obd->obd_fail || obd->obd_force)) {
+                        CERROR("OBD %s is still busy with %d references\n"
+                               "You should stop active file system users,"
+                               " or use the --force option to cleanup.\n",  
+                               obd->obd_name, atomic_read(&obd->obd_refcount));
                         dump_exports(obd);
                         GOTO(out, err = -EBUSY);
                 }
-                class_disconnect_exports(obd, flags);
-                CDEBUG(D_IOCTL,
-                       "%s: waiting for obd refs to go away: %d\n",
+                CDEBUG(D_IOCTL, "%s: forcing exports to disconnect: %d\n",
                        obd->obd_name, atomic_read(&obd->obd_refcount));
-
-                rc = l_wait_event(obd->obd_refcount_waitq,
-                                  atomic_read(&obd->obd_refcount) < 2, &lwi);
-                if (rc == 0) {
-                        LASSERT(atomic_read(&obd->obd_refcount) == 1);
-                } else {
-                        CERROR("wait cancelled cleaning anyway. "
-                               "refcount: %d\n",
-                               atomic_read(&obd->obd_refcount));
-                        dump_exports(obd);
-                }
-                CDEBUG(D_IOCTL, "%s: awake, now finishing cleanup\n",
-                       obd->obd_name);
+                dump_exports(obd);
+                class_disconnect_exports(obd);
         }
 
+        LASSERT(obd->obd_self_export);
         if (obd->obd_self_export) {
-                err = obd_precleanup(obd, flags);
-                if (err)
-                        GOTO(out, err);
-                class_unlink_export(obd->obd_self_export);
-                obd->obd_self_export = NULL;
-        }
-
-        err = obd_cleanup(obd, flags);
+               /* mds_precleanup will clean up the lov (and osc's)*/
+               err = obd_precleanup(obd);
+               if (err)
+                       GOTO(out, err);
+               obd->obd_self_export->exp_flags |= 
+                       (obd->obd_fail ? OBD_OPT_FAILOVER : 0) |
+                       (obd->obd_force ? OBD_OPT_FORCE : 0);
+               class_unlink_export(obd->obd_self_export);
+               obd->obd_self_export = NULL;
+        }
+
+        obd->obd_set_up = 0;
+        obd->obd_type->typ_refcnt--;
+        RETURN(0);
 out:
-        if (!err) {
-                obd->obd_set_up = 0;
-                obd->obd_type->typ_refcnt--;
-                /* XXX this should be an LASSERT */
-                if (atomic_read(&obd->obd_refcount) > 0)
-                        CERROR("%s still has refcount %d after "
-                               "cleanup.\n", obd->obd_name,
-                               atomic_read(&obd->obd_refcount));
-        } else {
-                /* Allow a failed cleanup to try again.  Note this may be
-                   unsafe, since we don't know where this one died. */
-                obd->obd_stopping = 0;
-        }
-
+        /* Allow a failed cleanup to try again. */
+        obd->obd_stopping = 0;
         RETURN(err);
-
 }
 
+void class_decref(struct obd_device *obd)
+{            
+        if (atomic_dec_and_test(&obd->obd_refcount)) {
+                int err;
+                CDEBUG(D_IOCTL, "finishing cleanup of obd %s (%s)\n",
+                       obd->obd_name, obd->obd_uuid.uuid);
+                LASSERT(!obd->obd_attached);
+                if (obd->obd_stopping) {
+                        /* If we're not stopping, we never set up */
+                        err = obd_cleanup(obd);
+                        if (err) 
+                                CERROR("Cleanup returned %d\n", err);
+                }
+                err = __class_detach(obd);
+                if (err) 
+                        CERROR("Detach returned %d\n", err);
+        }
+}               
+
 LIST_HEAD(lustre_profile_list);
 
 struct lustre_profile *class_get_profile(char * prof)
index b7fa894..e4704f2 100644 (file)
@@ -57,8 +57,26 @@ enum {
         OBD_LDLM_TIMEOUT,       /* LDLM timeout for ASTs before client eviction */
 };
 
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,8)
 int proc_fail_loc(ctl_table *table, int write, struct file *filp,
-                  void *buffer, size_t *lenp);
+                  void *buffer, size_t *lenp)
+#else
+int proc_fail_loc(ctl_table *table, int write, struct file *filp,
+                  void *buffer, size_t *lenp, loff_t *ppos)
+#endif
+{
+        int rc;
+        int old_fail_loc = obd_fail_loc;
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,8)
+        rc = proc_dointvec(table,write,filp,buffer,lenp);
+#else
+        rc = proc_dointvec(table,write,filp,buffer,lenp,ppos);
+#endif
+        if (old_fail_loc != obd_fail_loc)
+                wake_up(&obd_race_waitq);
+        return rc;
+}
 
 static ctl_table obd_table[] = {
         {OBD_FAIL_LOC, "fail_loc", &obd_fail_loc, sizeof(int), 0644, NULL,
@@ -100,15 +118,3 @@ void obd_sysctl_clean (void)
         obd_table_header = NULL;
 #endif
 }
-
-int proc_fail_loc(ctl_table *table, int write, struct file *filp,
-                  void *buffer, size_t *lenp)
-{
-        int rc;
-        int old_fail_loc = obd_fail_loc;
-
-        rc = proc_dointvec(table,write,filp,buffer,lenp);
-        if (old_fail_loc != obd_fail_loc)
-                wake_up(&obd_race_waitq);
-        return rc;
-}
index 3f12f12..63d8f99 100644 (file)
@@ -64,7 +64,7 @@ static int echo_connect(struct lustre_handle *conn, struct obd_device *obd,
         return class_connect(conn, obd, cluuid);
 }
 
-static int echo_disconnect(struct obd_export *exp, int flags)
+static int echo_disconnect(struct obd_export *exp)
 {
         unsigned long irqflags;
 
@@ -72,10 +72,6 @@ static int echo_disconnect(struct obd_export *exp, int flags)
 
         ldlm_cancel_locks_for_export(exp);
 
-        spin_lock_irqsave(&exp->exp_lock, irqflags);
-        exp->exp_flags = flags;
-        spin_unlock_irqrestore(&exp->exp_lock, irqflags);
-
         /* complete all outstanding replies */
         spin_lock_irqsave(&exp->exp_lock, irqflags);
         while (!list_empty(&exp->exp_outstanding_replies)) {
@@ -91,7 +87,7 @@ static int echo_disconnect(struct obd_export *exp, int flags)
         }
         spin_unlock_irqrestore(&exp->exp_lock, irqflags);
 
-        return class_disconnect(exp, flags);
+        return class_disconnect(exp);
 }
 
 static int echo_destroy_export(struct obd_export *exp)
@@ -502,7 +498,7 @@ static int echo_setup(struct obd_device *obd, obd_count len, void *buf)
         RETURN(0);
 }
 
-static int echo_cleanup(struct obd_device *obd, int flags)
+static int echo_cleanup(struct obd_device *obd)
 {
         int leaked;
         ENTRY;
@@ -517,7 +513,7 @@ static int echo_cleanup(struct obd_device *obd, int flags)
         set_current_state (TASK_UNINTERRUPTIBLE);
         schedule_timeout (HZ);
         
-        ldlm_namespace_free(obd->obd_namespace, flags & OBD_OPT_FORCE);
+        ldlm_namespace_free(obd->obd_namespace, obd->obd_force);
 
         leaked = atomic_read(&obd->u.echo.eo_prep);
         if (leaked != 0)
index 58d2358..fb67492 100644 (file)
@@ -1355,7 +1355,7 @@ echo_client_setup(struct obd_device *obddev, obd_count len, void *buf)
         RETURN(rc);
 }
 
-static int echo_client_cleanup(struct obd_device *obddev, int flags)
+static int echo_client_cleanup(struct obd_device *obddev)
 {
         struct list_head       *el;
         struct ec_object       *eco;
@@ -1379,7 +1379,7 @@ static int echo_client_cleanup(struct obd_device *obddev, int flags)
                 echo_put_object(eco);
         }
 
-        rc = obd_disconnect(ec->ec_exp, 0);
+        rc = obd_disconnect(ec->ec_exp);
         if (rc != 0)
                 CERROR("fail to disconnect device: %d\n", rc);
 
@@ -1402,7 +1402,7 @@ static int echo_client_connect(struct lustre_handle *conn,
         RETURN (rc);
 }
 
-static int echo_client_disconnect(struct obd_export *exp, int flags)
+static int echo_client_disconnect(struct obd_export *exp)
 {
         struct obd_device      *obd;
         struct echo_client_obd *ec;
@@ -1432,7 +1432,7 @@ static int echo_client_disconnect(struct obd_export *exp, int flags)
                 OBD_FREE (ecl, sizeof (*ecl));
         }
 
-        rc = class_disconnect(exp, 0);
+        rc = class_disconnect(exp);
         GOTO(out, rc);
  out:
         return rc;
index a93f1b2..d7fb733 100644 (file)
@@ -218,7 +218,7 @@ static int filter_client_add(struct obd_device *obd, struct filter_obd *filter,
         RETURN(0);
 }
 
-static int filter_client_free(struct obd_export *exp, int flags)
+static int filter_client_free(struct obd_export *exp)
 {
         struct filter_export_data *fed = &exp->exp_filter_data;
         struct filter_obd *filter = &exp->exp_obd->u.filter;
@@ -231,8 +231,8 @@ static int filter_client_free(struct obd_export *exp, int flags)
 
         if (fed->fed_fcd == NULL)
                 RETURN(0);
-
-        if (flags & OBD_OPT_FAILOVER)
+        
+        if (exp->exp_flags & OBD_OPT_FAILOVER)
                 GOTO(free, 0);
 
         /* XXX if fcd_uuid were a real obd_uuid, I could use obd_uuid_equals */
@@ -517,7 +517,7 @@ out:
         RETURN(0);
 
 err_client:
-        class_disconnect_exports(obd, 0);
+        class_disconnect_exports(obd);
 err_fsd:
         filter_free_server_data(filter);
         RETURN(rc);
@@ -1190,8 +1190,6 @@ int filter_common_setup(struct obd_device *obd, obd_count len, void *buf,
         int rc = 0;
         ENTRY;
 
-        dev_clear_rdonly(2);
-
         if (!lcfg->lcfg_inlbuf1 || !lcfg->lcfg_inlbuf2)
                 RETURN(-EINVAL);
 
@@ -1200,11 +1198,13 @@ int filter_common_setup(struct obd_device *obd, obd_count len, void *buf,
                 RETURN(PTR_ERR(obd->obd_fsops));
 
         mnt = do_kern_mount(lcfg->lcfg_inlbuf2, MS_NOATIME | MS_NODIRATIME,
-                            lcfg->lcfg_inlbuf1, option);
+                            lcfg->lcfg_inlbuf1, (void *)option);
         rc = PTR_ERR(mnt);
         if (IS_ERR(mnt))
                 GOTO(err_ops, rc);
 
+        LASSERT(!ll_check_rdonly(ll_sbdev(mnt->mnt_sb)));
+
         if (lcfg->lcfg_inllen3 > 0 && lcfg->lcfg_inlbuf3) {
                 if (*lcfg->lcfg_inlbuf3 == 'f') {
                         obd->obd_replayable = 1;
@@ -1337,29 +1337,36 @@ static int filter_setup(struct obd_device *obd, obd_count len, void *buf)
         return rc;
 }
 
-static int filter_cleanup(struct obd_device *obd, int flags)
+static int filter_precleanup(struct obd_device *obd)
+{
+        target_cleanup_recovery(obd);
+        return (0);
+}
+
+static int filter_cleanup(struct obd_device *obd)
 {
         struct filter_obd *filter = &obd->u.filter;
+        ll_sbdev_type save_dev;
         ENTRY;
-
-        if (flags & OBD_OPT_FAILOVER)
+        
+        if (obd->obd_fail)
                 CERROR("%s: shutting down for failover; client state will"
                        " be preserved.\n", obd->obd_name);
 
         if (!list_empty(&obd->obd_exports)) {
                 CERROR("%s: still has clients!\n", obd->obd_name);
-                class_disconnect_exports(obd, flags);
+                class_disconnect_exports(obd);
                 if (!list_empty(&obd->obd_exports)) {
                         CERROR("still has exports after forced cleanup?\n");
                         RETURN(-EBUSY);
                 }
         }
-        target_cleanup_recovery(obd);
 
-        ldlm_namespace_free(obd->obd_namespace, flags & OBD_OPT_FORCE);
+        ldlm_namespace_free(obd->obd_namespace, obd->obd_force);
 
         if (filter->fo_sb == NULL)
                 RETURN(0);
+        save_dev = ll_sbdev(filter->fo_sb);
 
         lprocfs_free_obd_stats(obd);
         lprocfs_obd_cleanup(obd);
@@ -1367,7 +1374,6 @@ static int filter_cleanup(struct obd_device *obd, int flags)
         filter_post(obd);
 
         shrink_dcache_parent(filter->fo_sb->s_root);
-        filter->fo_sb = 0;
 
         if (atomic_read(&filter->fo_vfsmnt->mnt_count) > 1)
                 CERROR("%s: mount point %p busy, mnt_count: %d\n",
@@ -1378,13 +1384,16 @@ static int filter_cleanup(struct obd_device *obd, int flags)
         mntput(filter->fo_vfsmnt);
         //destroy_buffers(filter->fo_sb->s_dev);
         filter->fo_sb = NULL;
+        
+        obd_llog_finish(obd, 0);
+
+        ll_clear_rdonly(save_dev);
+        
         fsfilt_put_ops(obd->obd_fsops);
         lock_kernel();
 
-        dev_clear_rdonly(2);
-
         LCONSOLE_INFO("OST %s has stopped.\n", obd->obd_name);
-
+        
         RETURN(0);
 }
 
@@ -1430,25 +1439,13 @@ cleanup:
         if (rc) {
                 if (fcd)
                         OBD_FREE(fcd, sizeof(*fcd));
-                class_disconnect(exp, 0);
+                class_disconnect(exp);
         } else {
                 class_export_put(exp);
         }
         return rc;
 }
 
-static int filter_precleanup(struct obd_device *obd, int flags)
-{
-        int rc = 0;
-        ENTRY;
-
-        rc = obd_llog_finish(obd, 0);
-        if (rc)
-                CERROR("failed to cleanup llogging subsystem\n");
-
-        RETURN(rc);
-}
-
 /* Do extra sanity checks for grant accounting.  We do this at connect,
  * disconnect, and statfs RPC time, so it shouldn't be too bad.  We can
  * always get rid of it or turn it off when we know accounting is good. */
@@ -1567,9 +1564,10 @@ static int filter_destroy_export(struct obd_export *exp)
         target_destroy_export(exp);
 
         if (exp->exp_obd->obd_replayable)
-                filter_client_free(exp, exp->exp_flags);
+                filter_client_free(exp);
 
         filter_grant_discard(exp);
+        
         if (!(exp->exp_flags & OBD_OPT_FORCE))
                 filter_grant_sanity_check(exp->exp_obd, __FUNCTION__);
 
@@ -1577,10 +1575,9 @@ static int filter_destroy_export(struct obd_export *exp)
 }
 
 /* also incredibly similar to mds_disconnect */
-static int filter_disconnect(struct obd_export *exp, int flags)
+static int filter_disconnect(struct obd_export *exp)
 {
         struct obd_device *obd = exp->exp_obd;
-        unsigned long irqflags;
         struct llog_ctxt *ctxt;
         int rc, err;
         ENTRY;
@@ -1588,16 +1585,12 @@ static int filter_disconnect(struct obd_export *exp, int flags)
         LASSERT(exp);
         class_export_get(exp);
 
-        spin_lock_irqsave(&exp->exp_lock, irqflags);
-        exp->exp_flags = flags;
-        spin_unlock_irqrestore(&exp->exp_lock, irqflags);
-
-        if (!(flags & OBD_OPT_FORCE))
+        if (!(exp->exp_flags & OBD_OPT_FORCE))
                 filter_grant_sanity_check(obd, __FUNCTION__);
         filter_grant_discard(exp);
 
         /* Disconnect early so that clients can't keep using export */
-        rc = class_disconnect(exp, flags);
+        rc = class_disconnect(exp);
 
         ldlm_cancel_locks_for_export(exp);
 
@@ -2393,10 +2386,17 @@ int filter_iocontrol(unsigned int cmd, struct obd_export *exp,
         int rc = 0;
 
         switch (cmd) {
-        case OBD_IOC_ABORT_RECOVERY:
+        case OBD_IOC_ABORT_RECOVERY: {
                 CERROR("aborting recovery for device %s\n", obd->obd_name);
                 target_abort_recovery(obd);
                 RETURN(0);
+        }
+
+        case OBD_IOC_SYNC: {
+                CDEBUG(D_HA, "syncing ost %s\n", obd->obd_name);
+                rc = fsfilt_sync(obd, obd->u.filter.fo_sb);
+                RETURN(rc);
+        }
 
         case OBD_IOC_SET_READONLY: {
                 void *handle;
@@ -2407,10 +2407,13 @@ int filter_iocontrol(unsigned int cmd, struct obd_export *exp,
                        ll_bdevname(sb, tmp));
 
                 handle = fsfilt_start(obd, inode, FSFILT_OP_MKNOD, NULL);
-                LASSERT(handle);
-                (void)fsfilt_commit(obd, inode, handle, 1);
+                if (!IS_ERR(handle)) 
+                        rc = fsfilt_commit(obd, inode, handle, 1);
+                
+                CDEBUG(D_HA, "syncing ost %s\n", obd->obd_name);
+                rc = fsfilt_sync(obd, obd->u.filter.fo_sb);
 
-                dev_set_rdonly(ll_sbdev(obd->u.filter.fo_sb), 2);
+                ll_set_rdonly(ll_sbdev(obd->u.filter.fo_sb));
                 RETURN(0);
         }
 
index f3cac9d..2681a46 100644 (file)
@@ -254,7 +254,7 @@ static int osc_setattr(struct obd_export *exp, struct obdo *oa,
         request = ptlrpc_prep_req(class_exp2cliimp(exp), OST_SETATTR, 1, &size,
                                   NULL);
         if (!request)
-               RETURN(-ENOMEM);
+                RETURN(-ENOMEM);
 
         body = lustre_msg_buf(request->rq_reqmsg, 0, sizeof(*body));
         memcpy(&body->oa, oa, sizeof(*oa));
@@ -2725,10 +2725,10 @@ static int osc_iocontrol(unsigned int cmd, struct obd_export *exp, int len,
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0))
         MOD_INC_USE_COUNT;
 #else
-       if (!try_module_get(THIS_MODULE)) {
-               CERROR("Can't get module. Is it alive?");
-               return -EINVAL;
-       }
+        if (!try_module_get(THIS_MODULE)) {
+                CERROR("Can't get module. Is it alive?");
+                return -EINVAL;
+        }
 #endif
         switch (cmd) {
         case OBD_IOC_LOV_GET_CONFIG: {
@@ -2796,7 +2796,7 @@ out:
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0))
         MOD_DEC_USE_COUNT;
 #else
-       module_put(THIS_MODULE);
+        module_put(THIS_MODULE);
 #endif
         return err;
 }
@@ -2858,7 +2858,7 @@ static int osc_set_info(struct obd_export *exp, obd_count keylen,
             memcmp(key, "next_id", strlen("next_id")) == 0) {
                 if (vallen != sizeof(obd_id))
                         RETURN(-EINVAL);
-               obd->u.cli.cl_oscc.oscc_next_id = *((obd_id*)val) + 1;
+                obd->u.cli.cl_oscc.oscc_next_id = *((obd_id*)val) + 1;
                 CDEBUG(D_HA, "%s: set oscc_next_id = "LPU64"\n",
                        exp->exp_obd->obd_name,
                        obd->u.cli.cl_oscc.oscc_next_id);
@@ -2870,7 +2870,7 @@ static int osc_set_info(struct obd_export *exp, obd_count keylen,
             memcmp(key, "growth_count", strlen("growth_count")) == 0) {
                 if (vallen != sizeof(int))
                         RETURN(-EINVAL);
-               obd->u.cli.cl_oscc.oscc_grow_count = *((int*)val);
+                obd->u.cli.cl_oscc.oscc_grow_count = *((int*)val);
                 RETURN(0);
         }
 
@@ -2955,14 +2955,20 @@ static int osc_llog_init(struct obd_device *obd, struct obd_device *tgt,
 
 static int osc_llog_finish(struct obd_device *obd, int count)
 {
-        int rc;
+        struct llog_ctxt *ctxt;
+        int rc = 0;
         ENTRY;
 
-        rc = llog_cleanup(llog_get_context(obd, LLOG_UNLINK_ORIG_CTXT));
+        ctxt = llog_get_context(obd, LLOG_UNLINK_ORIG_CTXT);
+        if (ctxt) 
+                rc = llog_cleanup(ctxt);
         if (rc)
                 RETURN(rc);
+        
+        ctxt = llog_get_context(obd, LLOG_SIZE_REPL_CTXT);
+        if (ctxt) 
+                rc = llog_cleanup(ctxt);
 
-        rc = llog_cleanup(llog_get_context(obd, LLOG_SIZE_REPL_CTXT));
         RETURN(rc);
 }
 
@@ -2977,7 +2983,7 @@ static int osc_connect(struct lustre_handle *exph,
         return rc;
 }
 
-static int osc_disconnect(struct obd_export *exp, int flags)
+static int osc_disconnect(struct obd_export *exp)
 {
         struct obd_device *obd = class_exp2obd(exp);
         struct llog_ctxt *ctxt = llog_get_context(obd, LLOG_SIZE_REPL_CTXT);
@@ -2987,7 +2993,7 @@ static int osc_disconnect(struct obd_export *exp, int flags)
                 /* flush any remaining cancel messages out to the target */
                 llog_sync(ctxt, exp);
 
-        rc = client_disconnect_export(exp, flags);
+        rc = client_disconnect_export(exp);
         return rc;
 }
 
@@ -3080,7 +3086,7 @@ int osc_setup(struct obd_device *obd, obd_count len, void *buf)
         RETURN(rc);
 }
 
-int osc_cleanup(struct obd_device *obd, int flags)
+int osc_cleanup(struct obd_device *obd)
 {
         struct osc_creator *oscc = &obd->u.cli.cl_oscc;
         int rc;
@@ -3093,8 +3099,9 @@ int osc_cleanup(struct obd_device *obd, int flags)
         oscc->oscc_flags |= OSCC_FLAG_EXITING;
         spin_unlock(&oscc->oscc_lock);
 
-        rc = client_obd_cleanup(obd, flags);
+        rc = client_obd_cleanup(obd);
         ptlrpcd_decref();
+        obd_llog_finish(obd, 0);
         RETURN(rc);
 }
 
index ae67814..44d4467 100644 (file)
@@ -1182,7 +1182,7 @@ out_lprocfs:
         RETURN(rc);
 }
 
-static int ost_cleanup(struct obd_device *obd, int flags)
+static int ost_cleanup(struct obd_device *obd)
 {
         struct ost_obd *ost = &obd->u.ost;
         int err = 0;
index e5ed15f..96901f1 100644 (file)
@@ -210,7 +210,8 @@ struct ptlrpc_request *ptlrpc_prep_req(struct obd_import *imp, int opcode,
         request->rq_send_state = LUSTRE_IMP_FULL;
         request->rq_type = PTL_RPC_MSG_REQUEST;
         request->rq_import = class_import_get(imp);
-
+        request->rq_export = NULL;
+        
         request->rq_req_cbid.cbid_fn  = request_out_callback;
         request->rq_req_cbid.cbid_arg = request;
 
@@ -486,7 +487,7 @@ static int after_reply(struct ptlrpc_request *req)
         /* Either we've been evicted, or the server has failed for
          * some reason. Try to reconnect, and if that fails, punt to the
          * upcall. */
-        if (rc == -ENOTCONN) {
+        if ((rc == -ENOTCONN) || (rc == -ENODEV)) {
                 if (req->rq_send_state != LUSTRE_IMP_FULL ||
                     imp->imp_obd->obd_no_recov || imp->imp_dlm_fake) {
                         RETURN(-ENOTCONN);
index 637e546..ee2257e 100644 (file)
@@ -322,8 +322,17 @@ int ptlrpc_send_reply (struct ptlrpc_request *req, int may_be_difficult)
         LASSERT (req->rq_repmsg == &rs->rs_msg);
         LASSERT (rs->rs_cb_id.cbid_fn == reply_out_callback);
         LASSERT (rs->rs_cb_id.cbid_arg == rs);
-
         LASSERT (req->rq_repmsg != NULL);
+
+        if (req->rq_export && req->rq_export->exp_obd &&
+            req->rq_export->exp_obd->obd_fail) {
+                /* Failed obd's only send ENODEV */
+                req->rq_type = PTL_RPC_MSG_ERR;
+                req->rq_status = -ENODEV;
+                CDEBUG(D_HA, "sending ENODEV from failed obd %d\n",
+                       req->rq_export->exp_obd->obd_minor);
+        }
+
         if (req->rq_type != PTL_RPC_MSG_ERR)
                 req->rq_type = PTL_RPC_MSG_REPLY;
 
@@ -389,6 +398,15 @@ int ptl_send_rpc(struct ptlrpc_request *request)
          * cleanly from the previous attempt */
         LASSERT (!request->rq_receiving_reply);
 
+        if (request->rq_import->imp_obd &&
+            request->rq_import->imp_obd->obd_fail) {
+                CDEBUG(D_HA, "muting rpc for failed imp obd %s\n",
+                       request->rq_import->imp_obd->obd_name);
+                /* this prevents us from waiting in ptlrpc_queue_wait */
+                request->rq_err = 1;
+                RETURN(-ENODEV);
+        }
+
         connection = request->rq_import->imp_connection;
 
         if (request->rq_bulk != NULL) {
index 299fc34..05172e2 100644 (file)
@@ -64,6 +64,11 @@ int ptlrpc_ping(struct obd_import *imp)
         RETURN(rc);
 }
 
+static inline void ptlrpc_update_next_ping(struct obd_import *imp)
+{
+        imp->imp_next_ping = jiffies + obd_timeout * HZ;
+}
+
 #ifdef __KERNEL__
 static int ptlrpc_pinger_main(void *arg)
 {
@@ -114,13 +119,13 @@ static int ptlrpc_pinger_main(void *arg)
                                 imp->imp_force_verify = 0;
                         spin_unlock_irqrestore(&imp->imp_lock, flags);
 
-                        if (imp->imp_next_ping <= this_ping || force) {
+                        if (force ||
+                            time_after_eq(this_ping, imp->imp_next_ping)) {
                                 if (level == LUSTRE_IMP_DISCON &&
                                     !imp->imp_deactive) {
                                         /* wait at least a timeout before
                                            trying recovery again. */
-                                        imp->imp_next_ping = jiffies +
-                                                (obd_timeout * HZ);
+                                        ptlrpc_update_next_ping(imp);
                                         ptlrpc_initiate_recovery(imp);
                                 }
                                 else if (level != LUSTRE_IMP_FULL ||
@@ -135,20 +140,25 @@ static int ptlrpc_pinger_main(void *arg)
                                         ptlrpc_ping(imp);
                                 }
 
-                        } else {
-                                if (imp->imp_pingable)
-                                        CDEBUG(D_HA, "don't need to ping %s "
-                                               "(%lu > %lu)\n",
-                                               imp->imp_target_uuid.uuid,
-                                               imp->imp_next_ping, this_ping);
+                        } else if (!imp->imp_pingable) {
+                                continue;
                         }
+
+                        CDEBUG(D_HA, "don't need to ping %s (%lu > %lu)\n",
+                               imp->imp_target_uuid.uuid,
+                               imp->imp_next_ping, this_ping);
+
+                        /* obd_timeout might have changed */
+                        if (time_after(imp->imp_next_ping,
+                                       this_ping + obd_timeout * HZ))
+                                ptlrpc_update_next_ping(imp);
                 }
                 up(&pinger_sem);
 
                 /* Wait until the next ping time, or until we're stopped. */
                 time_to_next_ping = this_ping + (obd_timeout * HZ) - jiffies;
                 CDEBUG(D_HA, "next ping in %lu (%lu)\n", time_to_next_ping,
-                       this_ping + (obd_timeout * HZ));
+                       this_ping + obd_timeout * HZ);
                 if (time_to_next_ping > 0) {
                         lwi = LWI_TIMEOUT(time_to_next_ping, NULL, NULL);
                         l_wait_event(thread->t_ctl_waitq,
@@ -235,7 +245,7 @@ int ptlrpc_stop_pinger(void)
 
 void ptlrpc_pinger_sending_on_import(struct obd_import *imp)
 {
-        imp->imp_next_ping = jiffies + (obd_timeout * HZ);
+        ptlrpc_update_next_ping(imp);
 }
 
 int ptlrpc_pinger_add_import(struct obd_import *imp)
@@ -247,7 +257,7 @@ int ptlrpc_pinger_add_import(struct obd_import *imp)
         down(&pinger_sem);
         CDEBUG(D_HA, "adding pingable import %s->%s\n",
                imp->imp_obd->obd_uuid.uuid, imp->imp_target_uuid.uuid);
-        imp->imp_next_ping = jiffies + (obd_timeout * HZ);
+        ptlrpc_update_next_ping(imp);
         /* XXX sort, blah blah */
         list_add_tail(&imp->imp_pinger_chain, &pinger_imports);
         class_import_get(imp);
@@ -289,14 +299,14 @@ void ptlrpc_pinger_wake_up()
 
 static struct pinger_data {
         int             pd_recursion;
-        unsigned long   pd_this_ping;
-        unsigned long   pd_next_ping;
+        unsigned long   pd_this_ping;   /* jiffies */
+        unsigned long   pd_next_ping;   /* jiffies */
         struct ptlrpc_request_set *pd_set;
 } pinger_args;
 
 static int pinger_check_rpcs(void *arg)
 {
-        unsigned long curtime = time(NULL);
+        unsigned long curtime = jiffies;
         struct ptlrpc_request *req;
         struct ptlrpc_request_set *set;
         struct list_head *iter;
@@ -312,7 +322,7 @@ static int pinger_check_rpcs(void *arg)
         }
 
         /* have we reached ping point? */
-        if (!pd->pd_set && pd->pd_next_ping > curtime) {
+        if (!pd->pd_set && time_before(curtime, pd->pd_next_ping)) {
                 pd->pd_recursion--;
                 return 0;
         }
@@ -332,12 +342,11 @@ static int pinger_check_rpcs(void *arg)
         down(&pinger_sem);
         list_for_each(iter, &pinger_imports) {
                 struct obd_import *imp =
-                        list_entry(iter, struct obd_import,
-                                   imp_pinger_chain);
+                        list_entry(iter, struct obd_import, imp_pinger_chain);
                 int generation, level;
                 unsigned long flags;
 
-                if (imp->imp_next_ping <= pd->pd_this_ping) {
+                if (time_after_eq(pd->pd_this_ping, imp->imp_next_ping)) {
                         /* Add a ping. */
                         spin_lock_irqsave(&imp->imp_lock, flags);
                         generation = imp->imp_generation;
@@ -390,7 +399,7 @@ do_check_set:
         rc = ptlrpc_check_set(set);
 
         /* not finished, and we are not expired, simply return */
-        if (!rc && curtime < pd->pd_this_ping + obd_timeout) {
+        if (!rc && time_before(curtime, pd->pd_this_ping + obd_timeout * HZ)) {
                 CDEBUG(D_HA, "not finished, but also not expired\n");
                 pd->pd_recursion--;
                 return 0;
@@ -421,7 +430,7 @@ do_check_set:
         ptlrpc_set_destroy(set);
         pd->pd_set = NULL;
 
-        pd->pd_next_ping = pd->pd_this_ping + obd_timeout;
+        pd->pd_next_ping = pd->pd_this_ping + obd_timeout * HZ;
         pd->pd_this_ping = 0; /* XXX for debug */
 
         CDEBUG(D_HA, "finished a round ping\n");
@@ -453,11 +462,11 @@ int ptlrpc_stop_pinger(void)
 void ptlrpc_pinger_sending_on_import(struct obd_import *imp)
 {
         down(&pinger_sem);
-        imp->imp_next_ping = time(NULL) + obd_timeout;
+        ptlrpc_update_next_ping(imp);
         if (pinger_args.pd_set == NULL &&
-            pinger_args.pd_next_ping > imp->imp_next_ping) {
+            time_before(imp->imp_next_ping, pinger_args.pd_next_ping)) {
                 CDEBUG(D_HA, "set next ping to %ld(cur %ld)\n",
-                        imp->imp_next_ping, time(NULL));
+                        imp->imp_next_ping, jiffies);
                 pinger_args.pd_next_ping = imp->imp_next_ping;
         }
         up(&pinger_sem);
index 8fe7108..1b264ce 100644 (file)
@@ -418,7 +418,7 @@ void ptlrpc_fail_export(struct obd_export *exp)
          * (request, for example) in addition to the one from the hash table.
          * We don't have such a reference here, so make one. */
         class_export_get(exp);
-        rc = obd_disconnect(exp, 0);
+        rc = obd_disconnect(exp);
         if (rc)
                 CERROR("disconnecting export %p failed: %d\n", exp, rc);
 }
index 5cd30eb..5f837e4 100644 (file)
@@ -516,6 +516,16 @@ ptlrpc_server_handle_request (struct ptlrpc_service *svc)
                                   request->rq_export->exp_conn_cnt);
                         goto put_conn;
                 }
+                if (request->rq_export->exp_obd
+                    && request->rq_export->exp_obd->obd_fail) {
+                        /* Failing over, don't handle any more reqs, send
+                           error response instead. */
+                        CDEBUG(D_HA, "Dropping req %p for failed obd %s\n",
+                               request, request->rq_export->exp_obd->obd_name);
+                        request->rq_status = -ENODEV;
+                        ptlrpc_error(request);
+                        goto put_conn;
+                }
 
                 request->rq_export->exp_last_request_time = CURRENT_SECONDS;
         }
index 96f9e7d..e3ebe1d 100644 (file)
@@ -24,7 +24,7 @@ noinst_PROGRAMS += wantedi statone runas openfile getdents o_directory
 noinst_PROGRAMS += small_write multiop sleeptest ll_sparseness_verify cmknod
 noinst_PROGRAMS += ll_sparseness_write mrename ll_dirstripe_verify mkdirmany rmdirmany
 noinst_PROGRAMS += openfilleddirunlink rename_many memhog iopentest1 iopentest2
-noinst_PROGRAMS += mmap_sanity
+noinst_PROGRAMS += mmap_sanity writemany
 if MPITESTS
 noinst_PROGRAMS += write_append_truncate createmany_mpi
 endif
index de01e97..7e9181e 100644 (file)
@@ -11,7 +11,8 @@ host-progs := openunlink testreq truncate directio openme writeme \
                stat createmany statmany multifstat createtest mlink \
                opendirunlink opendevunlink unlinkmany fchdir_test \
                checkstat wantedi statone runas openfile \
-               mcreate mkdirmany utime o_directory small_write multiop
+               mcreate mkdirmany utime o_directory small_write multiop \
+               writemany 
 
 always := $(host-progs) 
 
@@ -50,3 +51,5 @@ utime-objs :=utime.o
 o_directory-objs :=o_directory.o
 small_write-objs :=small_write.o
 multiop-objs :=multiop.o
+writemany-objs := writemany.o
+
index 2ca1485..f39bd8f 100644 (file)
@@ -3,7 +3,7 @@ mdsfailover_HOST=${mdsfailover_HOST:-""}
 ost1_HOST=${ost1_HOST:-"`hostname`"}
 ost2_HOST=${ost2_HOST:-"`hostname`"}
 EXTRA_OSTS=${EXTRA_OSTS:-"`hostname`"}
-client_HOST="'*'"
+client_HOST=${client_HOST:-"'*'"}
 LIVE_CLIENT=${LIVE_CLIENT:-"`hostname`"}
 # This should always be a list, not a regexp
 FAIL_CLIENTS=${FAIL_CLIENTS:-""}
index d97d094..5812c97 100755 (executable)
@@ -34,14 +34,20 @@ ${LMC} --add net --node  localhost --nid `hostname` --nettype $NETTYPE || exit 1
 ${LMC} --add net --node client --nid '*' --nettype $NETTYPE || exit 12
 
 # configure mds server
-${LMC} --add mds --nspath /mnt/mds_ns  --node localhost --mds mds1 --fstype $FSTYPE --dev $MDSDEV --size $MDSSIZE $JARG $IARG || exit 20
+${LMC} --add mds --node localhost --mds mds1 --fstype $FSTYPE \
+       --dev $MDSDEV --size $MDSSIZE $JARG $IARG $MDSOPT || exit 20
 
 # configure ost
-${LMC} -m $config --add lov --lov lov1 --mds mds1 --stripe_sz $STRIPE_BYTES --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0 || exit 20
+${LMC} -m $config --add lov --lov lov1 --mds mds1 --stripe_sz $STRIPE_BYTES \
+       --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0 $LOVOPT || exit 20
 # only specify "--mkfsoptions='-i 8192'" here because test fs is so small,
 # on a real fs this is not needed unless all files tiny with many stripes
-${LMC} --add ost --nspath /mnt/ost_ns --node localhost --lov lov1 --fstype $FSTYPE --dev $OSTDEV --size $OSTSIZE --mkfsoptions="-i 8192" $JARG || exit 30
+${LMC} --add ost --nspath /mnt/ost_ns --node localhost --lov lov1 \
+       --fstype $FSTYPE --dev $OSTDEV --size $OSTSIZE \
+       --mkfsoptions="-i 8192" $JARG $OSTOPT || exit 30
 
 # create client config
-${LMC} --add mtpt --node localhost --path $MOUNT --mds mds1 --lov lov1 || exit 40
-${LMC} --add mtpt --node client --path $MOUNT2 --mds mds1 --lov lov1 || exit 41
+${LMC} --add mtpt --node localhost --path $MOUNT --mds mds1 --lov lov1 \
+       $CLIENTOPT || exit 40
+${LMC} --add mtpt --node client --path $MOUNT2 --mds mds1 --lov lov1 \
+       $CLIENTOPT || exit 41
index 709de03..dd782c6 100755 (executable)
@@ -39,10 +39,12 @@ ${LMC} --add net --node  localhost --nid `hostname` --nettype $NETTYPE || exit 1
 ${LMC} --add net --node client --nid '*' --nettype $NETTYPE || exit 12
 
 # configure mds server
-${LMC} --format --add mds --node localhost --mds mds1 --fstype $FSTYPE --dev $MDSDEV --size $MDSSIZE || exit 20
+${LMC} --format --add mds --node localhost --mds mds1 --fstype $FSTYPE \
+       --dev $MDSDEV --size $MDSSIZE $MDSOPT || exit 20
 
 # configure ost
-${LMC} --add lov --lov lov1 --mds mds1 --stripe_sz $STRIPE_BYTES --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0 || exit 20
+${LMC} --add lov --lov lov1 --mds mds1 --stripe_sz $STRIPE_BYTES \
+       --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0 $LOVOPT || exit 20
 
 for num in `seq $OSTCOUNT`; do
     OST=ost$num
@@ -50,14 +52,18 @@ for num in `seq $OSTCOUNT`; do
     eval $DEVPTR=${!DEVPTR:=$TMP/$OST-`hostname`}
     # only specify "--mkfsoptions='-i 8192'" here because test fs is so small,
     # on a real fs this is not needed unless all files tiny with many stripes
-    ${LMC} --add ost --node localhost --lov lov1 --ost $OST --fstype $FSTYPE --dev ${!DEVPTR} --size $OSTSIZE --mkfsoptions="-i 8192"  $JARG || exit 30
+    ${LMC} --add ost --node localhost --lov lov1 --ost $OST --fstype $FSTYPE \
+       --dev ${!DEVPTR} --size $OSTSIZE --mkfsoptions="-i 8192" \
+       $JARG $OSTOPT || exit 30
 done
 
 
 if [ -z "$ECHO_CLIENT" ]; then
        # create client config
-       ${LMC} --add mtpt --node localhost --path $MOUNT --mds mds1 --lov lov1 || exit 40
-       ${LMC} --add mtpt --node client --path $MOUNT2 --mds mds1 --lov lov1 || exit 41
+       ${LMC} --add mtpt --node localhost --path $MOUNT --mds mds1 --lov lov1 \
+               $CLIENTOPT || exit 40
+       ${LMC} --add mtpt --node client --path $MOUNT2 --mds mds1 --lov lov1 \
+               $CLIENTOPT || exit 41
 else
        ${LMC} --add echo_client --node localhost --ost lov1 || exit 42
 fi
index 7412010..ba7084f 100755 (executable)
@@ -21,7 +21,7 @@ build_test_filter
 # setting SETUP=" " and CLEANUP=" "
 SETUP=${SETUP:-"setup"}
 CLEANUP=${CLEANUP:-"cleanup"}
-
+FORCE=${FORCE:-"--force"}
 
 make_config() {
     rm -f $XMLCONFIG
@@ -246,7 +246,6 @@ test_17() {
     sysctl -w lustre.fail_loc=0x80000503
     # need to write enough to ensure we send an RPC
     do_facet client dd if=/dev/zero of=$DIR/$tfile bs=1024k count=2
-
     sleep $TIMEOUT
     sysctl -w lustre.fail_loc=0
     do_facet client "df $DIR"
@@ -379,7 +378,7 @@ run_test 20b "ldlm_handle_enqueue error (should return error)"
 test_24() {    # bug 2248 - eviction fails writeback but app doesn't see it
        mkdir -p $DIR/$tdir
        cancel_lru_locks OSC
-       multiop $DIR/$tdir/$tfile Owyw_yc &
+       multiop $DIR/$tdir/$tfile Owy_wyc &
        MULTI_PID=$!
        usleep 500
 # OBD_FAIL_PTLRPC_BULK_PUT_NET|OBD_FAIL_ONCE
@@ -391,4 +390,88 @@ test_24() {        # bug 2248 - eviction fails writeback but app doesn't see it
 }
 run_test 24 "fsync error (should return error)" 
 
+
+test_25a() {
+       mkdir -p $DIR/$tdir
+       # put a load of file creates/writes/deletes for 10 min.
+       do_facet client "writemany -q -a $DIR/$tdir/$tfile 600 5" &
+        CLIENT_PID=$!
+       echo writemany pid $CLIENT_PID
+       sleep 10
+       FAILURE_MODE="SOFT"
+       fail mds
+       # wait for client to reconnect to MDS
+       sleep 60
+       fail mds
+       sleep 60
+       fail mds
+       # client process should see no problems even though MDS went down
+       wait $CLIENT_PID 
+       rc=$?
+       echo writemany returned $rc
+       return $rc
+}
+run_test 25a "failover MDS under load"
+
+test_25b() {
+       mkdir -p $DIR/$tdir
+       # put a load of file creates/writes/deletes
+       do_facet client "writemany -q -a $DIR/$tdir/$tfile 300 5" &
+        CLIENT_PID=$!
+       echo writemany pid $CLIENT_PID
+       sleep 1
+       FAILURE_MODE="SOFT"
+       facet_failover mds
+       # failover at various points during recovery
+       sleep 1
+       facet_failover mds
+       sleep 5
+       facet_failover mds
+       sleep 10
+       facet_failover mds
+       sleep 20
+       facet_failover mds
+       # client process should see no problems even though MDS went down
+        # and recovery was interrupted
+       wait $CLIENT_PID 
+       rc=$?
+       echo writemany returned $rc
+       return $rc
+}
+run_test 25b "failover MDS during recovery"
+
+test_25c_guts() {
+       do_facet client "writemany -q $DIR/$tdir/$tfile 600 5" &
+        CLIENT_PID=$!
+       echo writemany pid $CLIENT_PID
+       sleep 10
+       FAILURE_MODE="SOFT"
+       fail ost
+       rc=0
+       wait $CLIENT_PID || rc=$?
+       # active client process should see an EIO for down OST
+       [ $rc -eq 5 ] && { echo "writemany correctly failed $rc" && return 0; }
+       # but timing or failover setup may allow success
+       [ $rc -eq 0 ] && { echo "writemany succeeded" && return 0; }
+       echo "writemany returned $rc"
+       return $rc
+}
+
+test_25c() {
+       mkdir -p $DIR/$tdir
+       test_25c_guts
+       rc=$?
+       [ $rc -ne 0 ] && { return $rc; }
+       # wait for client to reconnect to OST
+       sleep 30
+       test_25c_guts
+       rc=$?
+       [ $rc -ne 0 ] && { return $rc; }
+       sleep 30
+       test_25c_guts
+       rc=$?
+       return $rc
+}
+run_test 25c "failover OST under load"
+
 $CLEANUP
index 742cc8c..9f6b778 100755 (executable)
@@ -11,6 +11,7 @@ init_test_env $@
 
 SETUP=${SETUP:-"setup"}
 CLEANUP=${CLEANUP:-"cleanup"}
+FORCE=${FORCE:-"--force"}
 
 gen_config() {
     rm -f $XMLCONFIG
@@ -40,7 +41,7 @@ cleanup() {
 
     umount $MOUNT2 || true
     umount $MOUNT  || true
-    rmmod llite
+    rmmod llite || true
     stop mds ${FORCE}
     stop ost2 ${FORCE}
     stop ost ${FORCE}  --dump $TMP/replay-dual-`hostname`.log
index 02e1214..9044078 100644 (file)
@@ -8,7 +8,7 @@ set -e
 
 ONLY=${ONLY:-"$*"}
 # bug number for skipped test: 2108 3637 3561 5188/5749
-ALWAYS_EXCEPT=${ALWAYS_EXCEPT:-"42a 42c 45 68"}
+ALWAYS_EXCEPT=${ALWAYS_EXCEPT:-"42a 42c  45   68"}
 # UPDATE THE COMMENT ABOVE WITH BUG NUMBERS WHEN CHANGING ALWAYS_EXCEPT!
 
 [ "$ALWAYS_EXCEPT$EXCEPT" ] && \
@@ -54,7 +54,7 @@ SAVE_PWD=$PWD
 
 clean() {
        echo -n "cln.."
-       sh llmountcleanup.sh > /dev/null || exit 20
+       sh llmountcleanup.sh ${FORCE} > /dev/null || exit 20
        I_MOUNTED=no
 }
 CLEAN=${CLEAN:-:}
@@ -1782,8 +1782,8 @@ test_48e() { # bug 4134
        $TRACE rmdir $DIR/d48e || error "remove parent $DIR/d48e failed"
        $TRACE touch $DIR/d48e || error "'touch $DIR/d48e' failed"
        $TRACE chmod +x $DIR/d48e || error "'chmod +x $DIR/d48e' failed"
-       $TRACE wait $cdpid && error "'cd ..' worked after recreate parent"
-       $TRACE rm $DIR/d48e || error "'$DIR/d48e' failed"
+       $TRACE wait $cdpid && echo "'cd ..' worked after recreate parent"
+       $TRACE rm $DIR/d48e || error "rm '$DIR/d48e' failed"
 }
 run_test 48e "Access to recreated parent subdir (should return errors)"
 
index d2135ca..94e2ebc 100644 (file)
@@ -37,7 +37,7 @@ SAVE_PWD=$PWD
 
 clean() {
        echo -n "cln.."
-       sh llmountcleanup.sh > /dev/null || exit 20
+       sh llmountcleanup.sh ${FORCE} > /dev/null || exit 20
 }
 CLEAN=${CLEAN:-}
 
index 3551c27..a0f8c9b 100644 (file)
@@ -90,11 +90,14 @@ zconf_mount() {
     do_node $client mkdir $mnt 2> /dev/null || :
 
     if [ -x /sbin/mount.lustre ] ; then
-       do_node $client mount -t lustre -o nettype=$NETTYPE `facet_active_host mds`:/mds_svc/client_facet $mnt || return 1
+       do_node $client mount -t lustre -o nettype=$NETTYPE,$MOUNTOPT \
+               `facet_active_host mds`:/mds_svc/client_facet $mnt || return 1
     else
-       # this is so cheating
-       do_node $client $LCONF --nosetup --node client_facet $XMLCONFIG  > /dev/null || return 2
-       do_node $client $LLMOUNT -o nettype=$NETTYPE `facet_active_host mds`:/mds_svc/client_facet $mnt || return 4
+       # this is so cheating
+       do_node $client $LCONF --nosetup --node client_facet $XMLCONFIG > \
+               /dev/null || return 2
+       do_node $client $LLMOUNT -o nettype=$NETTYPE,$MOUNTOPT \
+               `facet_active_host mds`:/mds_svc/client_facet $mnt || return 4
     fi
 
     [ -d /r ] && $LCTL modules > /r/tmp/ogdb-`hostname`
@@ -123,6 +126,8 @@ reboot_facet() {
     facet=$1
     if [ "$FAILURE_MODE" = HARD ]; then
        $POWER_UP `facet_active_host $facet`
+    else
+       sleep 10
     fi
 }
 
@@ -322,14 +327,16 @@ add_mds() {
     shift
     rm -f ${facet}active
     add_facet $facet
-    do_lmc --add mds --node ${facet}_facet --mds ${facet}_svc --fstype $FSTYPE $*
+    do_lmc --add mds --node ${facet}_facet --mds ${facet}_svc \
+       --fstype $FSTYPE $* $MDSOPT
 }
 
 add_mdsfailover() {
     facet=$1
     shift
     add_facet ${facet}failover  --lustre_upcall $UPCALL
-    do_lmc --add mds  --node ${facet}failover_facet --mds ${facet}_svc --fstype $FSTYPE $*
+    do_lmc --add mds  --node ${facet}failover_facet --mds ${facet}_svc \
+       --fstype $FSTYPE $* $MDSOPT
 }
 
 add_ost() {
@@ -337,22 +344,23 @@ add_ost() {
     shift
     rm -f ${facet}active
     add_facet $facet
-    do_lmc --add ost --node ${facet}_facet --ost ${facet}_svc --fstype $FSTYPE $*
+    do_lmc --add ost --node ${facet}_facet --ost ${facet}_svc \
+       --fstype $FSTYPE $* $OSTOPT
 }
 
 add_ostfailover() {
     facet=$1
     shift
     add_facet ${facet}failover
-    do_lmc --add ost --failover --node ${facet}failover_facet --ost ${facet}_svc --fstype $FSTYPE $*
+    do_lmc --add ost --failover --node ${facet}failover_facet \
+       --ost ${facet}_svc --fstype $FSTYPE $* $OSTOPT
 }
 
 add_lov() {
     lov=$1
     mds_facet=$2
     shift; shift
-    do_lmc --add lov --mds ${mds_facet}_svc --lov $lov $*
-    
+    do_lmc --add lov --mds ${mds_facet}_svc --lov $lov $* $LOVOPT
 }
 
 add_client() {
@@ -360,8 +368,7 @@ add_client() {
     mds=$2
     shift; shift
     add_facet $facet --lustre_upcall $UPCALL
-    do_lmc --add mtpt --node ${facet}_facet --mds ${mds}_svc $*
-
+    do_lmc --add mtpt --node ${facet}_facet --mds ${mds}_svc $* $CLIENTOPT
 }
 
 
index fbdd284..7ec18ae 100644 (file)
@@ -86,10 +86,12 @@ done
 
 # configure mds server
 echo; echo "adding MDS on: $MDSNODE"
-${LMC} -m $config --add mds --format --node $MDSNODE --mds mds1 --fstype $FSTYPE --dev $MDSDEV --size $MDSSIZE ||exit 10
+${LMC} -m $config --add mds --node $MDSNODE --mds mds1 --fstype $FSTYPE \
+       --dev $MDSDEV --size $MDSSIZE $MDSOPT || exit 10
 
 # configure ost
-${LMC} -m $config --add lov --lov lov1 --mds mds1 --stripe_sz $STRIPE_BYTES --stripe_cnt $STRIPECNT --stripe_pattern 0 || exit 20
+${LMC} -m $config --add lov --lov lov1 --mds mds1 --stripe_sz $STRIPE_BYTES \
+       --stripe_cnt $STRIPECNT --stripe_pattern 0 $LOVOPT || exit 20
 COUNT=1
 echo -n "adding OST on:"
 for NODE in $OSTNODES; do
@@ -104,7 +106,8 @@ for NODE in $OSTNODES; do
                        OSTARGS="--osdtype=obdecho"
                        ;;
        esac
-        ${LMC} -m $config --add ost --node $NODE --lov lov1 $OSTARGS $OSTFAILOVER || exit 21
+        ${LMC} -m $config --add ost --node $NODE --lov lov1 $OSTARGS \
+               $OSTFAILOVER $OSTOPT || exit 21
        COUNT=`expr $COUNT + 1`
 done
 
@@ -112,6 +115,7 @@ done
 echo; echo -n "adding CLIENT on:"
 for NODE in $CLIENTS; do
        echo -n " $NODE"
-       ${LMC} -m $config --add mtpt --node $NODE --path $MOUNT --mds mds1 --lov lov1 || exit 30
+       ${LMC} -m $config --add mtpt --node $NODE --path $MOUNT --mds mds1 \
+               --lov lov1 $CLIENTOPT || exit 30
 done
 echo
diff --git a/lustre/tests/writemany.c b/lustre/tests/writemany.c
new file mode 100644 (file)
index 0000000..5d4e42e
--- /dev/null
@@ -0,0 +1,250 @@
+/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
+ * vim:expandtab:shiftwidth=8:tabstop=8:
+ */
+#include <stdlib.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <signal.h>
+#include <fcntl.h>
+#include <errno.h>
+#include <string.h>
+#include <sys/wait.h>
+#include <time.h>
+#include <sys/time.h>
+
+
+#define difftime(a, b)                                          \
+        ((double)(a)->tv_sec - (b)->tv_sec +                    \
+         ((double)((a)->tv_usec - (b)->tv_usec) / 1000000))
+
+
+
+char cmdname[512];
+int o_abort = 0;
+int o_quiet = 0;
+
+struct kid_list_t {
+        pid_t kid;
+        struct kid_list_t *next;
+};
+
+struct kid_list_t *head = NULL;
+
+void push_kid(pid_t kid)
+{
+        struct kid_list_t *new;
+        new = (struct kid_list_t *)malloc(sizeof(struct kid_list_t));
+        new->kid = kid;
+        new->next = head;
+        head = new;
+}
+
+void kill_kids(void)
+{
+        while(head) {
+                kill(head->kid, SIGTERM);
+                head = head->next;
+        }
+}
+
+int wait_for_threads(int live_threads)
+{
+        int rc = 0;
+        
+        while (live_threads > 0) {
+                int status;
+                pid_t ret;
+                
+                ret = waitpid(0, &status, 0);
+                if (ret == 0) {
+                        continue;
+                }
+                
+                if (ret < 0) {
+                        fprintf(stderr, "%s: error: wait - %s\n",
+                                cmdname, strerror(errno));
+                        if (!rc)
+                                rc = errno;
+                } else {
+                        /*
+                         * This is a hack.  We _should_ be able to use
+                         * WIFEXITED(status) to see if there was an
+                         * error, but it appears to be broken and it
+                         * always returns 1 (OK).  See wait(2).
+                         */
+                        int err = WEXITSTATUS(status);
+                        if (err || WIFSIGNALED(status))
+                                fprintf(stderr,
+                                        "%s: error: PID %d had rc=%d\n",
+                                        cmdname, ret, err);
+                        /* Record first error */
+                        if (!rc)
+                                rc = err;
+
+                        /* Give up on first error */
+                        if (rc && o_abort) {
+                                kill_kids();
+                                break;
+                        }
+
+                        live_threads--;
+                }
+        }
+        if (!o_quiet)
+                printf("%s done, rc = %d\n", cmdname, rc);
+        return rc;
+}
+
+void print_err(char *op, char *filename, struct timeval *time, int err)
+{
+        fprintf(stderr, "%s: %d.%.06d error: %s(%s): %s\n",
+                cmdname, (int)(time->tv_sec), (int)(time->tv_usec), op, 
+                filename, strerror(errno));
+}
+
+int run_one_child(char *file, int thread, int seconds)
+{
+        struct timeval start, cur;
+        double diff;
+        char filename[1024];
+        char buf[1024];
+        int fd, rc = 0, rand, maxrand, len;
+        long nfiles = 0, nbytes = 0;
+
+        if (!o_quiet) 
+                printf("%s: running thread #%d\n", cmdname, thread);
+        
+        srandom(thread);
+        /* Higher thread numbers will produce bigger random files.  
+           Thread 1 will produce only 0-len files. */
+        maxrand = 1; rand = thread;
+        while (--rand)
+                maxrand *= 10;
+
+        gettimeofday(&start, NULL);
+
+        while(!rc) {
+                gettimeofday(&cur, NULL);
+                if (cur.tv_sec > (start.tv_sec + seconds))
+                        break;
+
+                sprintf(filename, "%s-%d-%ld", file, thread, nfiles);
+                
+                fd = open(filename, O_RDWR | O_CREAT, 0666);
+                if (fd < 0) {
+                        print_err("open", filename, &cur, errno);
+                        rc = errno;
+                        break;
+                }
+                
+                sprintf(buf, "%s %010ld %.19s.%012d\n", cmdname, 
+                        nfiles++, ctime(&cur.tv_sec), (int)cur.tv_usec);
+                len = strlen(buf);
+
+                rand = random() % maxrand;
+                while (rand-- > 0) {
+                        if (write(fd, buf, len) != len) {
+                                print_err("write", filename, &cur, errno);
+                                rc = errno;
+                                break;
+                        }                     
+                        nbytes += len;
+                }  
+                
+                if (close(fd) < 0) {
+                        print_err("close", filename, &cur, errno);
+                        rc = errno;
+                        break;
+                }
+                if (unlink(filename) < 0) {
+                        print_err("unlink", filename, &cur, errno);
+                        rc = errno;
+                        break;
+                }
+        }
+        
+        diff = difftime(&cur, &start);
+        if (!o_quiet) 
+                printf("%s: %7ld files, %4ld MB in %.2fs (%7.2f files/s, " 
+                       "%5.2f MB/s): rc = %d\n",
+                       cmdname, nfiles, nbytes >> 20, diff,
+                       (double)nfiles / diff, (double)nbytes/1024/1024 / diff,
+                       rc);
+
+        return rc;
+}
+
+void usage(char *name)
+{
+        fprintf(stderr,
+                "usage: %s [opts] <dirname> <seconds> <threads>\n",
+                name);
+        fprintf(stderr, "  -q quiet\n");
+        fprintf(stderr, "  -a abort other children on first err\n");
+        exit(1);
+}
+
+int main(int argc, char *argv[])
+{
+        unsigned long duration;
+        int threads = 0;
+        char *end;
+        char *directory;
+        int i = 1, rc = 0;
+
+        sprintf(cmdname, "%s", argv[0]);        
+
+        while((i < argc) && (argv[i][0] == '-')) {
+                switch (argv[i][1]) {
+                case 'q':
+                        o_quiet++;
+                        break;
+                case 'a':
+                        o_abort++;
+                        break;
+                }
+                i++;
+        }
+
+        if ((argc - i) < 3)
+                usage(argv[0]);
+
+        directory = argv[i];
+        duration = strtoul(argv[++i], &end, 0);
+        if (*end) {
+                fprintf(stderr, "%s: error: bad number of seconds '%s'\n",
+                        cmdname, argv[i]);
+                exit(2);
+        }
+
+        threads = strtoul(argv[++i], &end, 0);
+        if (*end) {
+                fprintf(stderr, "%s: error: bad thread count '%s'\n",
+                        cmdname, argv[i]);
+                exit(2);
+        }
+
+        for (i = 1; i <= threads; i++) {
+                rc = fork();
+                if (rc < 0) {
+                        if (!o_quiet)
+                                fprintf(stderr, "%s: error: #%d - %s\n",
+                                        cmdname, i, strerror(rc = errno));
+                        return (rc);
+                }
+                if (rc == 0) {
+                        /* children */
+                        sprintf(cmdname, "%s-%d", argv[0], i);
+                        return (run_one_child(directory, i, duration));
+                } else {
+                        /* parent */
+                        push_kid(rc);
+                }
+        }
+        /* parent process */
+        if (!o_quiet) 
+                printf("%s will run for %ld minutes\n", cmdname, duration/60);
+        return (wait_for_threads(threads));
+}
index a823c2f..1777fd0 100755 (executable)
@@ -1725,17 +1725,19 @@ class MDSDEV(Module):
             Module.cleanup(self)
         clean_loop(self.devpath)
 
-    def msd_remaining(self):
+    def mds_remaining(self):
         out = lctl.device_list()
         for s in out:
             if string.split(s)[2] in ('mds',):
+                if string.split(s)[1] in ('ST',):
+                    return 0
                 return 1
 
     def safe_to_clean(self):
         return self.active
 
     def safe_to_clean_modules(self):
-        return not self.msd_remaining()
+        return not self.mds_remaining()
 
     def cleanup(self):
         if not self.active:
@@ -1751,7 +1753,7 @@ class MDSDEV(Module):
                 e.dump()
                 cleanup_error(e.rc)
                 Module.cleanup(self)
-        if not self.msd_remaining() and is_prepared('MDT'):
+        if not self.mds_remaining() and is_prepared('MDT'):
             try:
                 lctl.cleanup("MDT", "MDT_UUID", config.force,
                              config.failover)