Whamcloud - gitweb
* refine local rpc code
authorniu <niu>
Thu, 15 Jan 2004 03:54:13 +0000 (03:54 +0000)
committerniu <niu>
Thu, 15 Jan 2004 03:54:13 +0000 (03:54 +0000)
* update from HEAD

lustre/kernel_patches/patches/snapfs_core-2.4.20.patch
lustre/snapfs/clonefs.c
lustre/snapfs/dir.c
lustre/snapfs/file.c
lustre/snapfs/inode.c
lustre/snapfs/snap.c

index a600722..e28baae 100644 (file)
@@ -2,8 +2,8 @@
 Index: linux-2.4.20-8/fs/ext3/snap.c
 ===================================================================
 --- linux-2.4.20-8.orig/fs/ext3/snap.c 2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-8/fs/ext3/snap.c      2004-01-05 10:54:25.000000000 +0800
-@@ -0,0 +1,2650 @@
++++ linux-2.4.20-8/fs/ext3/snap.c      2004-01-13 00:11:40.000000000 +0800
+@@ -0,0 +1,2645 @@
 +/* fs/ext3/snap.c
 + *
 + * Copyright (c) 2002 Cluster File Systems, Inc. <info@clusterfs.com>
@@ -448,7 +448,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      }
 +      err = ext3_xattr_get(last_inode, EXT3_SNAP_INDEX, EXT3_SNAP_ATTR,
 +                             buf, EXT3_MAX_SNAP_DATA);
-+        if (err == -ENOENT) {
++        if (err == -ENODATA) {
 +               snap_debug("no existing attributes - zeroing\n");
 +               memset(buf, 0, EXT3_MAX_SNAP_DATA);
 +        } else if (err < 0 || err > EXT3_MAX_SNAP_DATA) {
@@ -665,7 +665,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      /* read ea at first */
 +      err = ext3_xattr_get(pri, EXT3_SNAP_INDEX ,EXT3_SNAP_ATTR,
 +                                        buf, EXT3_MAX_SNAP_DATA);
-+      if (err == -ENOENT || err == -ENOATTR) {
++      if (err == -ENODATA || err == -ENOATTR) {
 +              snap_debug("no extended attributes - zeroing\n");
 +              memset(buf, 0, EXT3_MAX_SNAP_DATA);
 +              /* XXX
@@ -740,7 +740,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 + * Copy inode metadata from one inode to another, excluding blocks and size.
 + * FIXME do we copy EA data - ACLs and such (excluding snapshot data)?
 + */
-+static void ext3_copy_meta(struct inode *dst, struct inode *src)
++static void ext3_copy_meta(handle_t *handle, struct inode *dst, struct inode *src)
 +{
 +      int size;
 +      
@@ -776,7 +776,6 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +              while ((namelen = strlen(name))) {
 +                      int attrlen;
 +                      char *buf;
-+                      handle_t *handle = ext3_journal_current_handle();
 +                      
 +                      /* don't copy snap data */
 +                      if (!strcmp(name, EXT3_SNAP_ATTR)) {
@@ -816,10 +815,9 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 + *  This is for LAN free backup later.
 + */
 +
-+static int ext3_migrate_data (struct inode *dst, struct inode *src)
++static int ext3_migrate_data (handle_t *handle, struct inode *dst, struct inode *src)
 +{
 +      unsigned long err = 0;
-+      handle_t *handle = NULL;
 +      /* 512 byte disk blocks per inode block */
 +      int bpib = src->i_sb->s_blocksize >> 9;
 +      
@@ -828,10 +826,8 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      
 +      if (dst->i_ino == src->i_ino)
 +              return 0;
-+      handle = ext3_journal_start(dst, SNAP_MIGRATEDATA_TRANS_BLOCKS);
-+      if( !handle )
-+              return -EINVAL;
-+      ext3_copy_meta(dst, src);
++
++      ext3_copy_meta(handle, dst, src);
 +
 +      snap_debug("migrating %ld data blocks from %lu to %lu\n",
 +                                      blocks, src->i_ino, dst->i_ino);
@@ -863,8 +859,6 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +        ext3_mark_inode_dirty(handle, src);
 +        ext3_mark_inode_dirty(handle, dst);
 +
-+      ext3_journal_stop(handle, dst);
-+
 +      return SNAP_ERROR(err);
 +}
 +
@@ -903,7 +897,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      
 +      err = ext3_xattr_get(primary, EXT3_SNAP_INDEX, EXT3_SNAP_ATTR, 
 +                              buf, EXT3_MAX_SNAP_DATA); 
-+      if (err == -ENOENT) {
++      if (err == -ENODATA) {
 +              slot = 0;
 +      } else if (err < 0) {
 +              snap_debug(" attribute read error\n");
@@ -1258,7 +1252,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +                      goto exit;
 +              }
 +
-+              ext3_migrate_data(tmp, pri);
++              ext3_migrate_data(handle, tmp, pri);
 +              snap_debug("freeing half-copied %lu blocks\n", tmp->i_blocks );
 +              tmp->i_nlink = 0;
 +              iput( tmp );
@@ -1267,7 +1261,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      /* third: restore ind inode to pri inode */
 +      snap_debug("restore %lu blocks to primary inode %lu\n",
 +                      ind->i_blocks, pri->i_ino);
-+      ext3_migrate_data(pri, ind);
++      ext3_migrate_data(handle, pri, ind);
 +
 +      /* final: delete ind inode */
 +      ind->i_nlink = 0;
@@ -1445,7 +1439,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +                      tmp = ext3_new_inode(handle, pri, (int)pri->i_mode, 0);
 +                      if(tmp) {
 +                              down(&tmp->i_sem);
-+                              ext3_migrate_data(tmp, pri);
++                              ext3_migrate_data(handle, tmp, pri);
 +                              up(&tmp->i_sem);
 +                              tmp->i_nlink = 0;
 +                              iput(tmp);      
@@ -1476,6 +1470,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      loopfail( 2 );
 +
 +      snap_debug("got new inode %lu\n", ind->i_ino);
++      ind->i_rdev = pri->i_rdev;
 +      ind->i_op = pri->i_op;
 +      ext3_set_generation(ind, (unsigned long)gen);
 +      /* If we are deleting the primary inode, we want to ensure that it is
@@ -1491,7 +1486,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +              snap_debug("deleting primary inode\n");
 +              
 +              down(&ind->i_sem);
-+              err = ext3_migrate_data(ind, pri);
++              err = ext3_migrate_data(handle, ind, pri);
 +              if (err)
 +                      goto exit_unlock;
 +
@@ -1510,7 +1505,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +
 +              pri->u.ext3_i.i_flags |= EXT3_DEL_FL;
 +              ind->u.ext3_i.i_flags |= EXT3_COW_FL;
-+              if(S_ISREG(pri->i_mode))        pri->i_nlink = 1;
++              if(S_ISREG(pri->i_mode)) pri->i_nlink = 1;
 +              pri->u.ext3_i.i_dtime = CURRENT_TIME;
 +              //pri->u.ext3_i.i_generation++;
 +              ext3_mark_inode_dirty(handle, pri);
@@ -1518,7 +1513,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +              up(&ind->i_sem);
 +      } else {
 +              down(&ind->i_sem);
-+              err = ext3_migrate_data(ind, pri);
++              err = ext3_migrate_data(handle, ind, pri);
 +              if (err)
 +                      goto exit_unlock;
 +
@@ -1925,7 +1920,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      err = ext3_xattr_get(pri, EXT3_SNAP_INDEX, EXT3_SNAP_ATTR,
 +                                              buf, EXT3_MAX_SNAP_DATA);
 +      if (err < 0) {
-+              if (err == -ENOENT)
++              if (err == -ENODATA)
 +                      snap_err("inode %lu is not a redirector\n", pri->i_ino);
 +              else
 +                      snap_err(EXT3_SNAP_ATTR " attribute read error\n");
@@ -2002,7 +1997,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +                              continue;
 +                      if (ext3_copy_block (next_ind, ind, i ) < 0)    break;
 +              }
-+              mark_inode_dirty(next_ind);
++              ext3_mark_inode_dirty(handle, next_ind);
 +              double_unlock(next_ind, ind);
 +
 +#endif 
@@ -2113,7 +2108,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      tmp = ext3_new_inode(handle, pri, (int)pri->i_mode, 0);
 +      if(tmp) {
 +              snap_double_lock(pri, tmp);
-+              ext3_migrate_data(tmp, pri);
++              ext3_migrate_data(handle, tmp, pri);
 +              snap_double_unlock(pri, tmp);
 +
 +              tmp->i_nlink = 0;
@@ -2123,7 +2118,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +              snap_err("restore_indirect, new_inode err\n");
 +
 +      snap_double_lock(pri, ind);
-+      ext3_migrate_data(pri, ind);
++      ext3_migrate_data(handle, pri, ind);
 +      /* clear the cow flag for pri because ind has it */
 +      pri->u.ext3_i.i_flags &= ~EXT3_COW_FL;
 +      ext3_mark_inode_dirty(handle, pri);
@@ -2599,7 +2594,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 +      err = ext3_xattr_get(primary, EXT3_SNAP_INDEX, EXT3_SNAP_ATTR,
 +                                              buf, EXT3_MAX_SNAP_DATA);
 +      
-+      if (err == -ENOENT) {
++      if (err == -ENODATA) {
 +              memset(buf, 0, EXT3_MAX_SNAP_DATA);
 +      } 
 +      else if (err < 0) {
@@ -2657,7 +2652,7 @@ Index: linux-2.4.20-8/fs/ext3/snap.c
 Index: linux-2.4.20-8/fs/ext3/ioctl.c
 ===================================================================
 --- linux-2.4.20-8.orig/fs/ext3/ioctl.c        2004-01-05 10:54:00.000000000 +0800
-+++ linux-2.4.20-8/fs/ext3/ioctl.c     2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/fs/ext3/ioctl.c     2004-01-13 00:10:14.000000000 +0800
 @@ -13,6 +13,12 @@
  #include <linux/ext3_jbd.h>
  #include <linux/sched.h>
@@ -2778,7 +2773,7 @@ Index: linux-2.4.20-8/fs/ext3/ioctl.c
 Index: linux-2.4.20-8/fs/ext3/Makefile
 ===================================================================
 --- linux-2.4.20-8.orig/fs/ext3/Makefile       2004-01-05 10:54:03.000000000 +0800
-+++ linux-2.4.20-8/fs/ext3/Makefile    2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/fs/ext3/Makefile    2004-01-13 00:10:14.000000000 +0800
 @@ -13,7 +13,7 @@
  
  obj-y    := balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o iopen.o \
@@ -2791,7 +2786,7 @@ Index: linux-2.4.20-8/fs/ext3/Makefile
 Index: linux-2.4.20-8/fs/ext3/inode.c
 ===================================================================
 --- linux-2.4.20-8.orig/fs/ext3/inode.c        2004-01-05 10:54:03.000000000 +0800
-+++ linux-2.4.20-8/fs/ext3/inode.c     2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/fs/ext3/inode.c     2004-01-13 00:10:14.000000000 +0800
 @@ -1191,7 +1191,7 @@
   * So, if we see any bmap calls here on a modified, data-journaled file,
   * take extra steps to flush any blocks which might be in the cache. 
@@ -2804,7 +2799,7 @@ Index: linux-2.4.20-8/fs/ext3/inode.c
 Index: linux-2.4.20-8/fs/ext3/ialloc.c
 ===================================================================
 --- linux-2.4.20-8.orig/fs/ext3/ialloc.c       2004-01-05 10:54:03.000000000 +0800
-+++ linux-2.4.20-8/fs/ext3/ialloc.c    2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/fs/ext3/ialloc.c    2004-01-13 00:10:14.000000000 +0800
 @@ -78,7 +78,6 @@
        sb->u.ext3_sb.s_inode_bitmap[bitmap_nr] = bh;
        return retval;
@@ -2830,7 +2825,7 @@ Index: linux-2.4.20-8/fs/ext3/ialloc.c
 Index: linux-2.4.20-8/include/linux/snap.h
 ===================================================================
 --- linux-2.4.20-8.orig/include/linux/snap.h   2003-01-30 18:24:37.000000000 +0800
-+++ linux-2.4.20-8/include/linux/snap.h        2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/include/linux/snap.h        2004-01-13 00:10:14.000000000 +0800
 @@ -0,0 +1,266 @@
 +/*
 + * Copyright (c) 2002 Cluster File Systems, Inc. <info@clusterfs.com>
@@ -3101,7 +3096,7 @@ Index: linux-2.4.20-8/include/linux/snap.h
 Index: linux-2.4.20-8/include/linux/ext3_fs.h
 ===================================================================
 --- linux-2.4.20-8.orig/include/linux/ext3_fs.h        2004-01-05 10:54:03.000000000 +0800
-+++ linux-2.4.20-8/include/linux/ext3_fs.h     2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/include/linux/ext3_fs.h     2004-01-13 00:10:14.000000000 +0800
 @@ -183,7 +183,13 @@
  #define EXT3_INDEX_FL                 0x00001000 /* hash-indexed directory */
  #define EXT3_IMAGIC_FL                        0x00002000 /* AFS directory */
@@ -3144,23 +3139,24 @@ Index: linux-2.4.20-8/include/linux/ext3_fs.h
  /*
   * Structure of an inode on the disk
   */
-@@ -429,7 +450,14 @@
+@@ -429,7 +450,15 @@
        __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 */
 +      /* for snapfs */
-+      __u32   s_first_meta_bg; /* First metablock group */
-+      __u32   s_mkfs_time;  /* When the filesystem was created */
++      __u32   s_default_mount_opts;
++        __u32   s_first_meta_bg;        /* First metablock group */
++      __u32   s_mkfs_time;            /* When the filesystem was created */
 +      __u32   s_first_cowed_pri_ino;  /* For snapfs,the first cowed primary inode */
 +      __u32   s_last_cowed_pri_ino;     /* last cowed ino in memory */
 +      __u32   s_snaptable_ino;        /* snaptable ino in memory */
 +      __u32   s_last_snap_orphan;     /* SnapFS: start of cowing indirect inode */
-+      __u32   s_reserved[186];        /* Padding to the end of the block,originally 204 */
++      __u32   s_reserved[185];        /* Padding to the end of the block,originally 204 */
  };
  
  #ifdef __KERNEL__
-@@ -503,6 +531,9 @@
+@@ -503,6 +532,9 @@
  #define EXT3_FEATURE_INCOMPAT_RECOVER         0x0004 /* Needs recovery */
  #define EXT3_FEATURE_INCOMPAT_JOURNAL_DEV     0x0008 /* Journal device */
  
@@ -3173,7 +3169,7 @@ Index: linux-2.4.20-8/include/linux/ext3_fs.h
 Index: linux-2.4.20-8/include/linux/ext3_fs_sb.h
 ===================================================================
 --- linux-2.4.20-8.orig/include/linux/ext3_fs_sb.h     2004-01-05 10:54:00.000000000 +0800
-+++ linux-2.4.20-8/include/linux/ext3_fs_sb.h  2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/include/linux/ext3_fs_sb.h  2004-01-13 00:10:14.000000000 +0800
 @@ -86,6 +86,13 @@
        wait_queue_head_t s_delete_thread_queue;
        wait_queue_head_t s_delete_waiter_queue;
@@ -3191,7 +3187,7 @@ Index: linux-2.4.20-8/include/linux/ext3_fs_sb.h
 Index: linux-2.4.20-8/include/linux/ext3_jbd.h
 ===================================================================
 --- linux-2.4.20-8.orig/include/linux/ext3_jbd.h       2004-01-05 10:53:59.000000000 +0800
-+++ linux-2.4.20-8/include/linux/ext3_jbd.h    2004-01-05 10:54:25.000000000 +0800
++++ linux-2.4.20-8/include/linux/ext3_jbd.h    2004-01-13 00:10:14.000000000 +0800
 @@ -71,6 +71,33 @@
  
  #define EXT3_INDEX_EXTRA_TRANS_BLOCKS 8
@@ -3232,10 +3228,10 @@ Index: linux-2.4.20-8/include/linux/ext3_jbd.h
  fs/ext3/ialloc.c           |    8 
  fs/ext3/inode.c            |    2 
  fs/ext3/ioctl.c            |  103 +
- fs/ext3/snap.c             | 2650 +++++++++++++++++++++++++++++++++++++++++++++
- include/linux/ext3_fs.h    |   37 
+ fs/ext3/snap.c             | 2645 +++++++++++++++++++++++++++++++++++++++++++++
+ include/linux/ext3_fs.h    |   38 
  include/linux/ext3_fs_sb.h |    7 
  include/linux/ext3_jbd.h   |   27 
  include/linux/snap.h       |  266 ++++
- 9 files changed, 3096 insertions(+), 6 deletions(-)
+ 9 files changed, 3092 insertions(+), 6 deletions(-)
 
index 708b083..71a0735 100644 (file)
@@ -106,8 +106,10 @@ static void clonefs_read_inode(struct inode *inode)
                inode->i_op = &clonefs_file_inode_ops;
                if (inode->i_mapping)
                        inode->i_mapping->a_ops = &clonefs_file_address_ops;
+               inode->i_fop = &clonefs_file_file_ops;
        } else if (S_ISDIR(inode->i_mode)) {
                inode->i_op = &clonefs_dir_inode_ops;
+               inode->i_fop = &clonefs_dir_file_ops;
        } else if (S_ISLNK(inode->i_mode)) {
                inode->i_op = &clonefs_symlink_inode_ops;
        } else {
@@ -181,6 +183,20 @@ static void d_unalloc(struct dentry *dentry)
        dput(dentry); /* this will free the dentry memory */
 }
 
+static void prepare_parent_dentry(struct dentry *dentry, struct inode *inode)
+{
+       atomic_set(&dentry->d_count, 1);
+       dentry->d_vfs_flags = 0;
+       dentry->d_flags = 0;
+       dentry->d_inode = inode;
+       dentry->d_op = NULL;
+       dentry->d_fsdata = NULL;
+       dentry->d_mounted = 0;
+       INIT_LIST_HEAD(&dentry->d_hash);
+       INIT_LIST_HEAD(&dentry->d_lru);
+       INIT_LIST_HEAD(&dentry->d_subdirs);
+       INIT_LIST_HEAD(&dentry->d_alias);
+}
 /*
  * Return the underlying fs dentry with name in 'dentry' that points
  * to the right inode. 'dir' is the clone fs directory to search for
@@ -188,18 +204,25 @@ static void d_unalloc(struct dentry *dentry)
  */
 struct dentry *clonefs_lookup(struct inode *dir,  struct dentry *dentry)
 {
-       struct inode            *cache_dir;
-       struct dentry           *cache_dentry;
+       struct inode            *cache_dir = NULL;
+       struct dentry           *cache_dentry = NULL; 
        struct inode            *cache_inode;
        struct dentry           *result;
+       struct dentry           tmp;
        struct inode            *inode;
        struct snap_clone_info  *clone_sb;
 
        ENTRY;
 
        cache_dir = clonefs_get_inode(dir); 
-
-       cache_dentry = d_alloc(dentry->d_parent, &dentry->d_name);
+       if (!cache_dir) 
+               RETURN(ERR_PTR(-ENOENT));
+       /*FIXME later, we make parent dentry here
+        *there may some problems in lookup
+        */      
+       prepare_parent_dentry(&tmp, cache_dir);
+       cache_dentry = d_alloc(&tmp, &dentry->d_name);
+       
        if (!cache_dentry) {
                 iput(cache_dir);
                RETURN(ERR_PTR(-ENOENT));
@@ -306,7 +329,7 @@ static int clonefs_readdir(struct file *file, void *dirent,
        struct inode *cache_inode;
         struct file open_file;
        struct dentry open_dentry;
-       struct inode *inode=file->f_dentry->d_inode;
+       struct inode *inode = file->f_dentry->d_inode;
 
        ENTRY;
 
@@ -369,13 +392,14 @@ static int clonefs_readpage(struct file *file, struct page *page)
                              &open_dentry);
        /* tell currentfs_readpage the primary inode number */
        open_dentry.d_fsdata = (void*)inode->i_ino;
-
+       page->mapping->host = cache_inode;
        /* potemkin case: we are handed a directory inode */
        down(&cache_inode->i_sem);
         /* XXX - readpage NULL on directories... */
         result = cache_inode->i_mapping->a_ops->readpage(&open_file, page);
 
        up(&cache_inode->i_sem);
+       page->mapping->host = inode;
        clonefs_restore_snapfile(inode, file, cache_inode, &open_file);
        iput(cache_inode);
        RETURN(result);
index a1636f2..4db0908 100644 (file)
@@ -150,7 +150,6 @@ static int currentfs_create(struct inode *dir, struct dentry *dentry, int mode)
 {
        struct snap_cache       *cache;
        struct inode_operations *iops;
-       struct snapshot_operations *snapops;    
        void                    *handle = NULL;
        int                     rc;
 
@@ -165,16 +164,12 @@ static int currentfs_create(struct inode *dir, struct dentry *dentry, int mode)
                RETURN(-EINVAL);
        }
 
-       snapops = filter_c2csnapops(cache->cache_filter);
-       if (!snapops || !snapops->get_generation) 
-               RETURN(-EINVAL);
-
        handle = snap_trans_start(cache, dir, SNAP_OP_CREATE);
 
        if ( snap_needs_cow(dir) != -1 ) {
                CDEBUG(D_INODE, "snap_needs_cow for ino %lu \n",dir->i_ino);
                snap_debug_device_fail(dir->i_dev, SNAP_OP_CREATE, 1);
-               if (!(snap_do_cow(dir, get_parent_ino(dir), 0))) {
+               if ((snap_do_cow(dir, get_parent_ino(dir), 0))) {
                        CERROR("Do cow error\n");
                        RETURN(-EINVAL);
                }
@@ -192,20 +187,11 @@ static int currentfs_create(struct inode *dir, struct dentry *dentry, int mode)
                 CERROR("Error in currentfs_create, dentry->d_inode is NULL\n");
                 GOTO(exit, 0);
         }
-
-       if (S_ISDIR(dentry->d_inode->i_mode))
-                dentry->d_inode->i_op = filter_c2udiops(cache->cache_filter);
-        else if (S_ISREG(dentry->d_inode->i_mode)) {
-                if (!filter_c2cfiops(cache->cache_filter)) {
-                        filter_setup_file_ops(cache->cache_filter, dentry->d_inode,
-                                             &currentfs_file_iops, &currentfs_file_fops,
-                                             &currentfs_file_aops);
-                }
-                dentry->d_inode->i_op = filter_c2ufiops(cache->cache_filter);
-        }
+       set_filter_ops(cache, dentry->d_inode);
        CDEBUG(D_INODE, "inode %lu, i_op %p\n", dentry->d_inode->i_ino, dentry->d_inode->i_op);
        snap_debug_device_fail(dir->i_dev, SNAP_OP_CREATE, 3);
-       init_filter_data(dentry->d_inode, snapops, 0); exit:
+       init_filter_data(dentry->d_inode, 0); 
+exit:
        snap_trans_commit(cache, handle);
        RETURN(rc);
 }
index c6795aa..78cc9ab 100644 (file)
@@ -102,7 +102,7 @@ static ssize_t currentfs_write (struct file *filp, const char *buf,
        for( i=0; i<2; i++ ){
                if(block[i]!=-1 && aops->bmap(inode->i_mapping, block[i])) {
                        table = &snap_tables[cache->cache_snap_tableno];
-                       for (slot = table->tbl_count ; slot >= 1; slot--) {
+                       for (slot = table->tbl_count - 1; slot >= 1; slot--) {
                                struct address_space_operations *c_aops = 
                                        cache_inode->i_mapping->a_ops;
                                cache_inode = NULL;
@@ -179,7 +179,7 @@ static int currentfs_readpage(struct file *file, struct page *page)
 
        table = &snap_tables[cache->cache_snap_tableno];
 
-        for (slot = table->tbl_count ; slot >= 1; slot--)
+        for (slot = table->tbl_count - 1; slot >= 1; slot--)
         {
                struct address_space_operations *c_aops = 
                                        cache_inode->i_mapping->a_ops;
index 9f43d0d..25619a8 100644 (file)
@@ -49,25 +49,66 @@ int init_filter_info_cache()
 
 
 void init_filter_data(struct inode *inode, 
-                            struct snapshot_operations *snapops, 
                             int flag)
 {
        struct filter_inode_info *i;
+        struct snap_cache *cache;
+       struct snapshot_operations *snapops; 
 
-       if (inode->i_filterdata){
+       if (inode->i_filterdata || inode->i_ino & 0xF0000000)
                 return;
-        }
+       cache = snap_find_cache(inode->i_dev);
+       if (!cache) {
+               CERROR("currentfs_read_inode: cannot find cache\n");
+               make_bad_inode(inode);
+               return;
+       }
+       snapops = filter_c2csnapops(cache->cache_filter);
+       
        inode->i_filterdata = (struct filter_inode_info *) \
                              kmem_cache_alloc(filter_info_cache, SLAB_KERNEL);
        i = inode->i_filterdata;
        i -> generation = snapops->get_generation(inode);
        i -> flags      = flag;
 }
+
+void set_filter_ops(struct snap_cache *cache, struct inode *inode)
+{
+       /* XXX now set the correct snap_{file,dir,sym}_iops */
+       if (S_ISDIR(inode->i_mode)) { 
+               inode->i_op = filter_c2udiops(cache->cache_filter);
+               inode->i_fop = filter_c2udfops(cache->cache_filter);
+       } else if (S_ISREG(inode->i_mode)) {
+               if ( !filter_c2cfiops(cache->cache_filter) ) {
+                       filter_setup_file_ops(cache->cache_filter, inode, 
+                                             &currentfs_file_iops, 
+                                             &currentfs_file_fops, 
+                                             &currentfs_file_aops);
+               }
+               CDEBUG(D_INODE, "inode %lu, i_op at %p\n", 
+                      inode->i_ino, inode->i_op);
+               inode->i_fop = filter_c2uffops(cache->cache_filter);
+               inode->i_op = filter_c2ufiops(cache->cache_filter);
+               if (inode->i_mapping)
+                       inode->i_mapping->a_ops = filter_c2ufaops(cache->cache_filter);
+
+       }
+       else if (S_ISLNK(inode->i_mode)) {
+               if ( !filter_c2csiops(cache->cache_filter) ) {
+                       filter_setup_symlink_ops(cache->cache_filter, inode,
+                               &currentfs_sym_iops, &currentfs_sym_fops);
+               }
+               inode->i_op = filter_c2usiops(cache->cache_filter);
+               inode->i_fop = filter_c2usfops(cache->cache_filter);
+               CDEBUG(D_INODE, "inode %lu, i_op at %p\n", 
+                      inode->i_ino, inode->i_op);
+       }
+}
+
 /* Superblock operations. */
 static void currentfs_read_inode(struct inode *inode)
 {
         struct snap_cache *cache;
-       struct snapshot_operations *snapops;    
        ENTRY;
 
        if( !inode ) 
@@ -86,39 +127,14 @@ static void currentfs_read_inode(struct inode *inode)
                currentfs_dotsnap_read_inode(cache, inode);
                return;
        }
-       snapops = filter_c2csnapops(cache->cache_filter);
-       
-       if (!snapops || !snapops->get_indirect) 
-               return;
 
        if(filter_c2csops(cache->cache_filter))
                filter_c2csops(cache->cache_filter)->read_inode(inode);
 
-       /* XXX now set the correct snap_{file,dir,sym}_iops */
-       if (S_ISDIR(inode->i_mode)) 
-               inode->i_op = filter_c2udiops(cache->cache_filter);
-       else if (S_ISREG(inode->i_mode)) {
-               if ( !filter_c2cfiops(cache->cache_filter) ) {
-                       filter_setup_file_ops(cache->cache_filter, inode, 
-                                             &currentfs_file_iops, 
-                                             &currentfs_file_fops, 
-                                             &currentfs_file_aops);
-               }
-               CDEBUG(D_INODE, "inode %lu, i_op at %p\n", 
-                      inode->i_ino, inode->i_op);
-       }
-       else if (S_ISLNK(inode->i_mode)) {
-               if ( !filter_c2csiops(cache->cache_filter) ) {
-                       filter_setup_symlink_ops(cache->cache_filter, inode,
-                               &currentfs_sym_iops, &currentfs_sym_fops);
-               }
-               inode->i_op = filter_c2usiops(cache->cache_filter);
-               CDEBUG(D_INODE, "inode %lu, i_op at %p\n", 
-                      inode->i_ino, inode->i_op);
-       }
+       set_filter_ops(cache, inode);
        /*init filter_data struct 
         * FIXME flag should be set future*/
-       init_filter_data(inode, snapops, 0); 
+       init_filter_data(inode, 0); 
        return; 
 }
 
index a5032a6..afb4ddb 100644 (file)
@@ -70,16 +70,18 @@ struct inode *snap_redirect(struct inode *cache_inode,
 
        /* first find if there are indirected at the clone_index */
        redirected = snapops->get_indirect(cache_inode, NULL, 
-                                       clone_info->clone_index);
+                                          clone_info->clone_index);
        /* if not found, get the FIRST index after this and before NOW */
        /* XXX fix this later, now use tbl_count, not NOW */
        if (!redirected) {
                int index;
+
+               memset(my_table, 0, sizeof(my_table));
                clone_slot = snap_index2slot(table, clone_info->clone_index);
-               for (slot = table->tbl_count; slot >= clone_slot; slot --) {
-                       my_table[slot-clone_slot+1] = table->snap_items[slot].index;
+               for (slot = table->tbl_count-1; slot >= clone_slot; slot --) {
+                       my_table[slot - clone_slot + 1] = table->snap_items[slot].index;
                }
-               index = table->tbl_count - clone_slot + 1;
+               index = table->tbl_count - clone_slot;
                redirected = snapops->get_indirect(cache_inode, my_table, index);
        }
 
@@ -113,9 +115,11 @@ int snap_do_cow(struct inode *inode, ino_t parent_ino, int del)
        }
 
        snap_last(cache, &snap);
-       ind = snapops->create_indirect(inode, snap.index, 0, parent_ino, del);
+       ind = snapops->create_indirect(inode, snap.index, snap.gen, parent_ino, del);
        if(!ind)
                RETURN(-EINVAL);                
+       init_filter_data(ind, 0);
+       set_filter_ops(cache, ind);             
        iput(ind);
        RETURN(0);
 }