->encode_fh() API change

pass inode + parent's inode or NULL instead of dentry + bool saying
whether we want the parent or not.

NOTE: that needs ceph fix folded in.

Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
Al Viro 2012-04-02 14:34:06 -04:00
parent 6d42e7e9f6
commit b0b0382bb4
16 changed files with 93 additions and 139 deletions

View File

@ -13,15 +13,14 @@
parent_root_objectid) / 4) parent_root_objectid) / 4)
#define BTRFS_FID_SIZE_CONNECTABLE_ROOT (sizeof(struct btrfs_fid) / 4) #define BTRFS_FID_SIZE_CONNECTABLE_ROOT (sizeof(struct btrfs_fid) / 4)
static int btrfs_encode_fh(struct dentry *dentry, u32 *fh, int *max_len, static int btrfs_encode_fh(struct inode *inode, u32 *fh, int *max_len,
int connectable) struct inode *parent)
{ {
struct btrfs_fid *fid = (struct btrfs_fid *)fh; struct btrfs_fid *fid = (struct btrfs_fid *)fh;
struct inode *inode = dentry->d_inode;
int len = *max_len; int len = *max_len;
int type; int type;
if (connectable && (len < BTRFS_FID_SIZE_CONNECTABLE)) { if (parent && (len < BTRFS_FID_SIZE_CONNECTABLE)) {
*max_len = BTRFS_FID_SIZE_CONNECTABLE; *max_len = BTRFS_FID_SIZE_CONNECTABLE;
return 255; return 255;
} else if (len < BTRFS_FID_SIZE_NON_CONNECTABLE) { } else if (len < BTRFS_FID_SIZE_NON_CONNECTABLE) {
@ -36,19 +35,13 @@ static int btrfs_encode_fh(struct dentry *dentry, u32 *fh, int *max_len,
fid->root_objectid = BTRFS_I(inode)->root->objectid; fid->root_objectid = BTRFS_I(inode)->root->objectid;
fid->gen = inode->i_generation; fid->gen = inode->i_generation;
if (connectable && !S_ISDIR(inode->i_mode)) { if (parent) {
struct inode *parent;
u64 parent_root_id; u64 parent_root_id;
spin_lock(&dentry->d_lock);
parent = dentry->d_parent->d_inode;
fid->parent_objectid = BTRFS_I(parent)->location.objectid; fid->parent_objectid = BTRFS_I(parent)->location.objectid;
fid->parent_gen = parent->i_generation; fid->parent_gen = parent->i_generation;
parent_root_id = BTRFS_I(parent)->root->objectid; parent_root_id = BTRFS_I(parent)->root->objectid;
spin_unlock(&dentry->d_lock);
if (parent_root_id != fid->root_objectid) { if (parent_root_id != fid->root_objectid) {
fid->parent_root_objectid = parent_root_id; fid->parent_root_objectid = parent_root_id;
len = BTRFS_FID_SIZE_CONNECTABLE_ROOT; len = BTRFS_FID_SIZE_CONNECTABLE_ROOT;

View File

@ -247,7 +247,9 @@ static struct dentry *ceph_fh_to_parent(struct super_block *sb,
} }
const struct export_operations ceph_export_ops = { const struct export_operations ceph_export_ops = {
#ifdef CEPH_BREAKAGE_FIXED
.encode_fh = ceph_encode_fh, .encode_fh = ceph_encode_fh,
#endif
.fh_to_dentry = ceph_fh_to_dentry, .fh_to_dentry = ceph_fh_to_dentry,
.fh_to_parent = ceph_fh_to_parent, .fh_to_parent = ceph_fh_to_parent,
}; };

View File

@ -304,24 +304,23 @@ out:
/** /**
* export_encode_fh - default export_operations->encode_fh function * export_encode_fh - default export_operations->encode_fh function
* @dentry: the dentry to encode * @inode: the object to encode
* @fh: where to store the file handle fragment * @fh: where to store the file handle fragment
* @max_len: maximum length to store there * @max_len: maximum length to store there
* @connectable: whether to store parent information * @parent: parent directory inode, if wanted
* *
* This default encode_fh function assumes that the 32 inode number * This default encode_fh function assumes that the 32 inode number
* is suitable for locating an inode, and that the generation number * is suitable for locating an inode, and that the generation number
* can be used to check that it is still valid. It places them in the * can be used to check that it is still valid. It places them in the
* filehandle fragment where export_decode_fh expects to find them. * filehandle fragment where export_decode_fh expects to find them.
*/ */
static int export_encode_fh(struct dentry *dentry, struct fid *fid, static int export_encode_fh(struct inode *inode, struct fid *fid,
int *max_len, int connectable) int *max_len, struct inode *parent)
{ {
struct inode * inode = dentry->d_inode;
int len = *max_len; int len = *max_len;
int type = FILEID_INO32_GEN; int type = FILEID_INO32_GEN;
if (connectable && (len < 4)) { if (parent && (len < 4)) {
*max_len = 4; *max_len = 4;
return 255; return 255;
} else if (len < 2) { } else if (len < 2) {
@ -332,14 +331,9 @@ static int export_encode_fh(struct dentry *dentry, struct fid *fid,
len = 2; len = 2;
fid->i32.ino = inode->i_ino; fid->i32.ino = inode->i_ino;
fid->i32.gen = inode->i_generation; fid->i32.gen = inode->i_generation;
if (connectable && !S_ISDIR(inode->i_mode)) { if (parent) {
struct inode *parent;
spin_lock(&dentry->d_lock);
parent = dentry->d_parent->d_inode;
fid->i32.parent_ino = parent->i_ino; fid->i32.parent_ino = parent->i_ino;
fid->i32.parent_gen = parent->i_generation; fid->i32.parent_gen = parent->i_generation;
spin_unlock(&dentry->d_lock);
len = 4; len = 4;
type = FILEID_INO32_GEN_PARENT; type = FILEID_INO32_GEN_PARENT;
} }
@ -352,11 +346,22 @@ int exportfs_encode_fh(struct dentry *dentry, struct fid *fid, int *max_len,
{ {
const struct export_operations *nop = dentry->d_sb->s_export_op; const struct export_operations *nop = dentry->d_sb->s_export_op;
int error; int error;
struct dentry *p = NULL;
struct inode *inode = dentry->d_inode, *parent = NULL;
if (connectable && !S_ISDIR(inode->i_mode)) {
p = dget_parent(dentry);
/*
* note that while p might've ceased to be our parent already,
* it's still pinned by and still positive.
*/
parent = p->d_inode;
}
if (nop->encode_fh) if (nop->encode_fh)
error = nop->encode_fh(dentry, fid->raw, max_len, connectable); error = nop->encode_fh(inode, fid->raw, max_len, parent);
else else
error = export_encode_fh(dentry, fid, max_len, connectable); error = export_encode_fh(inode, fid, max_len, parent);
dput(p);
return error; return error;
} }

View File

@ -752,10 +752,9 @@ static struct dentry *fat_fh_to_dentry(struct super_block *sb,
} }
static int static int
fat_encode_fh(struct dentry *de, __u32 *fh, int *lenp, int connectable) fat_encode_fh(struct inode *inode, __u32 *fh, int *lenp, struct inode *parent)
{ {
int len = *lenp; int len = *lenp;
struct inode *inode = de->d_inode;
u32 ipos_h, ipos_m, ipos_l; u32 ipos_h, ipos_m, ipos_l;
if (len < 5) { if (len < 5) {
@ -771,9 +770,9 @@ fat_encode_fh(struct dentry *de, __u32 *fh, int *lenp, int connectable)
fh[1] = inode->i_generation; fh[1] = inode->i_generation;
fh[2] = ipos_h; fh[2] = ipos_h;
fh[3] = ipos_m | MSDOS_I(inode)->i_logstart; fh[3] = ipos_m | MSDOS_I(inode)->i_logstart;
spin_lock(&de->d_lock); fh[4] = ipos_l;
fh[4] = ipos_l | MSDOS_I(de->d_parent->d_inode)->i_logstart; if (parent)
spin_unlock(&de->d_lock); fh[4] |= MSDOS_I(parent)->i_logstart;
return 3; return 3;
} }

View File

@ -627,12 +627,10 @@ static struct dentry *fuse_get_dentry(struct super_block *sb,
return ERR_PTR(err); return ERR_PTR(err);
} }
static int fuse_encode_fh(struct dentry *dentry, u32 *fh, int *max_len, static int fuse_encode_fh(struct inode *inode, u32 *fh, int *max_len,
int connectable) struct inode *parent)
{ {
struct inode *inode = dentry->d_inode; int len = parent ? 6 : 3;
bool encode_parent = connectable && !S_ISDIR(inode->i_mode);
int len = encode_parent ? 6 : 3;
u64 nodeid; u64 nodeid;
u32 generation; u32 generation;
@ -648,14 +646,9 @@ static int fuse_encode_fh(struct dentry *dentry, u32 *fh, int *max_len,
fh[1] = (u32)(nodeid & 0xffffffff); fh[1] = (u32)(nodeid & 0xffffffff);
fh[2] = generation; fh[2] = generation;
if (encode_parent) { if (parent) {
struct inode *parent;
spin_lock(&dentry->d_lock);
parent = dentry->d_parent->d_inode;
nodeid = get_fuse_inode(parent)->nodeid; nodeid = get_fuse_inode(parent)->nodeid;
generation = parent->i_generation; generation = parent->i_generation;
spin_unlock(&dentry->d_lock);
fh[3] = (u32)(nodeid >> 32); fh[3] = (u32)(nodeid >> 32);
fh[4] = (u32)(nodeid & 0xffffffff); fh[4] = (u32)(nodeid & 0xffffffff);
@ -663,7 +656,7 @@ static int fuse_encode_fh(struct dentry *dentry, u32 *fh, int *max_len,
} }
*max_len = len; *max_len = len;
return encode_parent ? 0x82 : 0x81; return parent ? 0x82 : 0x81;
} }
static struct dentry *fuse_fh_to_dentry(struct super_block *sb, static struct dentry *fuse_fh_to_dentry(struct super_block *sb,

View File

@ -28,15 +28,14 @@
#define GFS2_LARGE_FH_SIZE 8 #define GFS2_LARGE_FH_SIZE 8
#define GFS2_OLD_FH_SIZE 10 #define GFS2_OLD_FH_SIZE 10
static int gfs2_encode_fh(struct dentry *dentry, __u32 *p, int *len, static int gfs2_encode_fh(struct inode *inode, __u32 *p, int *len,
int connectable) struct inode *parent)
{ {
__be32 *fh = (__force __be32 *)p; __be32 *fh = (__force __be32 *)p;
struct inode *inode = dentry->d_inode;
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
struct gfs2_inode *ip = GFS2_I(inode); struct gfs2_inode *ip = GFS2_I(inode);
if (connectable && (*len < GFS2_LARGE_FH_SIZE)) { if (parent && (*len < GFS2_LARGE_FH_SIZE)) {
*len = GFS2_LARGE_FH_SIZE; *len = GFS2_LARGE_FH_SIZE;
return 255; return 255;
} else if (*len < GFS2_SMALL_FH_SIZE) { } else if (*len < GFS2_SMALL_FH_SIZE) {
@ -50,14 +49,10 @@ static int gfs2_encode_fh(struct dentry *dentry, __u32 *p, int *len,
fh[3] = cpu_to_be32(ip->i_no_addr & 0xFFFFFFFF); fh[3] = cpu_to_be32(ip->i_no_addr & 0xFFFFFFFF);
*len = GFS2_SMALL_FH_SIZE; *len = GFS2_SMALL_FH_SIZE;
if (!connectable || inode == sb->s_root->d_inode) if (!parent || inode == sb->s_root->d_inode)
return *len; return *len;
spin_lock(&dentry->d_lock); ip = GFS2_I(parent);
inode = dentry->d_parent->d_inode;
ip = GFS2_I(inode);
igrab(inode);
spin_unlock(&dentry->d_lock);
fh[4] = cpu_to_be32(ip->i_no_formal_ino >> 32); fh[4] = cpu_to_be32(ip->i_no_formal_ino >> 32);
fh[5] = cpu_to_be32(ip->i_no_formal_ino & 0xFFFFFFFF); fh[5] = cpu_to_be32(ip->i_no_formal_ino & 0xFFFFFFFF);
@ -65,8 +60,6 @@ static int gfs2_encode_fh(struct dentry *dentry, __u32 *p, int *len,
fh[7] = cpu_to_be32(ip->i_no_addr & 0xFFFFFFFF); fh[7] = cpu_to_be32(ip->i_no_addr & 0xFFFFFFFF);
*len = GFS2_LARGE_FH_SIZE; *len = GFS2_LARGE_FH_SIZE;
iput(inode);
return *len; return *len;
} }

View File

@ -107,12 +107,11 @@ static struct dentry *isofs_export_get_parent(struct dentry *child)
} }
static int static int
isofs_export_encode_fh(struct dentry *dentry, isofs_export_encode_fh(struct inode *inode,
__u32 *fh32, __u32 *fh32,
int *max_len, int *max_len,
int connectable) struct inode *parent)
{ {
struct inode * inode = dentry->d_inode;
struct iso_inode_info * ei = ISOFS_I(inode); struct iso_inode_info * ei = ISOFS_I(inode);
int len = *max_len; int len = *max_len;
int type = 1; int type = 1;
@ -124,7 +123,7 @@ isofs_export_encode_fh(struct dentry *dentry,
* offset of the inode and the upper 16 bits of fh32[1] to * offset of the inode and the upper 16 bits of fh32[1] to
* hold the offset of the parent. * hold the offset of the parent.
*/ */
if (connectable && (len < 5)) { if (parent && (len < 5)) {
*max_len = 5; *max_len = 5;
return 255; return 255;
} else if (len < 3) { } else if (len < 3) {
@ -136,16 +135,12 @@ isofs_export_encode_fh(struct dentry *dentry,
fh32[0] = ei->i_iget5_block; fh32[0] = ei->i_iget5_block;
fh16[2] = (__u16)ei->i_iget5_offset; /* fh16 [sic] */ fh16[2] = (__u16)ei->i_iget5_offset; /* fh16 [sic] */
fh32[2] = inode->i_generation; fh32[2] = inode->i_generation;
if (connectable && !S_ISDIR(inode->i_mode)) { if (parent) {
struct inode *parent;
struct iso_inode_info *eparent; struct iso_inode_info *eparent;
spin_lock(&dentry->d_lock);
parent = dentry->d_parent->d_inode;
eparent = ISOFS_I(parent); eparent = ISOFS_I(parent);
fh32[3] = eparent->i_iget5_block; fh32[3] = eparent->i_iget5_block;
fh16[3] = (__u16)eparent->i_iget5_offset; /* fh16 [sic] */ fh16[3] = (__u16)eparent->i_iget5_offset; /* fh16 [sic] */
fh32[4] = parent->i_generation; fh32[4] = parent->i_generation;
spin_unlock(&dentry->d_lock);
len = 5; len = 5;
type = 2; type = 2;
} }

View File

@ -508,31 +508,29 @@ static struct dentry *nilfs_fh_to_parent(struct super_block *sb, struct fid *fh,
return nilfs_get_dentry(sb, fid->cno, fid->parent_ino, fid->parent_gen); return nilfs_get_dentry(sb, fid->cno, fid->parent_ino, fid->parent_gen);
} }
static int nilfs_encode_fh(struct dentry *dentry, __u32 *fh, int *lenp, static int nilfs_encode_fh(struct inode *inode, __u32 *fh, int *lenp,
int connectable) struct inode *parent)
{ {
struct nilfs_fid *fid = (struct nilfs_fid *)fh; struct nilfs_fid *fid = (struct nilfs_fid *)fh;
struct inode *inode = dentry->d_inode;
struct nilfs_root *root = NILFS_I(inode)->i_root; struct nilfs_root *root = NILFS_I(inode)->i_root;
int type; int type;
if (*lenp < NILFS_FID_SIZE_NON_CONNECTABLE || if (parent && *lenp < NILFS_FID_SIZE_CONNECTABLE) {
(connectable && *lenp < NILFS_FID_SIZE_CONNECTABLE)) *lenp = NILFS_FID_SIZE_CONNECTABLE;
return 255; return 255;
}
if (*lenp < NILFS_FID_SIZE_NON_CONNECTABLE) {
*lenp = NILFS_FID_SIZE_NON_CONNECTABLE;
return 255;
}
fid->cno = root->cno; fid->cno = root->cno;
fid->ino = inode->i_ino; fid->ino = inode->i_ino;
fid->gen = inode->i_generation; fid->gen = inode->i_generation;
if (connectable && !S_ISDIR(inode->i_mode)) { if (parent) {
struct inode *parent;
spin_lock(&dentry->d_lock);
parent = dentry->d_parent->d_inode;
fid->parent_ino = parent->i_ino; fid->parent_ino = parent->i_ino;
fid->parent_gen = parent->i_generation; fid->parent_gen = parent->i_generation;
spin_unlock(&dentry->d_lock);
type = FILEID_NILFS_WITH_PARENT; type = FILEID_NILFS_WITH_PARENT;
*lenp = NILFS_FID_SIZE_CONNECTABLE; *lenp = NILFS_FID_SIZE_CONNECTABLE;
} else { } else {

View File

@ -177,21 +177,23 @@ bail:
return parent; return parent;
} }
static int ocfs2_encode_fh(struct dentry *dentry, u32 *fh_in, int *max_len, static int ocfs2_encode_fh(struct inode *inode, u32 *fh_in, int *max_len,
int connectable) struct inode *parent)
{ {
struct inode *inode = dentry->d_inode;
int len = *max_len; int len = *max_len;
int type = 1; int type = 1;
u64 blkno; u64 blkno;
u32 generation; u32 generation;
__le32 *fh = (__force __le32 *) fh_in; __le32 *fh = (__force __le32 *) fh_in;
#ifdef TRACE_HOOKS_ARE_NOT_BRAINDEAD_IN_YOUR_OPINION
#error "You go ahead and fix that mess, then. Somehow"
trace_ocfs2_encode_fh_begin(dentry, dentry->d_name.len, trace_ocfs2_encode_fh_begin(dentry, dentry->d_name.len,
dentry->d_name.name, dentry->d_name.name,
fh, len, connectable); fh, len, connectable);
#endif
if (connectable && (len < 6)) { if (parent && (len < 6)) {
*max_len = 6; *max_len = 6;
type = 255; type = 255;
goto bail; goto bail;
@ -211,12 +213,7 @@ static int ocfs2_encode_fh(struct dentry *dentry, u32 *fh_in, int *max_len,
fh[1] = cpu_to_le32((u32)(blkno & 0xffffffff)); fh[1] = cpu_to_le32((u32)(blkno & 0xffffffff));
fh[2] = cpu_to_le32(generation); fh[2] = cpu_to_le32(generation);
if (connectable && !S_ISDIR(inode->i_mode)) { if (parent) {
struct inode *parent;
spin_lock(&dentry->d_lock);
parent = dentry->d_parent->d_inode;
blkno = OCFS2_I(parent)->ip_blkno; blkno = OCFS2_I(parent)->ip_blkno;
generation = parent->i_generation; generation = parent->i_generation;
@ -224,8 +221,6 @@ static int ocfs2_encode_fh(struct dentry *dentry, u32 *fh_in, int *max_len,
fh[4] = cpu_to_le32((u32)(blkno & 0xffffffff)); fh[4] = cpu_to_le32((u32)(blkno & 0xffffffff));
fh[5] = cpu_to_le32(generation); fh[5] = cpu_to_le32(generation);
spin_unlock(&dentry->d_lock);
len = 6; len = 6;
type = 2; type = 2;

View File

@ -1592,13 +1592,12 @@ struct dentry *reiserfs_fh_to_parent(struct super_block *sb, struct fid *fid,
(fh_type == 6) ? fid->raw[5] : 0); (fh_type == 6) ? fid->raw[5] : 0);
} }
int reiserfs_encode_fh(struct dentry *dentry, __u32 * data, int *lenp, int reiserfs_encode_fh(struct inode *inode, __u32 * data, int *lenp,
int need_parent) struct inode *parent)
{ {
struct inode *inode = dentry->d_inode;
int maxlen = *lenp; int maxlen = *lenp;
if (need_parent && (maxlen < 5)) { if (parent && (maxlen < 5)) {
*lenp = 5; *lenp = 5;
return 255; return 255;
} else if (maxlen < 3) { } else if (maxlen < 3) {
@ -1610,20 +1609,15 @@ int reiserfs_encode_fh(struct dentry *dentry, __u32 * data, int *lenp,
data[1] = le32_to_cpu(INODE_PKEY(inode)->k_dir_id); data[1] = le32_to_cpu(INODE_PKEY(inode)->k_dir_id);
data[2] = inode->i_generation; data[2] = inode->i_generation;
*lenp = 3; *lenp = 3;
/* no room for directory info? return what we've stored so far */ if (parent) {
if (maxlen < 5 || !need_parent) data[3] = parent->i_ino;
return 3; data[4] = le32_to_cpu(INODE_PKEY(parent)->k_dir_id);
spin_lock(&dentry->d_lock);
inode = dentry->d_parent->d_inode;
data[3] = inode->i_ino;
data[4] = le32_to_cpu(INODE_PKEY(inode)->k_dir_id);
*lenp = 5; *lenp = 5;
if (maxlen >= 6) { if (maxlen >= 6) {
data[5] = inode->i_generation; data[5] = parent->i_generation;
*lenp = 6; *lenp = 6;
} }
spin_unlock(&dentry->d_lock); }
return *lenp; return *lenp;
} }

View File

@ -2611,8 +2611,8 @@ struct dentry *reiserfs_fh_to_dentry(struct super_block *sb, struct fid *fid,
int fh_len, int fh_type); int fh_len, int fh_type);
struct dentry *reiserfs_fh_to_parent(struct super_block *sb, struct fid *fid, struct dentry *reiserfs_fh_to_parent(struct super_block *sb, struct fid *fid,
int fh_len, int fh_type); int fh_len, int fh_type);
int reiserfs_encode_fh(struct dentry *dentry, __u32 * data, int *lenp, int reiserfs_encode_fh(struct inode *inode, __u32 * data, int *lenp,
int connectable); struct inode *parent);
int reiserfs_truncate_file(struct inode *, int update_timestamps); int reiserfs_truncate_file(struct inode *, int update_timestamps);
void make_cpu_key(struct cpu_key *cpu_key, struct inode *inode, loff_t offset, void make_cpu_key(struct cpu_key *cpu_key, struct inode *inode, loff_t offset,

View File

@ -1260,16 +1260,15 @@ static struct dentry *udf_fh_to_parent(struct super_block *sb,
fid->udf.parent_partref, fid->udf.parent_partref,
fid->udf.parent_generation); fid->udf.parent_generation);
} }
static int udf_encode_fh(struct dentry *de, __u32 *fh, int *lenp, static int udf_encode_fh(struct inode *inode, __u32 *fh, int *lenp,
int connectable) struct inode *parent)
{ {
int len = *lenp; int len = *lenp;
struct inode *inode = de->d_inode;
struct kernel_lb_addr location = UDF_I(inode)->i_location; struct kernel_lb_addr location = UDF_I(inode)->i_location;
struct fid *fid = (struct fid *)fh; struct fid *fid = (struct fid *)fh;
int type = FILEID_UDF_WITHOUT_PARENT; int type = FILEID_UDF_WITHOUT_PARENT;
if (connectable && (len < 5)) { if (parent && (len < 5)) {
*lenp = 5; *lenp = 5;
return 255; return 255;
} else if (len < 3) { } else if (len < 3) {
@ -1282,14 +1281,11 @@ static int udf_encode_fh(struct dentry *de, __u32 *fh, int *lenp,
fid->udf.partref = location.partitionReferenceNum; fid->udf.partref = location.partitionReferenceNum;
fid->udf.generation = inode->i_generation; fid->udf.generation = inode->i_generation;
if (connectable && !S_ISDIR(inode->i_mode)) { if (parent) {
spin_lock(&de->d_lock); location = UDF_I(parent)->i_location;
inode = de->d_parent->d_inode;
location = UDF_I(inode)->i_location;
fid->udf.parent_block = location.logicalBlockNum; fid->udf.parent_block = location.logicalBlockNum;
fid->udf.parent_partref = location.partitionReferenceNum; fid->udf.parent_partref = location.partitionReferenceNum;
fid->udf.parent_generation = inode->i_generation; fid->udf.parent_generation = inode->i_generation;
spin_unlock(&de->d_lock);
*lenp = 5; *lenp = 5;
type = FILEID_UDF_WITH_PARENT; type = FILEID_UDF_WITH_PARENT;
} }

View File

@ -52,19 +52,18 @@ static int xfs_fileid_length(int fileid_type)
STATIC int STATIC int
xfs_fs_encode_fh( xfs_fs_encode_fh(
struct dentry *dentry, struct inode *inode,
__u32 *fh, __u32 *fh,
int *max_len, int *max_len,
int connectable) struct inode *parent)
{ {
struct fid *fid = (struct fid *)fh; struct fid *fid = (struct fid *)fh;
struct xfs_fid64 *fid64 = (struct xfs_fid64 *)fh; struct xfs_fid64 *fid64 = (struct xfs_fid64 *)fh;
struct inode *inode = dentry->d_inode;
int fileid_type; int fileid_type;
int len; int len;
/* Directories don't need their parent encoded, they have ".." */ /* Directories don't need their parent encoded, they have ".." */
if (S_ISDIR(inode->i_mode) || !connectable) if (!parent)
fileid_type = FILEID_INO32_GEN; fileid_type = FILEID_INO32_GEN;
else else
fileid_type = FILEID_INO32_GEN_PARENT; fileid_type = FILEID_INO32_GEN_PARENT;
@ -96,20 +95,16 @@ xfs_fs_encode_fh(
switch (fileid_type) { switch (fileid_type) {
case FILEID_INO32_GEN_PARENT: case FILEID_INO32_GEN_PARENT:
spin_lock(&dentry->d_lock); fid->i32.parent_ino = XFS_I(parent)->i_ino;
fid->i32.parent_ino = XFS_I(dentry->d_parent->d_inode)->i_ino; fid->i32.parent_gen = parent->i_generation;
fid->i32.parent_gen = dentry->d_parent->d_inode->i_generation;
spin_unlock(&dentry->d_lock);
/*FALLTHRU*/ /*FALLTHRU*/
case FILEID_INO32_GEN: case FILEID_INO32_GEN:
fid->i32.ino = XFS_I(inode)->i_ino; fid->i32.ino = XFS_I(inode)->i_ino;
fid->i32.gen = inode->i_generation; fid->i32.gen = inode->i_generation;
break; break;
case FILEID_INO32_GEN_PARENT | XFS_FILEID_TYPE_64FLAG: case FILEID_INO32_GEN_PARENT | XFS_FILEID_TYPE_64FLAG:
spin_lock(&dentry->d_lock); fid64->parent_ino = XFS_I(parent)->i_ino;
fid64->parent_ino = XFS_I(dentry->d_parent->d_inode)->i_ino; fid64->parent_gen = parent->i_generation;
fid64->parent_gen = dentry->d_parent->d_inode->i_generation;
spin_unlock(&dentry->d_lock);
/*FALLTHRU*/ /*FALLTHRU*/
case FILEID_INO32_GEN | XFS_FILEID_TYPE_64FLAG: case FILEID_INO32_GEN | XFS_FILEID_TYPE_64FLAG:
fid64->ino = XFS_I(inode)->i_ino; fid64->ino = XFS_I(inode)->i_ino;

View File

@ -165,8 +165,8 @@ struct fid {
*/ */
struct export_operations { struct export_operations {
int (*encode_fh)(struct dentry *de, __u32 *fh, int *max_len, int (*encode_fh)(struct inode *inode, __u32 *fh, int *max_len,
int connectable); struct inode *parent);
struct dentry * (*fh_to_dentry)(struct super_block *sb, struct fid *fid, struct dentry * (*fh_to_dentry)(struct super_block *sb, struct fid *fid,
int fh_len, int fh_type); int fh_len, int fh_type);
struct dentry * (*fh_to_parent)(struct super_block *sb, struct fid *fid, struct dentry * (*fh_to_parent)(struct super_block *sb, struct fid *fid,

View File

@ -80,7 +80,7 @@ EXPORT_SYMBOL(__cleancache_init_shared_fs);
static int cleancache_get_key(struct inode *inode, static int cleancache_get_key(struct inode *inode,
struct cleancache_filekey *key) struct cleancache_filekey *key)
{ {
int (*fhfn)(struct dentry *, __u32 *fh, int *, int); int (*fhfn)(struct inode *, __u32 *fh, int *, struct inode *);
int len = 0, maxlen = CLEANCACHE_KEY_MAX; int len = 0, maxlen = CLEANCACHE_KEY_MAX;
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
@ -88,9 +88,7 @@ static int cleancache_get_key(struct inode *inode,
if (sb->s_export_op != NULL) { if (sb->s_export_op != NULL) {
fhfn = sb->s_export_op->encode_fh; fhfn = sb->s_export_op->encode_fh;
if (fhfn) { if (fhfn) {
struct dentry d; len = (*fhfn)(inode, &key->u.fh[0], &maxlen, NULL);
d.d_inode = inode;
len = (*fhfn)(&d, &key->u.fh[0], &maxlen, 0);
if (len <= 0 || len == 255) if (len <= 0 || len == 255)
return -1; return -1;
if (maxlen > CLEANCACHE_KEY_MAX) if (maxlen > CLEANCACHE_KEY_MAX)

View File

@ -2033,11 +2033,9 @@ static struct dentry *shmem_fh_to_dentry(struct super_block *sb,
return dentry; return dentry;
} }
static int shmem_encode_fh(struct dentry *dentry, __u32 *fh, int *len, static int shmem_encode_fh(struct inode *inode, __u32 *fh, int *len,
int connectable) struct inode *parent)
{ {
struct inode *inode = dentry->d_inode;
if (*len < 3) { if (*len < 3) {
*len = 3; *len = 3;
return 255; return 255;