return NULL;
cache_inode = I2CI(fso->fso_dentry->d_inode);
- cache_dentry = pre_smfs_dentry(NULL, cache_inode, fso->fso_dentry);
+ cache_dentry = pre_smfs_dentry(NULL, cache_inode, fso->fso_dentry);
if (!cache_dentry)
GOTO(exit, rc = ERR_PTR(-ENOMEM));
} else {
rc = cache_fsfilt->fs_iocontrol(cache_inode, NULL, cmd, arg);
}
-
+#if 0
/* FIXME-UMKA: Should this be in duplicate_inode()? */
if (rc == 0 && cmd == EXT3_IOC_SETFLAGS)
inode->i_flags = cache_inode->i_flags;
-
+#endif
post_smfs_inode(inode, cache_inode);
RETURN(rc);
}
-static int fsfilt_smfs_set_md(struct inode *inode, void *handle,
- void *lmm, int lmm_size)
+typedef int (*set_ea_func_t) (struct inode *, void *, void *, int);
+typedef int (*get_ea_func_t) (struct inode *, void *, int);
+
+static int fsfilt_smfs_set_ea(struct inode *inode, void *handle,
+ void *ea, int ea_size,
+ set_ea_func_t set_ea_func)
{
struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
struct inode *cache_inode = NULL;
if (!cache_inode)
RETURN(-ENOENT);
- pre_smfs_inode(inode, cache_inode);
-
- if (!cache_fsfilt->fs_set_md)
+ if (!set_ea_func)
RETURN(-ENOSYS);
+ pre_smfs_inode(inode, cache_inode);
+
down(&cache_inode->i_sem);
- rc = cache_fsfilt->fs_set_md(cache_inode, handle, lmm, lmm_size);
+ rc = set_ea_func(cache_inode, handle, ea, ea_size);
up(&cache_inode->i_sem);
post_smfs_inode(inode, cache_inode);
- smfs_rec_md(inode, lmm, lmm_size);
-
RETURN(rc);
}
-/* Must be called with i_sem held */
-static int fsfilt_smfs_get_md(struct inode *inode, void *lmm, int lmm_size)
+static int fsfilt_smfs_get_ea(struct inode *inode, void *ea,
+ int ea_size, get_ea_func_t get_ea_func)
{
struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
struct inode *cache_inode = NULL;
if (!cache_inode)
RETURN(-ENOENT);
- pre_smfs_inode(inode, cache_inode);
-
- if (!cache_fsfilt->fs_get_md)
+ if (!get_ea_func)
RETURN(-ENOSYS);
+ pre_smfs_inode(inode, cache_inode);
+
down(&cache_inode->i_sem);
- rc = cache_fsfilt->fs_get_md(cache_inode, lmm, lmm_size);
+ rc = get_ea_func(cache_inode, ea, ea_size);
up(&cache_inode->i_sem);
post_smfs_inode(inode, cache_inode);
RETURN(rc);
}
-#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,5,0))
-static int fsfilt_smfs_send_bio(struct inode *inode, struct bio *bio)
-#else
-static int fsfilt_smfs_send_bio(struct inode *inode, struct kiobuf *bio)
-#endif
+static int fsfilt_smfs_set_md(struct inode *inode, void *handle,
+ void *lmm, int lmm_size)
+{
+ int rc = 0;
+ struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
+
+ rc = fsfilt_smfs_set_ea(inode, handle, lmm, lmm_size,
+ cache_fsfilt->fs_set_md);
+ if (rc)
+ return rc;
+
+ smfs_rec_md(inode, lmm, lmm_size);
+ return rc;
+}
+
+static int fsfilt_smfs_get_md(struct inode *inode, void *lmm, int
+ lmm_size)
+{
+ struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
+ return fsfilt_smfs_get_ea(inode, lmm, lmm_size,
+ cache_fsfilt->fs_get_md);
+}
+
+static int fsfilt_smfs_set_mid(struct inode *inode, void *handle,
+ void *mid, int mid_size)
+{
+ struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
+ return fsfilt_smfs_set_ea(inode, handle, mid, mid_size,
+ cache_fsfilt->fs_set_mid);
+}
+
+static int fsfilt_smfs_get_mid(struct inode *inode, void *mid,
+ int mid_size)
+{
+ struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
+ return fsfilt_smfs_get_ea(inode, mid, mid_size,
+ cache_fsfilt->fs_get_mid);
+}
+
+static int fsfilt_smfs_set_sid(struct inode *inode, void *handle,
+ void *sid, int sid_size)
+{
+ struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
+ return fsfilt_smfs_set_ea(inode, handle, sid, sid_size,
+ cache_fsfilt->fs_set_sid);
+}
+
+static int fsfilt_smfs_get_sid(struct inode *inode, void *sid,
+ int sid_size)
+{
+ struct fsfilt_operations *cache_fsfilt = I2FOPS(inode);
+ return fsfilt_smfs_get_ea(inode, sid, sid_size,
+ cache_fsfilt->fs_get_sid);
+}
+
+static int fsfilt_smfs_send_bio(int rw, struct inode *inode, void *bio)
{
struct inode *cache_inode;
struct fsfilt_operations *cache_fsfilt;
if (!cache_fsfilt->fs_send_bio)
RETURN(-ENOSYS);
- return cache_fsfilt->fs_send_bio(cache_inode, bio);
+ return cache_fsfilt->fs_send_bio(rw, cache_inode, bio);
}
static struct page *
if (!cache_fsfilt->fs_getpage)
RETURN(ERR_PTR(-ENOSYS));
-
+#if CONFIG_SNAPFS
+ if (SMFS_DO_COW(S2SMI(inode->i_sb))) {
+ struct address_space_operations *aops =
+ cache_inode->i_mapping->a_ops;
+ if (aops->bmap(cache_inode->i_mapping, index)) {
+ struct inode *ind_inode = NULL;
+ struct inode *cache_ind = NULL;
+ struct page *page = NULL;
+
+ ind_inode = smfs_cow_get_ind(inode, index);
+ if (!ind_inode) {
+ RETURN(ERR_PTR(-EIO));
+ }
+ cache_ind = I2CI(ind_inode);
+ /*FIXME cow inode should be bottom fs inode */
+ page = cache_fsfilt->fs_getpage(cache_ind, index);
+ iput(ind_inode);
+ RETURN(page);
+ }
+ }
+#endif
return cache_fsfilt->fs_getpage(cache_inode, index);
}
*cache_ppos = *off;
pre_smfs_inode(file->f_dentry->d_inode, cache_inode);
-
+#if CONFIG_SNAPFS
+ /*readdir page*/
+ if (smfs_dotsnap_inode(file->f_dentry->d_inode)) {
+ struct fsfilt_operations *snapops =
+ I2SNAPOPS(file->f_dentry->d_inode);
+
+ LASSERT(S_ISDIR(file->f_dentry->d_inode->i_mode));
+
+ rc = snapops->fs_read_dotsnap_dir_page(sfi->c_file, buf, count,
+ cache_ppos);
+ } else {
+ if (cache_fsfilt->fs_readpage)
+ rc = cache_fsfilt->fs_readpage(sfi->c_file, buf, count,
+ cache_ppos);
+ }
+#else
if (cache_fsfilt->fs_readpage)
rc = cache_fsfilt->fs_readpage(sfi->c_file, buf, count,
cache_ppos);
+#endif
*off = *cache_ppos;
post_smfs_inode(file->f_dentry->d_inode, cache_inode);
duplicate_file(file, sfi->c_file);
RETURN(rc);
}
-static int fsfilt_smfs_post_setup(struct obd_device *obd, struct vfsmount *mnt)
+static int fsfilt_smfs_post_setup(struct obd_device *obd, struct vfsmount *mnt,
+ struct dentry *root_dentry)
{
struct super_block *sb = NULL;
int rc = 0;
if (mnt) {
sb = mnt->mnt_sb;
S2SMI(sb)->smsi_exp = obd->obd_self_export;
+ smfs_post_setup(sb, mnt);
if (SMFS_DO_REC(S2SMI(sb)))
rc = smfs_start_rec(sb, mnt);
if (rc)
{
struct super_block *sb = NULL;
int rc = 0;
-
+ ENTRY;
+
if (mnt) {
sb = mnt->mnt_sb;
if (SMFS_DO_REC(S2SMI(sb)))
rc = smfs_stop_rec(sb);
+ smfs_post_cleanup(sb);
}
RETURN(rc);
}
-static int fsfilt_smfs_set_kml_flags(struct inode *inode)
+static int fsfilt_smfs_set_fs_flags(struct inode *inode, int flags)
{
int rc = 0;
- if (SMFS_DO_REC(S2SMI(inode->i_sb)))
+ ENTRY;
+
+ if (SMFS_DO_REC(S2SMI(inode->i_sb)) && (flags & SM_DO_REC))
SMFS_SET_INODE_REC(inode);
+ if (SMFS_DO_COW(S2SMI(inode->i_sb)) && (flags & SM_DO_COW))
+ SMFS_SET_INODE_COW(inode);
RETURN(rc);
}
-static int fsfilt_smfs_clear_kml_flags(struct inode *inode)
+static int fsfilt_smfs_clear_fs_flags(struct inode *inode, int flags)
{
int rc = 0;
- if (SMFS_DO_REC(S2SMI(inode->i_sb)))
+ ENTRY;
+
+ if (SMFS_DO_REC(S2SMI(inode->i_sb)) && (flags & SM_DO_REC))
SMFS_CLEAN_INODE_REC(inode);
+ if (SMFS_DO_COW(S2SMI(inode->i_sb)) && (flags & SM_DO_COW))
+ SMFS_CLEAN_INODE_COW(inode);
RETURN(rc);
}
+static int fsfilt_smfs_get_fs_flags(struct dentry *de)
+{
+ struct inode *inode = de->d_inode;
+ int flags = 0;
+ ENTRY;
+
+ LASSERT(inode);
+
+ if (SMFS_DO_REC(S2SMI(inode->i_sb)) && SMFS_DO_INODE_REC(inode))
+ flags |= SM_DO_REC;
+ if (SMFS_DO_COW(S2SMI(inode->i_sb)) && SMFS_DO_INODE_COW(inode))
+ flags |= SM_DO_COW;
+
+ RETURN(flags);
+}
static int fsfilt_smfs_set_ost_flags(struct super_block *sb)
{
int rc = 0;
csb = S2CSB(sb);
if (cache_fsfilt->fs_setup)
rc = cache_fsfilt->fs_setup(obd, csb);
+
+ duplicate_sb(sb, csb);
+
RETURN(rc);
}
ENTRY;
#if CONFIG_SNAPFS
- rc = smfs_add_snap_item(sb, name);
+#warning "still not implement for add snap item -wangdi"
#endif
RETURN(rc);
}
-
+static int fsfilt_smfs_do_write_cow(struct dentry *de, void *extents,
+ int num_extents)
+{
+ int rc = 0;
+#if CONFIG_SNAPFS
+ struct write_extents *w_ext = (struct write_extents *)extents;
+ int i = 0;
+ ENTRY;
+ for (i = 0; i < num_extents; i++) {
+ size_t count = w_ext->w_count;
+ loff_t off = w_ext->w_pos;
+ rc = smfs_cow_write_pre(de->d_inode, de, &count, &off);
+ if (rc)
+ RETURN(rc);
+ w_ext ++;
+ }
+#endif
+ RETURN(rc);
+}
static struct fsfilt_operations fsfilt_smfs_ops = {
.fs_type = "smfs",
.fs_owner = THIS_MODULE,
.fs_iocontrol = fsfilt_smfs_iocontrol,
.fs_set_md = fsfilt_smfs_set_md,
.fs_get_md = fsfilt_smfs_get_md,
+ .fs_set_mid = fsfilt_smfs_set_mid,
+ .fs_get_mid = fsfilt_smfs_get_mid,
+ .fs_set_sid = fsfilt_smfs_set_sid,
+ .fs_get_sid = fsfilt_smfs_get_sid,
.fs_readpage = fsfilt_smfs_readpage,
.fs_getpage = fsfilt_smfs_getpage,
.fs_add_journal_cb = fsfilt_smfs_add_journal_cb,
.fs_setup = fsfilt_smfs_setup,
.fs_post_setup = fsfilt_smfs_post_setup,
.fs_post_cleanup = fsfilt_smfs_post_cleanup,
- .fs_set_kml_flags = fsfilt_smfs_set_kml_flags,
- .fs_clear_kml_flags = fsfilt_smfs_clear_kml_flags,
+ .fs_set_fs_flags = fsfilt_smfs_set_fs_flags,
+ .fs_clear_fs_flags = fsfilt_smfs_clear_fs_flags,
+ .fs_get_fs_flags = fsfilt_smfs_get_fs_flags,
.fs_set_ost_flags = fsfilt_smfs_set_ost_flags,
.fs_set_mds_flags = fsfilt_smfs_set_mds_flags,
.fs_precreate_rec = fsfilt_smfs_precreate_rec,
.fs_free_write_extents = fsfilt_smfs_free_extents,
.fs_write_extents = fsfilt_smfs_write_extents,
.fs_set_snap_item = fsfilt_smfs_set_snap_item,
-
- /* FIXME-UMKA: probably fsfilt_smfs_get_op_len() should be
- * put here too. */
+ .fs_do_write_cow = fsfilt_smfs_do_write_cow,
};
static int __init fsfilt_smfs_init(void)