diff options
Diffstat (limited to 'fs/ceph/export.c')
-rw-r--r-- | fs/ceph/export.c | 24 |
1 files changed, 15 insertions, 9 deletions
diff --git a/fs/ceph/export.c b/fs/ceph/export.c index f67b687550de..9fbcdecaaccd 100644 --- a/fs/ceph/export.c +++ b/fs/ceph/export.c | |||
@@ -46,7 +46,7 @@ static int ceph_encode_fh(struct dentry *dentry, u32 *rawfh, int *max_len, | |||
46 | int type; | 46 | int type; |
47 | struct ceph_nfs_fh *fh = (void *)rawfh; | 47 | struct ceph_nfs_fh *fh = (void *)rawfh; |
48 | struct ceph_nfs_confh *cfh = (void *)rawfh; | 48 | struct ceph_nfs_confh *cfh = (void *)rawfh; |
49 | struct dentry *parent = dentry->d_parent; | 49 | struct dentry *parent; |
50 | struct inode *inode = dentry->d_inode; | 50 | struct inode *inode = dentry->d_inode; |
51 | int connected_handle_length = sizeof(*cfh)/4; | 51 | int connected_handle_length = sizeof(*cfh)/4; |
52 | int handle_length = sizeof(*fh)/4; | 52 | int handle_length = sizeof(*fh)/4; |
@@ -55,26 +55,33 @@ static int ceph_encode_fh(struct dentry *dentry, u32 *rawfh, int *max_len, | |||
55 | if (ceph_snap(inode) != CEPH_NOSNAP) | 55 | if (ceph_snap(inode) != CEPH_NOSNAP) |
56 | return -EINVAL; | 56 | return -EINVAL; |
57 | 57 | ||
58 | spin_lock(&dentry->d_lock); | ||
59 | parent = dget(dentry->d_parent); | ||
60 | spin_unlock(&dentry->d_lock); | ||
61 | |||
58 | if (*max_len >= connected_handle_length) { | 62 | if (*max_len >= connected_handle_length) { |
59 | dout("encode_fh %p connectable\n", dentry); | 63 | dout("encode_fh %p connectable\n", dentry); |
60 | cfh->ino = ceph_ino(dentry->d_inode); | 64 | cfh->ino = ceph_ino(dentry->d_inode); |
61 | cfh->parent_ino = ceph_ino(parent->d_inode); | 65 | cfh->parent_ino = ceph_ino(parent->d_inode); |
62 | cfh->parent_name_hash = ceph_dentry_hash(parent); | 66 | cfh->parent_name_hash = ceph_dentry_hash(parent->d_inode, |
67 | dentry); | ||
63 | *max_len = connected_handle_length; | 68 | *max_len = connected_handle_length; |
64 | type = 2; | 69 | type = 2; |
65 | } else if (*max_len >= handle_length) { | 70 | } else if (*max_len >= handle_length) { |
66 | if (connectable) { | 71 | if (connectable) { |
67 | *max_len = connected_handle_length; | 72 | *max_len = connected_handle_length; |
68 | return 255; | 73 | type = 255; |
74 | } else { | ||
75 | dout("encode_fh %p\n", dentry); | ||
76 | fh->ino = ceph_ino(dentry->d_inode); | ||
77 | *max_len = handle_length; | ||
78 | type = 1; | ||
69 | } | 79 | } |
70 | dout("encode_fh %p\n", dentry); | ||
71 | fh->ino = ceph_ino(dentry->d_inode); | ||
72 | *max_len = handle_length; | ||
73 | type = 1; | ||
74 | } else { | 80 | } else { |
75 | *max_len = handle_length; | 81 | *max_len = handle_length; |
76 | return 255; | 82 | type = 255; |
77 | } | 83 | } |
84 | dput(parent); | ||
78 | return type; | 85 | return type; |
79 | } | 86 | } |
80 | 87 | ||
@@ -123,7 +130,6 @@ static struct dentry *__fh_to_dentry(struct super_block *sb, | |||
123 | return dentry; | 130 | return dentry; |
124 | } | 131 | } |
125 | err = ceph_init_dentry(dentry); | 132 | err = ceph_init_dentry(dentry); |
126 | |||
127 | if (err < 0) { | 133 | if (err < 0) { |
128 | iput(inode); | 134 | iput(inode); |
129 | return ERR_PTR(err); | 135 | return ERR_PTR(err); |